Class: HelixWebServicesClient

Inherits:
Object
  • Object
show all
Defined in:
lib/helix_web_services_client.rb,
lib/helix_web_services_client/jobs.rb,
lib/helix_web_services_client/login.rb,
lib/helix_web_services_client/files.rb,
lib/helix_web_services_client/users.rb,
lib/helix_web_services_client/config.rb,
lib/helix_web_services_client/depots.rb,
lib/helix_web_services_client/labels.rb,
lib/helix_web_services_client/groups.rb,
lib/helix_web_services_client/changes.rb,
lib/helix_web_services_client/servers.rb,
lib/helix_web_services_client/streams.rb,
lib/helix_web_services_client/version.rb,
lib/helix_web_services_client/clients.rb,
lib/helix_web_services_client/branches.rb,
lib/helix_web_services_client/projects.rb,
lib/helix_web_services_client/commands.rb,
lib/helix_web_services_client/triggers.rb,
lib/helix_web_services_client/counters.rb,
lib/helix_web_services_client/helix_sync.rb,
lib/helix_web_services_client/protections.rb,
lib/helix_web_services_client/git_fusion_keys.rb,
lib/helix_web_services_client/git_fusion_repo.rb
more...

Overview

The client object handles authenticating and making calls to Helix Web Services.

See our user guide online at: swarm.workshop.perforce.com/projects/perforce-software-helix-web-services/view/main/build/doc/p4ws.html#ruby_client_sdk_overview

Constant Summary

INITIALIZE_LOCAL_OPTIONS =

Some values to initialize are only used by this class, and are not passed on to the Faraday initializer

[:user, :password, :ticket, :prefix, :api_level, :settings, :debug]
VERSION =
'2015.1.0.pre1'

Instance Attribute Summary (collapse)

Class Method Summary (collapse)

Instance Method Summary (collapse)

Constructor Details

- (HelixWebServicesClient) initialize(options)

Client initialization can handle ensuring a valid security token to the server.

Any client created via new should take care to call close().

Available Options

These options are used to configure the underlying Faraday connection:

  • :url - String base URL.

  • :params - Hash of URI query unencoded key/value pairs.

  • :header - Hash of unencoded HTTP header key/value pairs.

  • :request - Hash of request options.

  • :ssl - Hash of SSL options.

  • :proxy - Hash of Proxy options.

These options are specific to Helix Web Services:

  • :user - The Helix Versioning Engine login

  • :password - If set, we will generate a ticket using this password during initialization

  • :ticket - If not nil, we will use this ticket as our authentication password

  • :debug - Add response logging if set to true

Parameters:

  • options (Hash)

    See the section available options above

[View source]

56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
# File 'lib/helix_web_services_client.rb', line 56

def initialize(options)
  @api_level = options.key?(:api_level) ? options[:api_level] : '78'

  # Filter out options we pass to Faraday
  faraday_options = options.select { |k| !INITIALIZE_LOCAL_OPTIONS.include?(k) }

  @conn = Faraday.new(faraday_options) do |conn|
    conn.request :multipart
    conn.request :url_encoded
    conn.response :logger if options[:debug]
    conn.adapter :net_http
  end

  @conn.headers['Accept'] = 'application/json'

  if options.key?(:url)
    url = URI(options[:url])
    @prefix = url.path ? url.path : ''
  end

  @user = options[:user] if options.key?(:user)

  @ticket = options[:ticket] if options.key?(:ticket)

  if options.key?(:settings)
    options[:settings].each do |key, value|
      add_setting(key, value)
    end
  end

  if options.key?(:password) and @user
    response = @conn.post(path_for('/projects/v1/login'),
                          user: user, password: options[:password])
    assert_ok(response)
    @ticket = JSON.parse(response.body)['ticket']
  end

  set_auth(user, ticket) unless ticket.nil?
end

Instance Attribute Details

- (Object) api_level

The API level to use. Defaults to 78 (2015.1)


26
27
28
# File 'lib/helix_web_services_client.rb', line 26

def api_level
  @api_level
end

- (Object) prefix

Typically, Helix Web Services is mounted under /hws behind a reverse proxy. If a path is specified in the originating URL, we save the prefix here, and preprend it to every request.


23
24
25
# File 'lib/helix_web_services_client.rb', line 23

def prefix
  @prefix
end

- (Object) ticket

Upon successful login, we store the P4 ticket return value here.


18
19
20
# File 'lib/helix_web_services_client.rb', line 18

def ticket
  @ticket
end

- (Object) user

The Helix Versioning Engine login


15
16
17
# File 'lib/helix_web_services_client.rb', line 15

def user
  @user
end

Class Method Details

+ (Object) open(connection)

Provides standard I/O style interface, where when called in a block, will automatically close() the client when done. Otherwise, your code should call client.close() manually.

[View source]

121
122
123
124
125
126
127
128
129
130
131
# File 'lib/helix_web_services_client.rb', line 121

def self.open(connection)
  client = Client.new(connection)

  if block_given?
    yield client
  else
    return client
  end
ensure
  client.close if block_given? && client
end

Instance Method Details

- (Object) add_key(user, key_name, key)

Add a key for a specified user. It will try to add a new SSH key for specified user under a specific name. It will fail if the same key belongs to a different user, if the same key is under a different name and if there is already a key under the specified name. In case key with the same content is present for specified user under the same name - it will skip re-submission.

Parameters:

  • user (String)

    Username to assign SSH key to

  • key_name (String)

    File name to save the key under

  • key (String)

    Content of SSH key

[View source]

27
28
29
30
# File 'lib/helix_web_services_client/git_fusion_keys.rb', line 27

def add_key(user, key_name, key)
  path = "/git-fusion/v1/users/#{user}/keys/#{key_name}"
  execute_method_with_body(:put, path, {'key' => key})
end

- (Object) add_setting(key, value)

Set an override for all requests.

See “configuration” in HWS documentation.

This will automatically add the right prefix for overriding an HWS setting.

Parameters:

  • key (String)

    The setting value as indicated in documentation, e.g., P4PORT

  • value (String)

    The value to set

