aspera-cli 4.24.1 → 4.25.0.pre

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (99) hide show
  1. checksums.yaml +4 -4
  2. checksums.yaml.gz.sig +0 -0
  3. data/CHANGELOG.md +1064 -745
  4. data/CONTRIBUTING.md +43 -100
  5. data/README.md +1281 -720
  6. data/bin/ascli +20 -1
  7. data/bin/asession +23 -27
  8. data/lib/aspera/agent/base.rb +10 -21
  9. data/lib/aspera/agent/connect.rb +2 -3
  10. data/lib/aspera/agent/desktop.rb +2 -2
  11. data/lib/aspera/agent/direct.rb +49 -32
  12. data/lib/aspera/agent/factory.rb +31 -0
  13. data/lib/aspera/api/aoc.rb +134 -76
  14. data/lib/aspera/api/cos_node.rb +3 -2
  15. data/lib/aspera/api/faspex.rb +213 -0
  16. data/lib/aspera/api/node.rb +107 -94
  17. data/lib/aspera/ascmd.rb +1 -2
  18. data/lib/aspera/ascp/installation.rb +73 -58
  19. data/lib/aspera/ascp/management.rb +119 -23
  20. data/lib/aspera/assert.rb +39 -11
  21. data/lib/aspera/cli/error.rb +4 -2
  22. data/lib/aspera/cli/extended_value.rb +91 -67
  23. data/lib/aspera/cli/formatter.rb +62 -27
  24. data/lib/aspera/cli/hints.rb +8 -0
  25. data/lib/aspera/cli/info.rb +4 -4
  26. data/lib/aspera/cli/main.rb +76 -84
  27. data/lib/aspera/cli/manager.rb +352 -248
  28. data/lib/aspera/cli/plugins/alee.rb +5 -4
  29. data/lib/aspera/cli/plugins/aoc.rb +175 -195
  30. data/lib/aspera/cli/plugins/ats.rb +4 -4
  31. data/lib/aspera/cli/plugins/base.rb +343 -0
  32. data/lib/aspera/cli/plugins/basic_auth.rb +45 -0
  33. data/lib/aspera/cli/plugins/config.rb +283 -269
  34. data/lib/aspera/cli/plugins/console.rb +27 -22
  35. data/lib/aspera/cli/plugins/cos.rb +3 -3
  36. data/lib/aspera/cli/plugins/factory.rb +78 -0
  37. data/lib/aspera/cli/plugins/faspex.rb +49 -46
  38. data/lib/aspera/cli/plugins/faspex5.rb +113 -225
  39. data/lib/aspera/cli/plugins/faspio.rb +19 -18
  40. data/lib/aspera/cli/plugins/httpgw.rb +14 -13
  41. data/lib/aspera/cli/plugins/node.rb +162 -149
  42. data/lib/aspera/cli/plugins/oauth.rb +48 -0
  43. data/lib/aspera/cli/plugins/orchestrator.rb +129 -45
  44. data/lib/aspera/cli/plugins/preview.rb +30 -50
  45. data/lib/aspera/cli/plugins/server.rb +21 -21
  46. data/lib/aspera/cli/plugins/shares.rb +45 -47
  47. data/lib/aspera/cli/sync_actions.rb +50 -39
  48. data/lib/aspera/cli/transfer_agent.rb +35 -49
  49. data/lib/aspera/cli/transfer_progress.rb +6 -6
  50. data/lib/aspera/cli/version.rb +3 -3
  51. data/lib/aspera/cli/wizard.rb +70 -55
  52. data/lib/aspera/colors.rb +6 -0
  53. data/lib/aspera/command_line_builder.rb +59 -61
  54. data/lib/aspera/command_line_converter.rb +2 -1
  55. data/lib/aspera/coverage.rb +2 -2
  56. data/lib/aspera/data_repository.rb +1 -1
  57. data/lib/aspera/environment.rb +51 -41
  58. data/lib/aspera/faspex_gw.rb +7 -5
  59. data/lib/aspera/faspex_postproc.rb +1 -1
  60. data/lib/aspera/keychain/factory.rb +1 -2
  61. data/lib/aspera/keychain/macos_security.rb +1 -1
  62. data/lib/aspera/log.rb +37 -9
  63. data/lib/aspera/markdown.rb +31 -0
  64. data/lib/aspera/nagios.rb +7 -6
  65. data/lib/aspera/oauth/base.rb +25 -28
  66. data/lib/aspera/oauth/factory.rb +9 -9
  67. data/lib/aspera/oauth/url_json.rb +2 -1
  68. data/lib/aspera/oauth/web.rb +2 -2
  69. data/lib/aspera/preview/file_types.rb +23 -37
  70. data/lib/aspera/products/connect.rb +7 -6
  71. data/lib/aspera/products/desktop.rb +1 -4
  72. data/lib/aspera/products/other.rb +9 -1
  73. data/lib/aspera/products/transferd.rb +0 -1
  74. data/lib/aspera/rest.rb +168 -113
  75. data/lib/aspera/rest_error_analyzer.rb +4 -4
  76. data/lib/aspera/ssh.rb +7 -4
  77. data/lib/aspera/ssl.rb +41 -0
  78. data/lib/aspera/sync/args.schema.yaml +46 -3
  79. data/lib/aspera/sync/conf.schema.yaml +307 -123
  80. data/lib/aspera/sync/database.rb +2 -1
  81. data/lib/aspera/sync/operations.rb +135 -79
  82. data/lib/aspera/temp_file_manager.rb +17 -5
  83. data/lib/aspera/transfer/error.rb +16 -7
  84. data/lib/aspera/transfer/parameters.rb +35 -22
  85. data/lib/aspera/transfer/resumer.rb +74 -0
  86. data/lib/aspera/transfer/spec.rb +5 -5
  87. data/lib/aspera/transfer/spec.schema.yaml +170 -59
  88. data/lib/aspera/transfer/spec_doc.rb +49 -43
  89. data/lib/aspera/uri_reader.rb +2 -2
  90. data/lib/aspera/web_auth.rb +6 -6
  91. data/lib/transferd_pb.rb +2 -2
  92. data.tar.gz.sig +0 -0
  93. metadata +26 -11
  94. metadata.gz.sig +0 -0
  95. data/lib/aspera/cli/basic_auth_plugin.rb +0 -43
  96. data/lib/aspera/cli/plugin.rb +0 -333
  97. data/lib/aspera/cli/plugin_factory.rb +0 -81
  98. data/lib/aspera/resumer.rb +0 -77
  99. data/lib/aspera/transfer/error_info.rb +0 -91
