wetransfer 0.4.4 → 0.9.0.beta1

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 (53) hide show
  1. checksums.yaml +5 -5
  2. data/.rspec +1 -2
  3. data/.rubocop.yml +1 -1
  4. data/.travis.yml +3 -2
  5. data/Guardfile +11 -0
  6. data/README.md +82 -39
  7. data/V2_README.md +53 -0
  8. data/examples/create_collection.rb +13 -0
  9. data/examples/create_transfer.rb +1 -1
  10. data/lib/we_transfer_client/board_builder.rb +33 -0
  11. data/lib/we_transfer_client/boards.rb +74 -0
  12. data/lib/we_transfer_client/future_board.rb +32 -0
  13. data/lib/we_transfer_client/future_file.rb +28 -0
  14. data/lib/we_transfer_client/future_link.rb +28 -0
  15. data/lib/we_transfer_client/future_transfer.rb +11 -5
  16. data/lib/we_transfer_client/remote_board.rb +47 -0
  17. data/lib/we_transfer_client/remote_file.rb +55 -0
  18. data/lib/we_transfer_client/remote_link.rb +9 -0
  19. data/lib/we_transfer_client/remote_transfer.rb +24 -1
  20. data/lib/we_transfer_client/transfer_builder.rb +3 -10
  21. data/lib/we_transfer_client/transfers.rb +73 -0
  22. data/lib/we_transfer_client/version.rb +2 -2
  23. data/lib/we_transfer_client.rb +86 -120
  24. data/spec/board_integration_spec.rb +68 -0
  25. data/spec/features/add_items_to_board_spec.rb +55 -0
  26. data/spec/features/create_board_spec.rb +46 -0
  27. data/spec/features/get_board_spec.rb +34 -0
  28. data/spec/features/transfer_spec.rb +41 -0
  29. data/spec/fixtures/Japan-01.jpg +0 -0
  30. data/spec/fixtures/Japan-02.jpg +0 -0
  31. data/spec/spec_helper.rb +20 -0
  32. data/spec/transfer_integration_spec.rb +54 -0
  33. data/spec/we_transfer_client/board_builder_spec.rb +66 -0
  34. data/spec/we_transfer_client/boards_spec.rb +56 -0
  35. data/spec/we_transfer_client/future_board_spec.rb +98 -0
  36. data/spec/we_transfer_client/future_file_spec.rb +48 -0
  37. data/spec/we_transfer_client/future_link_spec.rb +44 -0
  38. data/spec/we_transfer_client/future_transfer_spec.rb +30 -13
  39. data/spec/we_transfer_client/remote_board_spec.rb +92 -0
  40. data/spec/we_transfer_client/remote_file_spec.rb +91 -0
  41. data/spec/we_transfer_client/remote_link_spec.rb +33 -0
  42. data/spec/we_transfer_client/remote_transfer_spec.rb +101 -0
  43. data/spec/we_transfer_client/transfer_builder_spec.rb +48 -51
  44. data/spec/we_transfer_client/transfers_spec.rb +45 -0
  45. data/spec/we_transfer_client_spec.rb +51 -3
  46. data/wetransfer.gemspec +11 -5
  47. metadata +67 -27
  48. data/lib/we_transfer_client/future_file_item.rb +0 -16
  49. data/lib/we_transfer_client/future_web_item.rb +0 -18
  50. data/lib/we_transfer_client/remote_item.rb +0 -2
  51. data/spec/integration_spec.rb +0 -160
  52. data/spec/we_transfer_client/future_file_item_spec.rb +0 -39
  53. data/spec/we_transfer_client/future_web_item_spec.rb +0 -39