[View source]

107
108
109
110
111
# File 'lib/helix_web_services_client.rb', line 107

def add_setting(key, value)
  # Note: Rack will automatically convert all hyphens to underscores...
  # but Nginx will (by default) block all underscores. Find a happy middle.
  @conn.headers["X-Perforce-Helix-Web-Services-#{key.gsub('_', '-')}"] = value
end

- (Object) arg_params(arg_values)

Creates a hash and creates keys 'arg1', 'arg2', etc that points to the values in the arg_values array. This is basically only used by the run methods

[View source]

45
46
47
48
49
# File 'lib/helix_web_services_client/commands.rb', line 45

def arg_params(arg_values)
  params = {}
  arg_values.each_index { |ii| params["arg#{ii + 1}"] = arg_values[ii] }
  params
end

- (Object) assert_ok(response)

Raises an error when the response is not 200. Some errors may have diagnostic information in the response body, so we pass that on as well

[View source]

210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
# File 'lib/helix_web_services_client.rb', line 210

def assert_ok(response)
  return unless response.status >= 400
  if response.status == 400
    begin
      messages = JSON.parse(response.body)
    rescue Exception
      messages = response.body
    end
    fail Errors::BadRequest.new(messages)
  elsif response.status == 403
    fail Errors::Unauthenticated.new, 'Illegal login or password'
  elsif response.status == 404
    fail Errors::ResourceNotFound.new, 'Required resource not found'
  elsif response.status == 500 && response.body
    messages = nil
    begin
      messages = JSON.parse(response.body)
    rescue Exception => e
      messages = response.body
    end
    fail Errors::PerforceProblem.new(messages),
         'Unknown issue from the Perforce server'
  else
    fail Errors::ServerError.new, "Unknown problem. Response code: #{response.status}"
  end
end

- (Object) branch(branch)

Returns the branch instance indicated by the branch name (or model)

[View source]

14
15
16
17
18
# File 'lib/helix_web_services_client/branches.rb', line 14

def branch(branch)
  branch = OpenModel.new(branch).branch unless branch.is_a?(String)
  obj = execute_method_with_body(:get, hve_path("branches/#{URI.encode(branch)}"))
  OpenModel.new(obj)
end

- (Object) branches

Array of Branch objects stored in the system. Not all fields will be filled out (e.g., view).

[View source]

8
9
10
11
# File 'lib/helix_web_services_client/branches.rb', line 8

def branches
  arr = execute_method_no_body(:get, hve_path('branches'))
  arr.map { |a| OpenModel.new(a) }
end

- (Object) change(change)

Returns the Change indicated by the change number or model.

If there are files submitted with the change, the change.files field should be filled out.

[View source]

21
22
23
24
25
# File 'lib/helix_web_services_client/changes.rb', line 21

def change(change)
  change_id = change.is_a?(OpenModel) ? change.change : change
  arr = execute_method_no_body(:get, hve_path("changes/#{change_id}"))
  OpenModel.new(arr.first)
end

- (Object) changes(options = nil)

List changelists in the system

options: - :max - cap the number of results - :status - :pending, :submitted, or :shelved (see Change) - :user - The perforce login to check out - :files - Depot path pattern to restrict changes to

[View source]

12
13
14
15
# File 'lib/helix_web_services_client/changes.rb', line 12

def changes(options = nil)
  arr = execute_method_no_body(:get, hve_path('changes'), options)
  arr.map { |obj| OpenModel.new(obj) }
end

- (Object) client(client)

Returns the client instance indicated by the client name or model

[View source]

12
13
14
15
16
# File 'lib/helix_web_services_client/clients.rb', line 12

def client(client)
  client = OpenModel.new(client).client unless client.is_a?(String)
  obj = execute_method_no_body(:get, hve_path("clients/#{URI.encode(client)}"))
  OpenModel.new(obj)
end

- (Object) clients

Array of Client objects stored in the system. Not all fields will be filled out (e.g., view).

[View source]

6
7
8
9
# File 'lib/helix_web_services_client/clients.rb', line 6

def clients
  arr = execute_method_no_body(:get, hve_path('clients'))
  arr.map { |a| OpenModel.new(a) }
end

- (Object) close

[View source]

96
97
# File 'lib/helix_web_services_client.rb', line 96

def close
end

- (OpenModel) command(cmd, *args)

Execute a Perforce command.

First argument should always be the command, followed by command line arguments.

Expect to always have an array of hashes as output.

Not all commands are allowed, since the command will be executed on the web server. In general, if your command requires a client workspace, it will likely fail, or be blocked.

Returns:

  • (OpenModel)

    wraps the output in an OpenModel instance

[View source]

18
19
20
21
22
# File 'lib/helix_web_services_client/commands.rb', line 18

def command(cmd, *args)
  params = arg_params(args)
  arr = execute_method_no_body(:get, hve_path("commands/#{URI.encode(cmd)}"), params)
  arr.map { |a| OpenModel.new(a) } if arr.is_a?(Array)
end

- (Object) command_with_input(cmd, input, *args)

Generic run command with and input body.

The first argument is the general command, followed by the input data, then followed by additional command line arguments.

Expect the output to always be an array of hashes.

Not all commands are allowed, since the command will be executed on the web server. In general, if your command requires a client workspace, it will likely fail, or be blocked.

[View source]

34
35
36
37
38
39
40
# File 'lib/helix_web_services_client/commands.rb', line 34

def command_with_input(cmd, input, *args)
  params = arg_params(args)
  params[:cmd] = cmd
  path = hve_path("commands/#{URI.encode(cmd)}")
  arr = execute_method_with_body(:post, path, params, input)
  arr.map { |a| OpenModel.new(a) } if arr.nil? == false and arr.is_a?(Array)
end

- (Object) commit_change(change)

Submits the shelved changelist.

This changelist should be pending, with no open files, and list of shelved changes. If you require resolves, this method will fail.

Parameters:

  • change (String)

    The changelist number

[View source]

61
62
63
64
# File 'lib/helix_web_services_client/changes.rb', line 61