@@ -1,12 +1,12 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require 'aspera/cli/basic_auth_plugin'
3
+ require 'aspera/cli/plugins/basic_auth'
4
4
  require 'aspera/nagios'
5
5
 
6
6
  module Aspera
7
7
  module Cli
8
8
  module Plugins
9
- class Console < Cli::BasicAuthPlugin
9
+ class Console < BasicAuth
10
10
  STANDARD_PATH = '/aspera/console'
11
11
  DEFAULT_FILTER_AGE_SECONDS = 24 * 3600
12
12
  EXPR_RE = /\A(\S+) (\S+) (.*)\z/
@@ -22,17 +22,18 @@ module Aspera
22
22
  next unless base_url.start_with?('https://')
23
23
  api = Rest.new(base_url: base_url, redirect_max: 2)
24
24
  test_endpoint = 'login'
25
- test_page = api.call(
25
+ http = api.call(
26
26
  operation: 'GET',
27
27
  subpath: test_endpoint,
28
- query: {local: true}
28
+ query: {local: true},
29
+ ret: :resp
29
30
  )
30
- next unless test_page[:http].body.include?('Aspera Console')
31
+ next unless http.body.include?('Aspera Console')
31
32
  version = 'unknown'
32
- if (m = test_page[:http].body.match(/\(v([1-9]\..*)\)/))
33
+ if (m = http.body.match(/\(v([1-9]\..*)\)/))
33
34
  version = m[1]
34
35
  end
35
- url = test_page[:http].uri.to_s
36
+ url = http.uri.to_s
36
37
  return {
37
38
  version: version,
38
39
  url: url[0..url.index(test_endpoint) - 2]
@@ -45,21 +46,25 @@ module Aspera
45
46
  return
46
47
  end
47
48
 
48
- # @param object [Plugin] An instance of this class
49
- # @return [Hash] :preset_value, :test_args
50
- def wizard(object:)
51
- options = object.options
52
- return {
53
- preset_value: {
54
- url: options.get_option(:url, mandatory: true),
55
- username: options.get_option(:username, mandatory: true),
56
- password: options.get_option(:password, mandatory: true)
57
- },
58
- test_args: 'transfer list'
59
- }
49
+ def time_to_string(time)
50
+ return time.strftime('%Y-%m-%d %H:%M:%S')
60
51
  end
61
52
  end
62
53
 
54
+ # @param wizard [Wizard] The wizard object
55
+ # @param app_url [Wizard] The wizard object
56
+ # @return [Hash] :preset_value, :test_args
57
+ def wizard(wizard, app_url)
58
+ return {
59
+ preset_value: {
60
+ url: app_url,
61
+ username: options.get_option(:username, mandatory: true),
62
+ password: options.get_option(:password, mandatory: true)
63
+ },
64
+ test_args: 'transfer list'
65
+ }
66
+ end
67
+
63
68
  def initialize(**_)
64
69
  super
65
70
  end
@@ -91,7 +96,7 @@ module Aspera
91
96
  rescue StandardError => e
92
97
  nagios.add_critical('console api', e.to_s)
93
98
  end
94
- return nagios.result
99
+ Main.result_object_list(nagios.status_list)
95
100
  when :transfer
96
101
  command = options.get_next_command(%i[current smart])
97
102
  case command
@@ -113,8 +118,8 @@ module Aspera
113
118
  query = query_read_delete(default: {})
114
119
  if query['from'].nil? && query['to'].nil?
115
120
  time_now = Time.now
116
- query['from'] = Manager.time_to_string(time_now - DEFAULT_FILTER_AGE_SECONDS)
117
- query['to'] = Manager.time_to_string(time_now)
121
+ query['from'] = self.class.time_to_string(time_now - DEFAULT_FILTER_AGE_SECONDS)
122
+ query['to'] = self.class.time_to_string(time_now)
118
123
  end
119
124
  if (filter = query.delete('filter'))
120
125
  parse_extended_filter(filter, query)
@@ -1,6 +1,6 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require 'aspera/cli/plugin'
3
+ require 'aspera/cli/plugins/base'
4
4
  require 'aspera/cli/plugins/node'
5
5
  require 'aspera/api/cos_node'
6
6
  require 'aspera/assert'
@@ -8,14 +8,14 @@ require 'aspera/assert'
8
8
  module Aspera
9
9
  module Cli
10
10
  module Plugins
11
- class Cos < Cli::Plugin
11
+ class Cos < Base
12
12
  def initialize(**_)
13
13
  super
14
14
  options.declare(:bucket, 'Bucket name')
15
15
  options.declare(:endpoint, 'Storage endpoint (URL)')
16
16
  options.declare(:apikey, 'Storage API key')
17
17
  options.declare(:crn, 'Resource instance id (CRN)')
18
- options.declare(:service_credentials, 'IBM Cloud service credentials', types: Hash)
18
+ options.declare(:service_credentials, 'IBM Cloud service credentials', allowed: [Hash, NilClass])
19
19
  options.declare(:region, 'Storage region')
20
20
  options.declare(:identity, "Authentication URL (#{Api::CosNode::IBM_CLOUD_TOKEN_URL})", default: Api::CosNode::IBM_CLOUD_TOKEN_URL)
21
21
  options.parse_options!
@@ -0,0 +1,78 @@
1
+ # frozen_string_literal: true
2
+
3
+ require 'singleton'
4
+ require 'aspera/assert'
5
+ require 'aspera/cli/error'
6
+ require 'aspera/environment'
7
+
8
+ module Aspera
9
+ module Cli
10
+ # Instantiate plugin from well-known locations
11
+ module Plugins
12
+ class Factory
13
+ include Singleton
14
+
15
+ attr_reader :lookup_folders
16
+
17
+ def initialize
18
+ @lookup_folders = []
19
+ # information on plugins
20
+ @plugins = {}
21
+ end
22
+
23
+ # @return list of registered plugins
24
+ def plugin_list
25
+ @plugins.keys
26
+ end
27
+
28
+ # add a folder to the list of folders to look for plugins
29
+ def add_lookup_folder(folder)
30
+ @lookup_folders.unshift(folder)
31
+ end
32
+
33
+ # find plugins in defined paths
34
+ def add_plugins_from_lookup_folders
35
+ @lookup_folders.each do |folder|
36
+ next unless File.directory?(folder)
37
+ # TODO: add gem root to load path ? and require short folder ?
38
+ # $LOAD_PATH.push(folder) if i[:add_path]
39
+ Dir.entries(folder).each do |source|
40
+ next unless source.end_with?(Environment::RB_EXT)
41
+ path = File.join(folder, source)
42
+ plugin_symbol = File.basename(path, Environment::RB_EXT).to_sym
43
+ next if IGNORE_PLUGINS.include?(plugin_symbol)
44
+ req = path.sub(/#{Environment::RB_EXT}$/o, '')
45
+ Aspera.assert(!@plugins.key?(plugin_symbol), type: :warn){"Plugin already registered: #{plugin_symbol}"}
46
+ @plugins[plugin_symbol] = {source: path, require_stanza: req}
47
+ end
48
+ end
49
+ end
50
+
51
+ # @return path to source file of plugin
52
+ def plugin_source(plugin_name_sym)
53
+ Aspera.assert(@plugins.key?(plugin_name_sym), type: NoSuchElement){"plugin not found: #{plugin_name_sym}"}
54
+ @plugins[plugin_name_sym][:source]
55
+ end
56
+
57
+ # @return Class object for plugin
58
+ def plugin_class(plugin_name_sym)
59
+ Aspera.assert(@plugins.key?(plugin_name_sym), type: NoSuchElement){"plugin not found: #{plugin_name_sym}"}
60
+ require @plugins[plugin_name_sym][:require_stanza]
61
+ # Module.nesting[1] is Aspera::Cli::Plugins
62
+ return Object.const_get("#{Module.nesting[1]}::#{plugin_name_sym.to_s.snake_to_capital}")
63
+ end
64
+
65
+ # Create specified plugin
66
+ # @param plugin_name_sym [Symbol] name of plugin
67
+ # @param args [Hash] arguments to pass to plugin constructor
68
+ def create(plugin_name_sym, **args)
69
+ # TODO: check that ancestor is Plugin?
70
+ plugin_class(plugin_name_sym).new(**args)
71
+ end
72
+
73
+ IGNORE_PLUGINS = %i[factory base basic_auth oauth]
74
+ private_constant :IGNORE_PLUGINS
75
+ end
76
+ end
77
+ end
78
+ end
@@ -1,9 +1,8 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  # cspell:ignore passcode xrds workgroups dmembership wmembership
4
- require 'aspera/cli/basic_auth_plugin'
4
+ require 'aspera/cli/plugins/basic_auth'
5
5
  require 'aspera/cli/plugins/node'
6
- require 'aspera/cli/plugins/config'
7
6
  require 'aspera/cli/extended_value'
8
7
  require 'aspera/cli/special_values'
9
8
  require 'aspera/cli/transfer_agent'
@@ -17,12 +16,11 @@ require 'aspera/log'
17
16
  require 'aspera/assert'
18
17
  require 'xmlsimple'
19
18
  require 'json'
20
- require 'cgi'
21
19
 
22
20
  module Aspera
23
21
  module Cli
24
22
  module Plugins
25
- class Faspex < Cli::BasicAuthPlugin
23
+ class Faspex < BasicAuth
26
24
  # required hash key for source in config
27
25
  KEY_NODE = 'node' # value must be hash with url, username, password
28
26
  KEY_PATH = 'path' # value must be same sub-path as in Faspex's node
@@ -49,22 +47,23 @@ module Aspera
49
47
  urls.each do |base_url|
50
48
  next unless base_url.start_with?('https://')
51
49
  api = Rest.new(base_url: base_url, redirect_max: 1)
52
- result = api.call(
50
+ http = api.call(
53
51
  operation: 'POST',
54
52
  headers: {
55
53
  'Content-type' => Rest::MIME_TEXT,
56
54
  'Accept' => 'application/xrds+xml'
57
- }
55
+ },
56
+ ret: :resp
58
57
  )
59
58
  # 4.x
60
- next unless result[:http].body.start_with?('<?xml')
61
- res_s = XmlSimple.xml_in(result[:http].body, {'ForceArray' => false})
62
- Log.log.debug{"version: #{result[:http][HEADER_FASPEX_VERSION]}"}
59
+ next unless http.body.start_with?('<?xml')
60
+ res_s = XmlSimple.xml_in(http.body, {'ForceArray' => false})
61
+ Log.log.debug{"version: #{http[HEADER_FASPEX_VERSION]}"}
63
62
  version = res_s['XRD']['application']['version']
64
63
  # take redirect if any
65
64
  return {
66
65
  version: version,
67
- url: result[:http].uri.to_s
66
+ url: http.uri.to_s
68
67
  }
69
68
  rescue StandardError => e
70
69
  error = e
@@ -74,20 +73,6 @@ module Aspera
74
73
  return
75
74
  end
76
75
 
77
- # @param object [Plugin] An instance of this class
78
- # @return [Hash] :preset_value, :test_args
79
- def wizard(object:)
80
- options = object.options
81
- return {
82
- preset_value: {
83
- url: options.get_option(:url, mandatory: true),
84
- username: options.get_option(:username, mandatory: true),
85
- password: options.get_option(:password, mandatory: true)
86
- },
87
- test_args: 'me'
88
- }
89
- end
90
-
91
76
  # extract elements from faspex public link
92
77
  def get_link_data(public_url)
93
78
  public_uri = URI.parse(public_url)
@@ -122,16 +107,30 @@ module Aspera
122
107
  end
123
108
  end
124
109
 
110
+ # @param wizard [Wizard] The wizard object
111
+ # @param app_url [Wizard] The wizard object
112
+ # @return [Hash] :preset_value, :test_args
113
+ def wizard(wizard, app_url)
114
+ return {
115
+ preset_value: {
116
+ url: app_url,
117
+ username: options.get_option(:username, mandatory: true),
118
+ password: options.get_option(:password, mandatory: true)
119
+ },
120
+ test_args: 'me'
121
+ }
122
+ end
123
+
125
124
  def initialize(**_)
126
125
  super
127
126
  @api_v3 = nil
128
127
  @api_v4 = nil
129
128
  options.declare(:link, 'Public link for specific operation')
130
- options.declare(:delivery_info, 'Package delivery information', types: Hash)
129
+ options.declare(:delivery_info, 'Package delivery information', allowed: Hash)
131
130
  options.declare(:remote_source, 'Remote source for package send (id or %name:)')
132
131
  options.declare(:storage, 'Faspex local storage definition (for browsing source)')
133
132
  options.declare(:recipient, 'Use if recipient is a dropbox (with *)')
134
- options.declare(:box, 'Package box', values: ATOM_MAILBOXES, default: :inbox)
133
+ options.declare(:box, 'Package box', allowed: ATOM_MAILBOXES, default: :inbox)
135
134
  options.parse_options!
136
135
  end
137
136
 
@@ -186,8 +185,9 @@ module Aspera
186
185
  operation: 'GET',
187
186
  subpath: "#{mailbox}.atom",
188
187
  headers: {'Accept' => 'application/xml'},
189
- query: mailbox_query
190
- )[:http].body
188
+ query: mailbox_query,
189
+ ret: :resp
190
+ ).body
191
191
  box_data = XmlSimple.xml_in(atom_xml, {'ForceArray' => %w[entry field link to]})
192
192
  Log.dump(:box_data, box_data)
193
193
  items = box_data.key?('entry') ? box_data['entry'] : []
@@ -227,8 +227,7 @@ module Aspera
227
227
  # no next link
228
228
  break if link.nil?
229
229
  # replace parameters with the ones from next link
230
- params = CGI.parse(URI.parse(link['href']).query)
231
- mailbox_query = params.keys.each_with_object({}){ |i, m| m[i] = params[i].first}
230
+ mailbox_query = Rest.query_to_h(URI.parse(link['href']).query)
232
231
  Log.log.debug{"query: #{mailbox_query}"}
233
232
  break if !max_pages.nil? && (mailbox_query['page'].to_i > max_pages)
234
233
  end
@@ -254,8 +253,9 @@ module Aspera
254
253
  subpath: create_path,
255
254
  content_type: Rest::MIME_JSON,
256
255
  body: package_create_params,
257
- headers: {'Accept' => 'text/javascript'}
258
- )[:http].body
256
+ headers: {'Accept' => 'text/javascript'},
257
+ ret: :resp
258
+ ).body
259
259
  # get arguments of function call