@@ -0,0 +1,28 @@
1
+ class FutureFile
2
+ attr_reader :name, :io
3
+
4
+ def initialize(name:, io:)
5
+ @name = name
6
+ @io = io
7
+ end
8
+
9
+ def to_request_params
10
+ {
11
+ name: @name,
12
+ size: @io.size,
13
+ }
14
+ end
15
+
16
+ def add_to_board(client:, remote_board:)
17
+ client.authorize_if_no_bearer_token!
18
+ response = client.faraday.post(
19
+ "/v2/boards/#{remote_board.id}/files",
20
+ # this needs to be a array with hashes => [{name, filesize}]
21
+ JSON.pretty_generate([to_request_params]),
22
+ client.auth_headers.merge('Content-Type' => 'application/json')
23
+ )
24
+ client.ensure_ok_status!(response)
25
+ file_item = JSON.parse(response.body, symbolize_names: true).first
26
+ remote_board.items << RemoteFile.new(file_item)
27
+ end
28
+ end
@@ -0,0 +1,28 @@
1
+ class FutureLink
2
+ attr_reader :url, :title
3
+
4
+ def initialize(url:, title: url)
5
+ @url = url
6
+ @title = title
7
+ end
8
+
9
+ def to_request_params
10
+ {
11
+ url: url,
12
+ title: title,
13
+ }
14
+ end
15
+
16
+ def add_to_board(client:, remote_board:)
17
+ client.authorize_if_no_bearer_token!
18
+ response = client.faraday.post(
19
+ "/v2/boards/#{remote_board.id}/links",
20
+ # this needs to be a array with hashes => [{name, filesize}]
21
+ JSON.pretty_generate([to_request_params]),
22
+ client.auth_headers.merge('Content-Type' => 'application/json')
23
+ )
24
+ client.ensure_ok_status!(response)
25
+ file_item = JSON.parse(response.body, symbolize_names: true).first
26
+ remote_board.items << RemoteLink.new(file_item)
27
+ end
28
+ end
@@ -1,9 +1,15 @@
1
- class FutureTransfer < Ks.strict(:name, :description, :items)
2
- def to_create_transfer_params
1
+ class FutureTransfer
2
+ attr_accessor :message, :files
3
+
4
+ def initialize(message:, files: [])
5
+ @message = message
6
+ @files = files
7
+ end
8
+
9
+ def to_request_params
3
10
  {
4
- name: name,
5
- description: description,
6
- items: items.map(&:to_item_request_params),
11
+ message: message,
12
+ files: files.map(&:to_request_params),
7
13
  }
8
14
  end
9
15
  end