def commit_change(change)
  change_id = change.is_a?(OpenModel) ? change.change : URI.encode(change)
  execute_method_no_body(:post, hve_path("changes/#{change_id}"))
end

- (Object) counter(counter)

Return the counter hash for a particular counter key.

Parameters:

  • counter (String)

    The counter ID

[View source]

14
15
16
17
# File 'lib/helix_web_services_client/counters.rb', line 14

def counter(counter)
  obj = execute_method_no_body(:get, hve_path("counters/#{URI.encode(counter)}"))
  OpenModel.new(obj)
end

- (Object) counters

List all counters in the system. Each counter typically has a counter and value attribute.

[View source]

6
7
8
9
# File 'lib/helix_web_services_client/counters.rb', line 6

def counters
  arr = execute_method_no_body(:get, hve_path('counters'))
  arr.map { |a| OpenModel.new(a) }
end

- (Object) create_branch(branch)

Creates a new branch in the system.

[View source]

21
22
23
24
# File 'lib/helix_web_services_client/branches.rb', line 21

def create_branch(branch)
  execute_method_with_body(:post, hve_path('branches'), branch)
  true
end

- (Object) create_change(change)

Creates a new changelist, that can be used for a few different tasks.

The change should be a hash with the following top-level keys:

  • Description: The change description (optional)

  • Files: An array of Hashes

Each hash in the Files array can contain these keys:

  • DepotFile: The depot path

  • Action: One of 'upload', 'move', or 'branch'

  • FromDepotFile: if action is 'move' or 'branch', the source file

  • Content: Base64-encoded file content for 'upload' actions

  • RequireVersion: Optional value for 'upload' actions, if set, will fail the upload if the current file version is not this version.

Parameters:

  • change (Hash)

    See method description

[View source]

50
51
52
53
# File 'lib/helix_web_services_client/changes.rb', line 50

def create_change(change)
  change = OpenModel.new(change) unless change.is_a?(OpenModel)
  execute_method_with_body(:post, hve_path('changes'), nil, change.marshal_dump)
end

- (Object) create_client(client)

Creates a new client in the system.

[View source]

19
20
21
22
23
# File 'lib/helix_web_services_client/clients.rb', line 19

def create_client(client)
  client = OpenModel.new(client) unless client.is_a?(OpenModel)
  execute_method_with_body(:post, hve_path('clients'), client.marshal_dump)
  true
end

- (Object) create_depot(depot)

Creates a new depot in the system.

[View source]

20
21
22
23
# File 'lib/helix_web_services_client/depots.rb', line 20

def create_depot(depot)
  depot = OpenModel.new(depot) unless depot.is_a?(OpenModel)
  execute_method_with_body(:post, hve_path('depots'), depot.marshal_dump)
end

- (Object) create_group(group)

Creates a new group in the system.

[View source]

20
21
22
23
# File 'lib/helix_web_services_client/groups.rb', line 20

def create_group(group)
  group = OpenModel.new(group) unless group.is_a?(OpenModel)
  execute_method_with_body(:post, hve_path('groups'), group.marshal_dump)
end

- (Object) create_helix_sync_device_client(project_id, device, root)

Create a new client workspace specification for a Helix Sync project.

Returns a simple object with a 'client' property.

[View source]

8
9
10
11
12
13
14
15
# File 'lib/helix_web_services_client/helix_sync.rb', line 8

def create_helix_sync_device_client(project_id, device, root)
  data = {
      device: device,
      root: root
  }
  obj = execute_method_with_body(:post, "/helix-sync/v1/#{URI.encode(project_id)}/clients/device", nil, data)
  OpenModel.new(obj)
end

- (Object) create_helix_sync_shelf_client(project_id)

[View source]

17
18
19
20
# File 'lib/helix_web_services_client/helix_sync.rb', line 17

def create_helix_sync_shelf_client(project_id)
  obj = execute_method_no_body(:post, "/helix-sync/v1/#{URI.encode(project_id)}/clients/shelf")
  OpenModel.new(obj)
end

- (Object) create_job(job)

Creates a new job in the system.

[View source]

19
20
21
22
23
24
25
# File 'lib/helix_web_services_client/jobs.rb', line 19

def create_job(job)
  job = OpenModel.new(job) unless job.is_a?(OpenModel)
  job.Job = 'new' unless job.job
  job.Status = 'open' unless job.status
  execute_method_with_body(:post, hve_path('jobs'),
                           job.marshal_dump)
end

- (Object) create_label(label)

Creates a new label in the system.

[View source]

20
21
22
23
# File 'lib/helix_web_services_client/labels.rb', line 20

def create_label(label)
  label = OpenModel.new(label) unless label.is_a?(OpenModel)
  execute_method_with_body(:post, hve_path('labels'), label.marshal_dump)
end

- (Object) create_server(server)

Creates a new server in the system based on the Server instance

[View source]

19
20
21
22
# File 'lib/helix_web_services_client/servers.rb', line 19

def create_server(server)
  server = OpenModel.new(server) unless server.is_a?(OpenModel)
  execute_method_with_body(:post, hve_path('servers'), server.marshal_dump)
end

- (Object) create_stream(stream)

Creates a new stream in the system based on the Stream instance

[View source]

21
22
23
24
# File 'lib/helix_web_services_client/streams.rb', line 21

def create_stream(stream)
  stream = OpenModel.new(stream) unless stream.is_a?(OpenModel)
  execute_method_with_body(:post, hve_path('streams'), stream.marshal_dump)
end

- (Object) create_user(user)

Creates a new user in the system based on the User instance

[View source]

19
20
21
22
# File 'lib/helix_web_services_client/users.rb', line 19

def create_user(user)
  user = OpenModel.new(user) unless user.is_a?(OpenModel)
  execute_method_with_body(:post, hve_path('users'), user.marshal_dump)
end

- (Object) delete_branch(branch)

Deletes the branch specification in the system.

[View source]

35
36
37
38
39
# File 'lib/helix_web_services_client/branches.rb', line 35

def delete_branch(branch)
  branch = OpenModel.new(branch).branch unless branch.is_a?(String)
  execute_method_no_body(:delete, hve_path("branches/#{URI.encode(branch)}"))
  true