260
260
  package_creation_data.delete!("\n") # one line
261
261
  package_creation_data.gsub!(/^[^"]+\("\{/, '{') # delete header
@@ -283,7 +283,7 @@ module Aspera
283
283
  rescue StandardError => e
284
284
  nagios.add_critical('faspex api', e.to_s)
285
285
  end
286
- return nagios.result
286
+ Main.result_object_list(nagios.status_list)
287
287
  when :package
288
288
  command_pkg = options.get_next_command(%i[send receive list show], aliases: {recv: :receive})
289
289
  case command_pkg
@@ -303,10 +303,11 @@ module Aspera
303
303
  delivery_info['sources'] ||= [{'paths' => []}]
304
304
  first_source = delivery_info['sources'].first
305
305
  first_source['paths'].concat(transfer.source_list)
306
- source_id = instance_identifier(as_option: :remote_source) do |field, value|
307
- Aspera.assert(field.eql?('name'), type: Cli::BadArgument){'only name as selector, or give id'}
306
+ source_id = options.get_option(:remote_source)
307
+ if source_id && (m = Base.percent_selector(source_id))
308
+ Aspera.assert(m[:field].eql?('name'), type: Cli::BadArgument){'only name as selector, or give id'}
308
309
  source_list = api_v3.read('source_shares')['items']
309
- self.class.get_source_id_by_name(value, source_list)
310
+ source_id = self.class.get_source_id_by_name(m[:value], source_list)
310
311
  end
311
312
  first_source['id'] = source_id.to_i unless source_id.nil?
312
313
  pkg_created = api_v3.create('send', package_create_params)
@@ -365,7 +366,7 @@ module Aspera
365
366
  when :inbox, :archive then'received'
366
367
  when :sent then 'sent'
367
368
  end
368
- entry_xml = api_v3.call(operation: 'GET', subpath: "#{endpoint}/#{delivery_id}", headers: {'Accept' => 'application/xml'})[:http].body
369
+ entry_xml = api_v3.call(operation: 'GET', subpath: "#{endpoint}/#{delivery_id}", headers: {'Accept' => 'application/xml'}, ret: :resp).body
369
370
  package_entry = XmlSimple.xml_in(entry_xml, {'ForceArray' => true})
370
371
  pkg_id_uri = [{id: delivery_id, uri: self.class.get_fasp_uri_from_entry(package_entry)}]
371
372
  end
@@ -376,17 +377,18 @@ module Aspera
376
377
  raise Cli::BadArgument, "Pub link is #{link_data[:subpath]}. Expecting #{PUB_LINK_EXTERNAL_MATCH}" if !link_data[:subpath].start_with?(PUB_LINK_EXTERNAL_MATCH)
377
378
  # NOTE: unauthenticated API (authorization is in url params)
378
379
  api_public_link = Rest.new(base_url: link_data[:base_url])
379
- package_creation_data = api_public_link.call(
380
+ pkg_xml = api_public_link.call(
380
381
  operation: 'GET',
381
382
  subpath: link_data[:subpath],
382
383
  headers: {'Accept' => 'application/xml'},
383
- query: {passcode: link_data[:query]['passcode']}
384
- )
385
- if !package_creation_data[:http].body.start_with?('<?xml ')
384
+ query: {passcode: link_data[:query]['passcode']},
385
+ ret: :resp
386
+ ).body
387
+ if !pkg_xml.start_with?('<?xml ')
386
388
  Environment.instance.open_uri(link_url)
387
389
  raise Cli::Error, 'Unexpected response: package not found ?'
388
390
  end
389
- package_entry = XmlSimple.xml_in(package_creation_data[:http].body, {'ForceArray' => false})
391
+ package_entry = XmlSimple.xml_in(pkg_xml, {'ForceArray' => false})
390
392
  Log.dump(:package_entry, package_entry)
391
393
  transfer_uri = self.class.get_fasp_uri_from_entry(package_entry)
392
394
  pkg_id_uri = [{id: package_entry['id'], uri: transfer_uri}]
@@ -415,8 +417,9 @@ module Aspera
415
417
  query: {'direction' => 'down'},
416
418
  content_type: Rest::MIME_TEXT,
417
419
  body: xml_payload,
418
- headers: {'Accept' => Rest::MIME_TEXT, 'Content-Type' => 'application/vnd.aspera.url-list+xml'}
419
- )[:http].body
420
+ headers: {'Accept' => Rest::MIME_TEXT, 'Content-Type' => 'application/vnd.aspera.url-list+xml'},
421
+ ret: :resp
422
+ ).body
420
423
  end