@@ -0,0 +1,47 @@
1
+ class RemoteBoard
2
+ ItemTypeError = Class.new(NameError)
3
+
4
+ attr_reader :id, :items, :url, :state
5
+
6
+ CHUNK_SIZE = 6 * 1024 * 1024
7
+
8
+ def initialize(id:, state:, url:, name:, description: '', items: [])
9
+ @id = id
10
+ @state = state
11
+ @url = url
12
+ @name = name
13
+ @description = description
14
+ @items = to_instances(items: items)
15
+ end
16
+
17
+ def prepare_file_upload(client:, file:, part_number:)
18
+ url = file.request_board_upload_url(client: client, board_id: @id, part_number: part_number)
19
+ [url, CHUNK_SIZE]
20
+ end
21
+
22
+ def prepare_file_completion(client:, file:)
23
+ file.complete_board_file(client: client, board_id: @id)
24
+ end
25
+
26
+ def files
27
+ @items.select { |item| item.class == RemoteFile }
28
+ end
29
+
30
+ def links
31
+ @items.select { |item| item.class == RemoteLink }
32
+ end
33
+
34
+ private
35
+
36
+ def to_instances(items:)
37
+ items.map do |item|
38
+ begin
39
+ remote_class = "Remote#{item[:type].capitalize}"
40
+ Module.const_get(remote_class)
41
+ .new(item)
42
+ rescue NameError
43
+ raise ItemTypeError, "Cannot instantiate item with type '#{item[:type]}' and id '#{item[:id]}'"
44
+ end
45
+ end
46
+ end
47
+ end
@@ -0,0 +1,55 @@
1
+ class RemoteFile
2
+ attr_reader :multipart, :name, :id, :url, :type
3
+
4
+ def initialize(id:, name:, size:, url: nil, type: 'file', multipart:)
5
+ @id = id
6
+ @name = name
7
+ @size = size
8
+ @url = url
9
+ @type = type
10
+ @size = size
11
+ multi = Struct.new(*multipart.keys)
12
+ @multipart = multi.new(*multipart.values)
13
+ end
14
+
15
+ def request_transfer_upload_url(client:, transfer_id:, part_number:)
16
+ response = client.faraday.get(
17
+ "/v2/transfers/#{transfer_id}/files/#{@id}/upload-url/#{part_number}",
18
+ {},
19
+ client.auth_headers.merge('Content-Type' => 'application/json')
20
+ )
21
+ client.ensure_ok_status!(response)
22
+ JSON.parse(response.body, symbolize_names: true).fetch(:url)
23
+ end
24
+
25
+ def request_board_upload_url(client:, board_id:, part_number:)
26
+ response = client.faraday.get(
27
+ "/v2/boards/#{board_id}/files/#{@id}/upload-url/#{part_number}/#{@multipart.id}",
28
+ {},
29
+ client.auth_headers.merge('Content-Type' => 'application/json')
30
+ )
31
+ client.ensure_ok_status!(response)
32
+ JSON.parse(response.body, symbolize_names: true).fetch(:url)
33
+ end
34
+
35
+ def complete_transfer_file(client:, transfer_id:)
36
+ body = {part_numbers: @multipart.part_numbers}
37
+ response = client.faraday.put(
38
+ "/v2/transfers/#{transfer_id}/files/#{@id}/upload-complete",
39
+ JSON.pretty_generate(body),
40
+ client.auth_headers.merge('Content-Type' => 'application/json')
41
+ )
42
+ client.ensure_ok_status!(response)
43
+ JSON.parse(response.body, symbolize_names: true)
44
+ end
45
+
46
+ def complete_board_file(client:, board_id:)
47
+ response = client.faraday.put(
48
+ "/v2/boards/#{board_id}/files/#{@id}/upload-complete",
49
+ '{}',
50
+ client.auth_headers.merge('Content-Type' => 'application/json')
51
+ )
52
+ client.ensure_ok_status!(response)
53
+ JSON.parse(response.body, symbolize_names: true)
54
+ end
55
+ end
@@ -0,0 +1,9 @@
1
+ class RemoteLink
2
+ attr_reader :type
3
+ def initialize(id:, url:, type:, meta:)
4
+ @id = id
5
+ @url = url
6
+ @title = meta.fetch(:title)
7
+ @type = type
8
+ end
9
+ end
@@ -1,2 +1,25 @@
1
- class RemoteTransfer < Ks.strict(:id, :version_identifier, :state, :shortened_url, :name, :description, :size, :items)
1
+ class RemoteTransfer
2
+ attr_reader :files, :url, :state, :id
3
+
4
+ def initialize(id:, state:, url:, message:, files: [])
5
+ @id = id
6
+ @state = state
7
+ @message = message
8
+ @url = url
9
+ @files = files_to_class(files)
10
+ end
11
+
12
+ def prepare_file_upload(client:, file:, part_number:)
13
+ url = file.request_transfer_upload_url(client: client, transfer_id: @id, part_number: part_number)
14
+ chunk_size = file.multipart.chunk_size
15
+ [url, chunk_size]
16
+ end
17
+
18
+ def prepare_file_completion(client:, file:)
19
+ file.complete_transfer_file(client: client, transfer_id: @id)
20
+ end
21
+
22
+ def files_to_class(files)
23
+ files.map { |x| RemoteFile.new(x) }
24
+ end
2
25
  end
@@ -1,27 +1,20 @@
1
1
  class TransferBuilder
2
- attr_reader :items
2
+ attr_reader :files
3
3
  class TransferIOError < StandardError; end
4
4
 
5
5
  def initialize
6
- @items = []
6
+ @files = []
7
7
  end
8
8
 
9
9
  def add_file(name:, io:)
10
10
  ensure_io_compliant!(io)
11
- @items << FutureFileItem.new(name: name, io: io)
12
- true
11
+ @files << FutureFile.new(name: name, io: io)
13
12
  end
14
13
 
15
14
  def add_file_at(path:)
16
15
  add_file(name: File.basename(path), io: File.open(path, 'rb'))
17
16
  end
18
17
 
19
- def add_web_url(url:, title: nil)
20
- title ||= url
21
- @items << FutureWebItem.new(url: url, title: title)
22
- true
23
- end
24
-
25
18
  def ensure_io_compliant!(io)
26
19
  io.seek(0)
27
20
  io.read(1) # Will cause things like Errno::EACCESS to happen early, before the upload begins