end

- (Object) delete_client(client)

Deletes the client specification in the system.

[View source]

34
35
36
37
38
# File 'lib/helix_web_services_client/clients.rb', line 34

def delete_client(client)
  client = OpenModel.new(client).client unless client.is_a?(String)
  execute_method_no_body(:delete, hve_path("clients/#{URI.encode(client)}"))
  true
end

- (Object) delete_counter(counter)

Delete the counter

Parameters:

  • counter (String)

    The counter ID

[View source]

37
38
39
# File 'lib/helix_web_services_client/counters.rb', line 37

def delete_counter(counter)
  execute_method_no_body(:delete, hve_path("counters/#{URI.encode(counter)}"))
end

- (Object) delete_depot(depot)

Deletes the depot specification in the system.

[View source]

33
34
35
36
# File 'lib/helix_web_services_client/depots.rb', line 33

def delete_depot(depot)
  depot = depot.depot if depot.is_a?(OpenModel)
  execute_method_no_body(:delete, hve_path("depots/#{URI.encode(depot)}"))
end

- (Object) delete_file(path)

[View source]

106
107
108
109
# File 'lib/helix_web_services_client/files.rb', line 106

def delete_file(path)
  path = encode_path(path)
  execute_method_no_body(:delete, hve_path("files/#{path}"))
end

- (Object) delete_group(group)

Deletes the group specification in the system.

[View source]

33
34
35
36
# File 'lib/helix_web_services_client/groups.rb', line 33

def delete_group(group)
  group = group.group if group.is_a?(OpenModel)
  execute_method_no_body(:delete, hve_path("groups/#{URI.encode(group)}"))
end

- (Object) delete_helix_sync_device_client(project_id, device)

[View source]

22
23
24
25
# File 'lib/helix_web_services_client/helix_sync.rb', line 22

def delete_helix_sync_device_client(project_id, device)
  obj = execute_method_no_body(:delete, "/helix-sync/v1/#{URI.encode(project_id)}/clients/device/#{URI.encode(device)}")
  OpenModel.new(obj)
end

- (Object) delete_helix_sync_pending_changelist(project_id)

Remove the pending changelist used for a Helix Sync project.

[View source]

49
50
51
52
# File 'lib/helix_web_services_client/helix_sync.rb', line 49

def delete_helix_sync_pending_changelist(project_id)
  obj = execute_method_no_body(:delete, "/helix-sync/v1/#{URI.encode(project_id)}/pending")
  OpenModel.new(obj)
end

- (Object) delete_helix_sync_shelf_client(project_id)

[View source]

27
28
29
30
# File 'lib/helix_web_services_client/helix_sync.rb', line 27

def delete_helix_sync_shelf_client(project_id)
  obj = execute_method_no_body(:delete, "/helix-sync/v1/#{URI.encode(project_id)}/clients/shelf")
  OpenModel.new(obj)
end

- (Object) delete_job(job_id)

Deletes the job specification in the system.

[View source]

35
36
37
# File 'lib/helix_web_services_client/jobs.rb', line 35

def delete_job(job_id)
  execute_method_no_body(:delete, hve_path("jobs/#{URI.encode(job_id)}"))
end

- (Object) delete_key(user, key_name)

Delete a specific SSH key. It accepts an SSH key looks up the owner and then proceeds to remove it.

Parameters:

  • key (String)

    SSH key string to be removed

[View source]

35
36
37
38
# File 'lib/helix_web_services_client/git_fusion_keys.rb', line 35

def delete_key(user, key_name)
  path = "/git-fusion/v1/users/#{user}/keys/#{key_name}"
  execute_method_no_body(:delete, path)
end

- (Object) delete_keys(user)

Delete all keys for a user. All keys for specified user will be deleted from perforce.

Parameters:

  • user (String)

    Chosen user to remove all keys for

[View source]

43
44
45
46
# File 'lib/helix_web_services_client/git_fusion_keys.rb', line 43

def delete_keys(user)
  path = "/git-fusion/v1/users/#{user}/keys"
  execute_method_no_body(:delete, path)
end

- (Object) delete_label(label)

Deletes the label specification in the system.

[View source]

33
34
35
36
# File 'lib/helix_web_services_client/labels.rb', line 33

def delete_label(label)
  label = label.label if label.is_a?(OpenModel)
  execute_method_no_body(:delete, hve_path("labels/#{URI.encode(label)}"))
end

- (Object) delete_repo(repo_name)

Delete a repository. This will remove config file for specified repository, removing it in result.

Parameters:

  • repo_name (String)

    Repository name to be encoded to git_fusion standards

[View source]

57
58
59
60
# File 'lib/helix_web_services_client/git_fusion_repo.rb', line 57

def delete_repo(repo_name)
  path = "/git-fusion/v1/repos/#{GitFusionStrings.encode(repo_name)}"
  execute_method_no_body(:delete, path)
end

- (Object) delete_server(server)

[View source]

31
32
33
34
# File 'lib/helix_web_services_client/servers.rb', line 31

def delete_server(server)
  server = server.server_id if server.is_a?(OpenModel)
  execute_method_no_body(:delete, hve_path("servers/#{URI.encode(server)}"))
end

- (Object) delete_stream(stream)

[View source]

32
33
34
35
# File 'lib/helix_web_services_client/streams.rb', line 32

def delete_stream(stream)
  stream = stream.stream if stream.is_a?(OpenModel)
  execute_method_no_body(:delete, hve_path("streams/#{URI.encode(stream)}"))
end

- (Object) delete_user(user)

[View source]

30
31
32
33
# File 'lib/helix_web_services_client/users.rb', line 30

def delete_user(user)
  user = user.user if user.is_a?(OpenModel)
  execute_method_no_body(:delete, hve_path("users/#{URI.encode(user)}"))
end

- (Object) depot(depot)

Returns the depot instance indicated by the depot name (or depot object)

[View source]

13
14
15
16
17
# File 'lib/helix_web_services_client/depots.rb', line 13