421
424
  transfer_spec['direction'] = Transfer::Spec::DIRECTION_RECEIVE
422
425
  statuses = transfer.start(transfer_spec)
@@ -458,7 +461,7 @@ module Aspera
458
461
  when :info
459
462
  return Main.result_single_object(source_info)
460
463
  when :node
461
- node_config = ExtendedValue.instance.evaluate(source_info[KEY_NODE])
464
+ node_config = ExtendedValue.instance.evaluate(source_info[KEY_NODE], context: 'faspex node')
462
465
  Log.log.debug{"node=#{node_config}"}
463
466
  Aspera.assert_type(node_config, Hash, type: Cli::Error){source_info[KEY_NODE]}
464
467
  api_node = Rest.new(
@@ -522,7 +525,7 @@ module Aspera
522
525
  end
523
526
  return Main.result_object_list(users)
524
527
  when :login_methods
525
- login_meths = api_v3.call(operation: 'GET', subpath: 'login/new', headers: {'Accept' => 'application/xrds+xml'})[:http].body
528
+ login_meths = api_v3.call(operation: 'GET', subpath: 'login/new', headers: {'Accept' => 'application/xrds+xml'}, ret: :resp).body
526
529
  login_methods = XmlSimple.xml_in(login_meths, {'ForceArray' => false})
527
530
  return Main.result_object_list(login_methods['XRD']['Service'])
528
531
  end