@@ -0,0 +1,73 @@
1
+ module WeTransfer
2
+ class Client
3
+ module Transfers
4
+ def create_transfer_and_upload_files(message:, &block)
5
+ future_transfer = create_future_transfer(message: message, &block)
6
+ remote_transfer = create_remote_transfer(future_transfer)
7
+ remote_transfer.files.each do |file|
8
+ check_for_file_duplicates(future_transfer.files, file)
9
+ local_file = future_transfer.files.select { |x| x.name == file.name }.first
10
+ upload_file(object: remote_transfer, file: file, io: local_file.io)
11
+ complete_file!(object: remote_transfer, file: file)
12
+ end
13
+ complete_transfer(transfer: remote_transfer)
14
+ end
15
+
16
+ def get_transfer(transfer_id:)
17
+ request_transfer(transfer_id)
18
+ end
19
+
20
+ private
21
+
22
+ def create_transfer(message:, &block)
23
+ transfer = create_future_transfer(message: message, &block)
24
+ create_remote_transfer(transfer)
25
+ end
26
+
27
+ def complete_transfer(transfer:)
28
+ complete_transfer_call(transfer)
29
+ end
30
+
31
+ def create_future_transfer(message:, future_transfer_class: FutureTransfer, transfer_builder_class: TransferBuilder)
32
+ builder = transfer_builder_class.new
33
+ yield(builder)
34
+ future_transfer_class.new(message: message, files: builder.files)
35
+ rescue LocalJumpError
36
+ raise ArgumentError, 'No files were added to transfer'
37
+ end
38
+
39
+ def create_remote_transfer(xfer)
40
+ authorize_if_no_bearer_token!
41
+ response = faraday.post(
42
+ '/v2/transfers',
43
+ JSON.pretty_generate(xfer.to_request_params),
44
+ auth_headers.merge('Content-Type' => 'application/json')
45
+ )
46
+ ensure_ok_status!(response)
47
+ RemoteTransfer.new(JSON.parse(response.body, symbolize_names: true))
48
+ end
49
+
50
+ def complete_transfer_call(object)
51
+ authorize_if_no_bearer_token!
52
+ response = faraday.put(
53
+ "/v2/transfers/#{object.id}/finalize",
54
+ '',
55
+ auth_headers.merge('Content-Type' => 'application/json')
56
+ )
57
+ ensure_ok_status!(response)
58
+ RemoteTransfer.new(JSON.parse(response.body, symbolize_names: true))
59
+ end
60
+
61
+ def request_transfer(transfer_id)
62
+ authorize_if_no_bearer_token!
63
+ response = faraday.get(
64
+ "/v2/transfers/#{transfer_id}",
65
+ {},
66
+ auth_headers.merge('Content-Type' => 'application/json')
67
+ )
68
+ ensure_ok_status!(response)
69
+ RemoteTransfer.new(JSON.parse(response.body, symbolize_names: true))
70
+ end
71
+ end
72
+ end
73
+ end
@@ -1,3 +1,3 @@
1
- class WeTransferClient
2
- VERSION = '0.4.4'
1
+ module WeTransfer
2
+ VERSION = '0.9.0.beta1'
3
3
  end
@@ -1,142 +1,108 @@
1
1
  require 'faraday'
2
2
  require 'logger'
3
- require 'ks'
4
- require 'securerandom'
5
3
  require 'json'
6
4
 