def depot(depot)
  depot = depot.depot if depot.is_a?(OpenModel)
  obj = execute_method_no_body(:get, hve_path("depots/#{URI.encode(depot)}"))
  OpenModel.new(obj)
end

- (Object) depots

Array of Depot objects stored in the system. Not all fields will be filled out (e.g., view).

[View source]

7
8
9
10
# File 'lib/helix_web_services_client/depots.rb', line 7

def depots
  arr = execute_method_no_body(:get, hve_path('depots'))
  arr.map { |a| OpenModel.new(a) }
end

- (Object) encode_component(str)

Parameters:

  • str (String)

    Component to be URI escaped

[View source]

52
53
54
55
56
57
58
59
60
# File 'lib/helix_web_services_client/git_fusion_keys.rb', line 52

def encode_component(str)
  str.chars.map do |ch|
    if GitFusionStrings::URI_RESERVED_CHARACTERS.include?(ch)
      '%' + ch.ord.to_s(16)
    else
      ch
    end
  end.join('')
end

- (Object) execute_method_no_body(method, path, params = nil)

Runs the method against Helix Web Services, checks for errors, then parses the JSON response.

Parameters:

  • method (Symbol)

    HTTP method, for example, :get, :post, :delete

  • path (String)

    URL path part (no URI parameters) for the method

  • params (Hash) (defaults to: nil)

    URI parameters to send in

[View source]

150
151
152
153
# File 'lib/helix_web_services_client.rb', line 150

def execute_method_no_body(method, path, params = nil)
  response = run_method_no_body(method, path, params)
  JSON.parse(response.body) if response.body && !response.body.empty?
end

- (Object) execute_method_with_body(method, path, params = nil, body = nil)

Runs the method against Helix Web Services, checks for errors, then parses the JSON response.

This variation will send the body (expected to be a Hash) as JSON to the server.

Parameters:

  • method (Symbol)

    HTTP method, for example, :get, :post, :delete

  • path (String)

    URL path part (no URI parameters) for the method

  • params (Hash) (defaults to: nil)

    URI parameters to send in

  • body (Hash) (defaults to: nil)

    The Request content (which will be converted to JSON)

[View source]

165
166
167
168
# File 'lib/helix_web_services_client.rb', line 165

def execute_method_with_body(method, path, params = nil, body = nil)
  response = run_method_with_body(method, path, params, body)
  JSON.parse(response.body) if response.body && !response.body.empty?
end

- (Object) fetch_helix_sync_latest_changelist(project_id)

Retrieve the latest changelist.

If the change doesn't exist, you'll get a ResourceNotFound exception.

[View source]

35
36
37
38
# File 'lib/helix_web_services_client/helix_sync.rb', line 35

def fetch_helix_sync_latest_changelist(project_id)
  obj = execute_method_no_body(:get, "/helix-sync/v1/#{URI.encode(project_id)}/last-change")
  OpenModel.new(obj)
end

- (Object) fetch_helix_sync_pending_changelist(project_id)

Retrieve the pending changelist.

If the change doesn't exist, you'll get a ResourceNotFound exception.

[View source]

43
44
45
46
# File 'lib/helix_web_services_client/helix_sync.rb', line 43

def fetch_helix_sync_pending_changelist(project_id)
  obj = execute_method_no_body(:get, "/helix-sync/v1/#{URI.encode(project_id)}/pending")
  OpenModel.new(obj)
end

- (Object) file(path)

Returns the file metadata at this location, with the content field filled out.

If path happens to be a directory, this method is synonymous with the files() method.

[View source]

48
49
50
# File 'lib/helix_web_services_client/files.rb', line 48

def file(path)
  files(path)
end

- (Object) files(path = '')

General file browsing method.

The path parameter should be a directory location, starting with a depot location, e.g., my_depot/dir1.

When path is empty, will return the list of depots.

Note: if path happens to be a file, instead of a directory, this is a synonym with the file() method.

If the path contains wildcards, the return will only be the list of HelixWebServicesClient::Models::File instances.

See also the HelixWebServicesClient::Models::File, HelixWebServicesClient::Models::Dir, and HelixWebServicesClient::Models::Depot for the output types.

[View source]

21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
# File 'lib/helix_web_services_client/files.rb', line 21

def files(path = '')
  unless path.empty?
    path = path.split('/').map { |p| URI.encode(p) }.join('/')
  end

  arr = nil

  if wildcards?(path)
    arr = execute_method_no_body(:get, hve_path('files'), path: path)
  else
    arr = execute_method_no_body(:get, hve_path("files/#{path}"))
  end

  if arr.is_a?(Array)
    arr.map{ |x| OpenModel.new(x) }
  else
    m = OpenModel.new(arr)
    m.Content = Base64.decode64(m.content)
    m
  end
end

- (Object) group(group)

Returns the group instance indicated by the group name (or group object)

[View source]

13
14
15
16
17
# File 'lib/helix_web_services_client/groups.rb', line 13

def group(group)
  group = group.group if group.is_a?(OpenModel)
  obj = execute_method_no_body(:get, hve_path("groups/#{URI.encode(group)}"))
  OpenModel.new(obj)
end

- (Object) groups

Array of Group objects stored in the system. Not all fields will be filled out (e.g., view).

[View source]

7
8
9
10
# File 'lib/helix_web_services_client/groups.rb', line 7

def groups
  arr = execute_method_no_body(:get, hve_path('groups'))
  arr.map { |x| OpenModel.new(x) }
end

- (Object) hve_path(subpath)

[View source]

237
238
239
# File 'lib/helix_web_services_client.rb', line 237

def hve_path(subpath)
  "/p4/v#{api_level}/#{subpath}"
end

- (Object) increment_counter(counter)

Increment the value of a numerical counter

Parameters:

  • counter (String)

    The counter ID

[View source]

22
23
24
# File 'lib/helix_web_services_client/counters.rb', line 22

def increment_counter(counter)
  execute_method_no_body(:post, hve_path("counters/#{URI.encode(counter)}/increment"))
end

- (Object) job(job_id)

Returns the array of jobs in the system. Each job model is simply a hash of string -> string values, since each system can very likely adjust job output.

[View source]

13
14
15
16
# File 'lib/helix_web_services_client/jobs.rb', line 13

def job(job_id)
  obj = execute_method_no_body(:get, hve_path("jobs/#{URI.encode(job_id)}"))
  OpenModel.new(obj)
end

- (Object) jobs

[View source]

5
6
7
8
# File 'lib/helix_web_services_client/jobs.rb', line 5

def jobs
  arr = execute_method_no_body(:get, hve_path('jobs'))
  arr.map { |x| OpenModel.new(x) }
end

- (Object) keys(user)

Return all keys for specified user. Every entry contains key name and its contents.

Parameters:

  • user (String)

    Username for which keys will be fetched

[View source]

13
14
15
16
# File 'lib/helix_web_services_client/git_fusion_keys.rb', line 13

def keys(user)
  path = "/git-fusion/v1/users/#{user}/keys"
  execute_method_no_body(:get, path)
end

- (Object) label(label)

Returns the label instance indicated by the label name (or label object)

[View source]

13
14
15
16
17
# File 'lib/helix_web_services_client/labels.rb', line 13

def label(label)
  label = label.label if label.is_a?(OpenModel)
  obj = execute_method_no_body(:get, hve_path("labels/#{URI.encode(label)}"))
  OpenModel.new(obj)
end

- (Object) labels

Array of Label objects stored in the system. Not all fields will be filled out (e.g., view).

[View source]

7
8
9
10
# File 'lib/helix_web_services_client/labels.rb', line 7

def labels
  arr = execute_method_no_body(:get, hve_path('labels'))
  arr.map { |a| OpenModel.new(a) }
end

- (Object) list_repos

Return list of configured repositories. It will fetch all configured repositories returning a list of hashes with id and name of the repository, where id is a git-fusion encoded name, and name is a full human-readable string.

[View source]

14
15
16
# File 'lib/helix_web_services_client/git_fusion_repo.rb', line 14

def list_repos
  execute_method_no_body(:get, '/git-fusion/v1/repos')
end

- (Object) login(user, password)

Generates a host unlocked ticket for the user.

In some installations, such as Helix Cloud, the authentication source is not the p4d instance used for connections. This allows you to generate p4 ticket which should then be passed along as the P4PASSWD per-request header.

Parameters:

  • user (String)
  • password (String)
[View source]

11
12
13
14
15
# File 'lib/helix_web_services_client/login.rb', line 11

def (user, password)
  obj = execute_method_with_body(:post, hve_path('login'), nil,
                                 {user: user, password: password})
  obj['ticket']
end

- (Boolean) p4_ticket?(str)

Returns:

  • (Boolean)
[View source]

140
141
142
# File 'lib/helix_web_services_client.rb', line 140

def p4_ticket?(str)
  /^[a-zA-Z0-9]{32,}$/.match(str) != nil
end

- (Object) path_for(subpath)

Basically just prepends the prefix to our subpath, typically, '/p4'.

[View source]

198
199
200
201
202
203
204
205
206
# File 'lib/helix_web_services_client.rb', line 198

def path_for(subpath)
  if @prefix.nil? || @prefix.empty?
    subpath
  elsif subpath.nil? or subpath.empty?
    @prefix
  else
    File.join(@prefix, subpath)
  end
end

- (Object) preview_helix_sync_pending_change(project_id)

“Preview”, or generate the resolve plan, for the pending changelist.

If the change doesn't exist, you'll get a ResourceNotFound exception.

[View source]

57
58
59
60
# File 'lib/helix_web_services_client/helix_sync.rb', line 57

def preview_helix_sync_pending_change(project_id)
  arr = execute_method_no_body(:get, "/helix-sync/v1/#{URI.encode(project_id)}/preview")
  arr.map { |o| OpenModel.new(o) }
end

- (Object) project(project_id)

Return the project details

Parameters:

  • project_id (String)

    The project's String id

[View source]

23
24
25
26
27
# File 'lib/helix_web_services_client/projects.rb', line 23

def project(project_id)
  path = "/projects/v1/#{URI.encode(project_id)}"
  obj = execute_method_no_body(:get, path)
  OpenModel.new(obj)
end

- (Object) projects(details: nil, extension: nil)

Lists the projects available on the server for the user.

Parameters:

  • details (Boolean)

    Defaults to false, if true, output will be an array of project details. If false, output will be an array of project IDs.

  • extension (String)

    If set, will only return projects with the indicated extension ID.

[View source]

11
12
13
14
15
16
17
18
# File 'lib/helix_web_services_client/projects.rb', line 11

def projects(details: nil, extension: nil)
  query = {}
  query[:details] = details if details
  query[:extension] = extension if extension
  arr = execute_method_no_body(:get, '/projects/v1', query)
  arr = arr.map { |a| OpenModel.new(a) } if details
  arr
end

- (Object) protections

Fetch all protections in the system. Returns a single Protections instance.

[View source]

6
7
8
9
# File 'lib/helix_web_services_client/protections.rb', line 6

def protections
  obj = execute_method_no_body(:get, hve_path('protections'))
  OpenModel.new(obj)
end

- (Object) remove_setting(key)

Remove a setting added via add_setting

[View source]

114
115
116
# File 'lib/helix_web_services_client.rb', line 114

def remove_setting(key)
  @conn.headers.delete("X-Perforce-Helix-Web-Services-#{key}")
end

- (Object) repo(repo_name)

Return the repository details. For specified repository it will fetch and return currently submitted configuration.

Parameters:

  • repo_name (String)

    Repository name to be encoded to git-fusion standards

[View source]

22
23
24
25
# File 'lib/helix_web_services_client/git_fusion_repo.rb', line 22

def repo(repo_name)
  path = "/git-fusion/v1/repos/#{GitFusionStrings.encode(repo_name)}"
  execute_method_no_body(:get, path)
end

- (Object) run_method_no_body(method, path, params = nil)

[View source]

170
171
172
173
174
175
176
# File 'lib/helix_web_services_client.rb', line 170