7
- class WeTransferClient
8
- require_relative 'we_transfer_client/version'
9
- require_relative 'we_transfer_client/future_file_item'
10
- require_relative 'we_transfer_client/future_web_item'
11
- require_relative 'we_transfer_client/future_transfer'
12
- require_relative 'we_transfer_client/transfer_builder'
13
- require_relative 'we_transfer_client/remote_transfer'
14
- require_relative 'we_transfer_client/remote_item'
15
-
16
- class Error < StandardError
17
- end
18
-
19
- NULL_LOGGER = Logger.new(nil)
20
- MAGIC_PART_SIZE = 6 * 1024 * 1024
21
-
22
- def initialize(api_key:, logger: NULL_LOGGER)
23
- @api_url_base = 'https://dev.wetransfer.com'
24
- @api_key = api_key.to_str
25
- @bearer_token = nil
26
- @logger = logger
27
- end
28
-
29
- def create_transfer(name:, description:)
30
- builder = TransferBuilder.new
31
- yield(builder)
32
- future_transfer = FutureTransfer.new(name: name, description: description, items: builder.items)
33
- create_and_upload(future_transfer)
34
- end
35
-
36
- def create_empty_transfer(name:, description:)
37
- future_transfer = FutureTransfer.new(name: name, description: description, items: [])
38
- create_and_upload(future_transfer)
39
- end
40
-
41
- def create_and_upload(xfer)
42
- authorize_if_no_bearer_token!
43
- response = faraday.post(
44
- '/v1/transfers',
45
- JSON.pretty_generate(xfer.to_create_transfer_params),
46
- auth_headers.merge('Content-Type' => 'application/json')
47
- )
48
- ensure_ok_status!(response)
49
- create_transfer_response = JSON.parse(response.body, symbolize_names: true)
50
-
51
- remote_transfer = hash_to_struct(create_transfer_response, RemoteTransfer)
52
- remote_transfer.items = remote_transfer.items.map do |remote_item_hash|
53
- hash_to_struct(remote_item_hash, RemoteItem)
5
+ require_relative 'we_transfer_client/version'
6
+ require_relative 'we_transfer_client/transfer_builder'
7
+ require_relative 'we_transfer_client/board_builder'
8
+ require_relative 'we_transfer_client/future_file'
9
+ require_relative 'we_transfer_client/future_link'
10
+ require_relative 'we_transfer_client/future_transfer'
11
+ require_relative 'we_transfer_client/future_board'
12
+ require_relative 'we_transfer_client/remote_transfer'
13
+ require_relative 'we_transfer_client/remote_board'
14
+ require_relative 'we_transfer_client/remote_link'
15
+ require_relative 'we_transfer_client/remote_file'
16
+ require_relative 'we_transfer_client/transfers'
17
+ require_relative 'we_transfer_client/boards'
18
+
19
+ module WeTransfer
20
+ class Client
21
+ include WeTransfer::Client::Transfers
22
+ include WeTransfer::Client::Boards
23
+
24
+ class Error < StandardError
54
25
  end
55
26
 
56
- item_id_map = Hash[xfer.items.map(&:local_identifier).zip(xfer.items)]
57
-
58
- create_transfer_response.fetch(:items).each do |remote_item|
59
- local_item = item_id_map.fetch(remote_item.fetch(:local_identifier))
60
- next unless local_item.is_a?(FutureFileItem)
61
- remote_item_id = remote_item.fetch(:id)
27
+ NULL_LOGGER = Logger.new(nil)
62
28
 
63
- put_io_in_parts(
64
- remote_item_id,
65
- remote_item.fetch(:meta).fetch(:multipart_parts),
66
- remote_item.fetch(:meta).fetch(:multipart_upload_id),
67
- local_item.io
68
- )
29
+ def initialize(api_key:, logger: NULL_LOGGER)
30
+ @api_url_base = 'https://dev.wetransfer.com'
31
+ @api_key = api_key.to_str
32
+ @bearer_token = nil
33
+ @logger = logger
34
+ end
69
35
 
70
- complete_response = faraday.post(
71
- "/v1/files/#{remote_item_id}/uploads/complete",
72
- '{}',
73
- auth_headers.merge('Content-Type' => 'application/json')
74
- )
75
- ensure_ok_status!(complete_response)
36
+ def upload_file(object:, file:, io:)
37
+ put_io_in_parts(object: object, file: file, io: io)
76
38
  end
77
- remote_transfer
78
- end
79
39
 
80
- def hash_to_struct(hash, struct_class)
81
- members = struct_class.members
82
- struct_attrs = Hash[members.zip(hash.values_at(*members))]
83
- struct_class.new(**struct_attrs)
84
- end
40
+ def complete_file!(object:, file:)
41
+ object.prepare_file_completion(client: self, file: file)
42
+ end
85
43
 
86
- def put_io_in_parts(item_id, n_parts, multipart_id, io)
87
- chunk_size = MAGIC_PART_SIZE
88
- (1..n_parts).each do |part_n_one_based|
89
- response = faraday.get("/v1/files/#{item_id}/uploads/#{part_n_one_based}/#{multipart_id}", {}, auth_headers)
90
- ensure_ok_status!(response)
91
- response = JSON.parse(response.body, symbolize_names: true)
44
+ def check_for_file_duplicates(files, new_file)
45
+ if files.select { |file| file.name == new_file.name }.size != 1
46
+ raise ArgumentError, 'Duplicate file entry'
47
+ end
48
+ end
92
49
 