def run_method_no_body(method, path, params = nil)
  path = path_for(path)

  response = @conn.send(method, path, params)
  assert_ok(response)
  response
end

- (Object) run_method_with_body(method, path, params = nil, body = nil)

[View source]

178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
# File 'lib/helix_web_services_client.rb', line 178

def run_method_with_body(method, path, params = nil, body = nil)
  if !body && params
    body = params
    params = nil
  end

  path = path_for(path)

  if params
    params_hash = Faraday::Utils::ParamsHash.new
    params_hash.merge!(params)
    path += "?#{params_hash.to_query}"
  end

  response = @conn.send(method, path, body)
  assert_ok(response)
  response
end

- (Object) server(server)

Returns a HelixWebServicesClient::OpenModel for the login

[View source]

12
13
14
15
16
# File 'lib/helix_web_services_client/servers.rb', line 12

def server(server)
  server = server.ServerID if server.is_a?(OpenModel)
  obj = execute_method_no_body(:get, hve_path("servers/#{URI.encode(server)}"))
  OpenModel.new(obj)
end

- (Object) servers

Returns an array of Server objects representing people in the system.

[View source]

6
7
8
9
# File 'lib/helix_web_services_client/servers.rb', line 6

def servers
  arr = execute_method_no_body(:get, hve_path('servers'))
  arr.map { |obj| OpenModel.new(obj) }
end

- (Object) services

Returns an array of all service definitions in the system. Each definition is a hash with type and uri values.

[View source]

8
9
10
# File 'lib/helix_web_services_client/config.rb', line 8

def services
  execute_method_no_body(:get, '/config/v1/services')
end

- (Object) set_auth(user, token)

Note: this class is really just common implementation. Methods are generally defined in other files that reopen this class.

[View source]

136
137
138
# File 'lib/helix_web_services_client.rb', line 136

def set_auth(user, token)
  @conn.basic_auth(user, token)
end

- (Object) set_counter(counter)

Set the counter value

Parameters:

  • counter (Hash|OpenModel)

    A has containing counter and value properties

[View source]

29
30
31
32
# File 'lib/helix_web_services_client/counters.rb', line 29

def set_counter(counter)
  counter = OpenModel.new(counter) unless counter.is_a?(OpenModel)
  execute_method_with_body(:put, hve_path("counters/#{URI.encode(counter.counter)}"), counter.marshal_dump)
end

- (Object) stream(stream)

Fetch single stream details

Returns:

  • An OpenModel wrapper around the stream data

[View source]

14
15
16
17
18
# File 'lib/helix_web_services_client/streams.rb', line 14

def stream(stream)
  stream = stream.stream if stream.is_a?(OpenModel)
  obj = execute_method_no_body(:get, hve_path("streams/#{URI.encode(stream)}"))
  OpenModel.new(obj)
end

- (Object) streams

Returns an array of Stream objects representing people in the system.

[View source]

6
7
8
9
# File 'lib/helix_web_services_client/streams.rb', line 6

def streams
  arr = execute_method_no_body(:get, hve_path('streams'))
  arr.map { |obj| OpenModel.new(obj) }
end

- (Object) submit_config(repo_name, config)

Replace config for a specified repository. This will replace current config for a Git Fusion repo with a new one under the same name, for the same path.

Parameters:

  • repo_name (String)

    Repository name to be encoded to git-fusion standards

  • config (String)

    GitFusion config file

[View source]

40
41
42
43
# File 'lib/helix_web_services_client/git_fusion_repo.rb', line 40

def submit_config(repo_name, config)
  path = "/git-fusion/v1/repos/#{GitFusionStrings.encode(repo_name)}"
  execute_method_with_body(:put, path, {'config' => config})
end

- (Object) submit_helix_sync_pending_change(project_id)

Submits the pending changelist for the helix sync project.

Currently this assumes that all files are shelved and nothing's open on the client. This is likely not what we want … but it's a start.

Parameters:

  • project_id (String)
[View source]

68
69
70
71
# File 'lib/helix_web_services_client/helix_sync.rb', line 68

def submit_helix_sync_pending_change(project_id)
  obj = execute_method_no_body(:post, "/helix-sync/v1/#{URI.encode(project_id)}/submit")
  OpenModel.new(obj)
end

- (OpenModel) triggers

Fetch the list of trigger lines in the system.

Returns:

  • (OpenModel)

    A hash with a Triggers property that is an array of lines in the triggers table.

[View source]

8
9
10
11
# File 'lib/helix_web_services_client/triggers.rb', line 8

def triggers
  obj = execute_method_no_body(:get, hve_path('triggers'))
  OpenModel.new(obj)
end

- (Object) update_branch(branch)

Updates the branch specification.

[View source]

27
28
29
30
31
32
# File 'lib/helix_web_services_client/branches.rb', line 27

def update_branch(branch)
  branch = OpenModel.new(branch) unless branch.is_a?(OpenModel)
  execute_method_with_body(:patch, hve_path("branches/#{URI.encode(branch.branch)}"),
                           branch.marshal_dump)
  true
end

- (Object) update_client(client)

Updates the client specification.

[View source]

26
27
28
29
30
31
# File 'lib/helix_web_services_client/clients.rb', line 26

def update_client(client)
  client = OpenModel.new(client) unless client.is_a?(OpenModel)
  execute_method_with_body(:patch, hve_path("clients/#{URI.encode(client.client)}"),
                           client.marshal_dump)
  true
end

- (Object) update_config(repo_name, config)

Modify config for a specified repository. This will update chosen parts of p4gf_file.

Parameters:

  • repo_name (String)

    Repository name to be encoded to git-fusion standards

  • config (String)

    String to update in current p4gf_config file

[View source]

49
50
51
# File 'lib/helix_web_services_client/git_fusion_repo.rb', line 49

def update_config(repo_name, config)
  execute_method_with_body(:patch, "/git-fusion/v1/repos/#{GitFusionStrings.encode(repo_name)}", {'config' => config})
end

- (Object) update_depot(depot)

Updates the depot specification.

[View source]

26
27
28
29
30
# File 'lib/helix_web_services_client/depots.rb', line 26

def update_depot(depot)
  depot = OpenModel.new(depot) unless depot.is_a?(OpenModel)
  execute_method_with_body(:patch, hve_path("depots/#{URI.encode(depot.depot)}"),
                           depot.marshal_dump)
end

- (Object) update_group(group)

Updates the group specification.

[View source]

26
27
28
29
30
# File 'lib/helix_web_services_client/groups.rb', line 26

def update_group(group)
  group = OpenModel.new(group) unless group.is_a?(OpenModel)
  execute_method_with_body(:patch, hve_path("groups/#{URI.encode(group.group)}"),
                           group.marshal_dump)
end

- (Object) update_job(job)

Updates the job specification.

[View source]

28
29
30
31
32
# File 'lib/helix_web_services_client/jobs.rb', line 28

def update_job(job)
  job = OpenModel.new(job) unless job.is_a?(OpenModel)
  execute_method_with_body(:patch, hve_path("jobs/#{URI.encode(job['Job'])}"),
                           job.marshal_dump)
end

- (Object) update_label(label)

Updates the label specification.

[View source]

26
27
28
29
30
# File 'lib/helix_web_services_client/labels.rb', line 26

def update_label(label)
  label = OpenModel.new(label) unless label.is_a?(OpenModel)
  execute_method_with_body(:patch, hve_path("labels/#{URI.encode(label.label)}"),
                           label.marshal_dump)
end

- (Object) update_protections(protections)

Updates the protections table based on the Protections instance passed in

Parameters:

  • protections (Hash|OpenModel)

    A hash with a protections property that is an Array of protections entries

[View source]

15
16
17
18
19
# File 'lib/helix_web_services_client/protections.rb', line 15

def update_protections(protections)
  protections = OpenModel.new(protections) unless protections.is_a?(OpenModel)
  execute_method_with_body(:put, hve_path('protections'),
                           protections.marshal_dump)
end

- (Object) update_server(server)

[View source]

24
25
26
27
28
29
# File 'lib/helix_web_services_client/servers.rb', line 24

def update_server(server)
  server = OpenModel.new(server) unless server.is_a?(OpenModel)
  execute_method_with_body(:patch,
                           hve_path("servers/#{URI.encode(server.ServerID)}"),
                           server.marshal_dump)
end

- (Object) update_stream(stream)

[View source]

26
27
28
29
30
# File 'lib/helix_web_services_client/streams.rb', line 26

def update_stream(stream)
  stream = OpenModel.new(stream) unless stream.is_a?(OpenModel)
  execute_method_with_body(:patch, hve_path("streams/#{URI.encode(stream.stream)}"),
                           stream.marshal_dump)
end

- (Object) update_triggers(triggers)

Update the triggers table using the Triggers model instance

Parameters:

  • triggers (Hash|OpenModel)

    A hash with a Triggers property

[View source]

16
17
18
19
# File 'lib/helix_web_services_client/triggers.rb', line 16

def update_triggers(triggers)
  triggers = OpenModel.new(triggers) unless triggers.is_a?(OpenModel)
  execute_method_with_body(:put, hve_path('triggers'), triggers.marshal_dump)
end

- (Object) update_user(user)

[View source]

24
25
26
27
28
# File 'lib/helix_web_services_client/users.rb', line 24

def update_user(user)
  user = OpenModel.new(user) unless user.is_a?(OpenModel)
  execute_method_with_body(:patch, hve_path("users/#{URI.encode(user.user)}"),
                           user.marshal_dump)
end

- (Object) upload_file(file)

Upload a single file's content.

The file hash should contain the following fields:

  • DepotFile: target depot path

  • Content: file content

Parameters:

  • file (Hash)

    See description

[View source]

60
61
62
63
64
65
66
67
68
69
70
71
# File 'lib/helix_web_services_client/files.rb', line 60

def upload_file(file)
  file = OpenModel.new(file) unless file.is_a?(OpenModel)
  path = encode_path(file.depot_file)
  body = {
      'DepotFile' => file.depot_file,
      'Content' => Base64.encode64(file.content)
  }
  execute_method_with_body(:patch,
                           hve_path("files/#{path}"),
                           nil,
                           body)
end

- (Object) upload_files(files: [], path: nil, description: nil)

Upload multiple files

Each file in the Files array should have two fields

  • DepotFile: target path, can be relative if path is indicated

  • Content: File content

The optional path parameter can indicate the root directory for all files.

Parameters:

  • files (Array)

    See description

  • path (String)

    If set, the root directory for all files

  • description (String)

    Informative message about the change

[View source]

86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
# File 'lib/helix_web_services_client/files.rb', line 86

def upload_files(files: [], path: nil, description: nil)
  files = files.map do |f|
    OpenModel.new(f) unless f.is_a?(OpenModel)
  end

  path = path ? encode_path(path) : ''

  obj = {
      'Files' => files.map do |f|
        {
            'DepotFile' => f.depot_file,
            'Content' => Base64.encode64(f.content)
        }
      end
  }
  obj['Description'] = description if description

  execute_method_with_body(:patch, hve_path("files/#{path}"), nil, obj)
end

- (Object) user_details(user)

Returns a HelixWebServicesClient::OpenModel for the login

[View source]

12
13
14
15
16
# File 'lib/helix_web_services_client/users.rb', line 12

def user_details(user)
  user = user.user if user.is_a?(OpenModel)
  obj = execute_method_no_body(:get, hve_path("users/#{URI.encode(user)}"))
  OpenModel.new(obj)
end

- (Object) users

Returns an array of User objects representing people in the system.

[View source]

6
7
8
9
# File 'lib/helix_web_services_client/users.rb', line 6

def users
  arr = execute_method_no_body(:get, hve_path('users'))
  arr.map { |obj| OpenModel.new(obj) }
end

- (Object) version

Return the product version ID of the Helix Web Services instance

[View source]

242
243
244
245
# File 'lib/helix_web_services_client.rb', line 242

def version
  response = run_method_no_body(:get, '/status')
  response.headers['X-Helix-Web-Services-Version']
end