93
- upload_url = response.fetch(:upload_url)
94
- part_io = StringIO.new(io.read(chunk_size)) # needs a lens
95
- part_io.rewind
96
- response = faraday.put(upload_url, part_io, 'Content-Type' => 'binary/octet-stream', 'Content-Length' => part_io.size.to_s)
97
- ensure_ok_status!(response)
50
+ def put_io_in_parts(object:, file:, io:)
51
+ (1..file.multipart.part_numbers).each do |part_n_one_based|
52
+ upload_url, chunk_size = object.prepare_file_upload(client: self, file: file, part_number: part_n_one_based)
53
+ part_io = StringIO.new(io.read(chunk_size))
54
+ part_io.rewind
55
+ response = faraday.put(
56
+ upload_url,
57
+ part_io,
58
+ 'Content-Type' => 'binary/octet-stream',
59
+ 'Content-Length' => part_io.size.to_s
60
+ )
61
+ ensure_ok_status!(response)
62
+ end
63
+ {success: true, message: 'File Uploaded'}
98
64
  end
99
- end
100
65
 
101
- def faraday
102
- Faraday.new(@api_url_base) do |c|
103
- c.response :logger, @logger
104
- c.adapter Faraday.default_adapter
105
- c.headers = { 'User-Agent' => "WetransferRubySdk/#{WeTransferClient::VERSION} Ruby #{RUBY_VERSION}"}
66
+ def faraday
67
+ Faraday.new(@api_url_base) do |c|
68
+ c.response :logger, @logger
69
+ c.adapter Faraday.default_adapter
70
+ c.headers = { 'User-Agent' => "WetransferRubySdk/#{WeTransfer::VERSION} Ruby #{RUBY_VERSION}"}
71
+ end
106
72
  end
107
- end
108
73
 
109
- def authorize_if_no_bearer_token!
110
- return if @bearer_token
111
- response = faraday.post('/v1/authorize', '{}', 'Content-Type' => 'application/json', 'X-API-Key' => @api_key)
112
- ensure_ok_status!(response)
113
- @bearer_token = JSON.parse(response.body, symbolize_names: true)[:token]
114
- if @bearer_token.nil? || @bearer_token.empty?
115
- raise Error, "The authorization call returned #{response.body} and no usable :token key could be found there"
74
+ def authorize_if_no_bearer_token!
75
+ return if @bearer_token
76
+ response = faraday.post('/v2/authorize', '{}', 'Content-Type' => 'application/json', 'X-API-Key' => @api_key)
77
+ ensure_ok_status!(response)
78
+ @bearer_token = JSON.parse(response.body, symbolize_names: true)[:token]
79
+ if @bearer_token.nil? || @bearer_token.empty?
80
+ raise Error, "The authorization call returned #{response.body} and no usable :token key could be found there"
81
+ end
116
82
  end
117
- end
118
83
 
119
- def auth_headers
120
- raise 'No bearer token retrieved yet' unless @bearer_token
121
- {
122
- 'X-API-Key' => @api_key,
123
- 'Authorization' => ('Bearer %s' % @bearer_token),
124
- }
125
- end
84
+ def auth_headers
85
+ raise 'No bearer token retrieved yet' unless @bearer_token
86
+ {
87
+ 'X-API-Key' => @api_key,
88
+ 'Authorization' => ('Bearer %s' % @bearer_token),
89
+ }
90
+ end
126
91
 
127
- def ensure_ok_status!(response)
128
- case response.status
129
- when 200..299
130
- nil
131
- when 400..499
132
- @logger.error { response.body }
133
- raise Error, "Response had a #{response.status} code, the server will not accept this request even if retried"
134
- when 500..504
135
- @logger.error { response.body }
136
- raise Error, "Response had a #{response.status} code, we could retry"
137
- else
138
- @logger.error { response.body }
139
- raise Error, "Response had a #{response.status} code, no idea what to do with that"
92
+ def ensure_ok_status!(response)
93
+ case response.status
94
+ when 200..299
95
+ true
96
+ when 400..499
97
+ @logger.error response
98
+ raise Error, "Response had a #{response.status} code, the server will not accept this request even if retried"
99
+ when 500..504
100
+ @logger.error response
101
+ raise Error, "Response had a #{response.status} code, we could retry"
102
+ else
103
+ @logger.error response
104
+ raise Error, "Response had a #{response.status} code, no idea what to do with that"
105
+ end
140
106
  end
141
107
  end
142
108
  end