azure-storage-common2 2.0.6 → 2.0.9

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 (57) hide show
  1. checksums.yaml +4 -4
  2. data/lib/azure/core/auth/authorizer.rb +36 -0
  3. data/lib/azure/core/auth/shared_key.rb +125 -0
  4. data/lib/azure/core/auth/shared_key_lite.rb +48 -0
  5. data/lib/azure/core/auth/signer.rb +51 -0
  6. data/lib/azure/core/default.rb +23 -0
  7. data/lib/azure/core/error.rb +21 -0
  8. data/lib/azure/core/filtered_service.rb +45 -0
  9. data/lib/azure/core/http/debug_filter.rb +36 -0
  10. data/lib/azure/core/http/http_error.rb +135 -0
  11. data/lib/azure/core/http/http_filter.rb +53 -0
  12. data/lib/azure/core/http/http_request.rb +195 -0
  13. data/lib/azure/core/http/http_response.rb +102 -0
  14. data/lib/azure/core/http/retry_policy.rb +84 -0
  15. data/lib/azure/core/http/signer_filter.rb +33 -0
  16. data/lib/azure/core/service.rb +46 -0
  17. data/lib/azure/core/signed_service.rb +45 -0
  18. data/lib/azure/core/utility.rb +244 -0
  19. data/lib/azure/core/version.rb +33 -0
  20. data/lib/azure/storage/common/autoload.rb +62 -0
  21. data/lib/azure/storage/common/client.rb +162 -0
  22. data/lib/azure/storage/common/client_options.rb +363 -0
  23. data/lib/azure/storage/common/client_options_error.rb +41 -0
  24. data/lib/azure/storage/common/configurable.rb +212 -0
  25. data/lib/azure/storage/common/core/auth/anonymous_signer.rb +43 -0
  26. data/lib/azure/storage/common/core/auth/shared_access_signature.rb +30 -0
  27. data/lib/azure/storage/common/core/auth/shared_access_signature_generator.rb +399 -0
  28. data/lib/azure/storage/common/core/auth/shared_access_signature_signer.rb +57 -0
  29. data/lib/azure/storage/common/core/auth/shared_key.rb +60 -0
  30. data/lib/azure/storage/common/core/auth/token_signer.rb +43 -0
  31. data/lib/azure/storage/common/core/autoload.rb +53 -0
  32. data/lib/azure/storage/common/core/error.rb +43 -0
  33. data/lib/azure/storage/common/core/filter/exponential_retry_filter.rb +64 -0
  34. data/lib/azure/storage/common/core/filter/linear_retry_filter.rb +55 -0
  35. data/lib/azure/storage/common/core/filter/retry_filter.rb +300 -0
  36. data/lib/azure/storage/common/core/http_client.rb +82 -0
  37. data/lib/azure/storage/common/core/sr.rb +85 -0
  38. data/lib/azure/storage/common/core/token_credential.rb +64 -0
  39. data/lib/azure/storage/common/core/utility.rb +261 -0
  40. data/lib/azure/storage/common/core.rb +35 -0
  41. data/lib/azure/storage/common/default.rb +868 -0
  42. data/lib/azure/storage/common/service/access_policy.rb +37 -0
  43. data/lib/azure/storage/common/service/cors.rb +38 -0
  44. data/lib/azure/storage/common/service/cors_rule.rb +48 -0
  45. data/lib/azure/storage/common/service/enumeration_results.rb +32 -0
  46. data/lib/azure/storage/common/service/geo_replication.rb +40 -0
  47. data/lib/azure/storage/common/service/logging.rb +47 -0
  48. data/lib/azure/storage/common/service/metrics.rb +45 -0
  49. data/lib/azure/storage/common/service/retention_policy.rb +37 -0
  50. data/lib/azure/storage/common/service/serialization.rb +335 -0
  51. data/lib/azure/storage/common/service/signed_identifier.rb +40 -0
  52. data/lib/azure/storage/common/service/storage_service.rb +322 -0
  53. data/lib/azure/storage/common/service/storage_service_properties.rb +48 -0
  54. data/lib/azure/storage/common/service/storage_service_stats.rb +39 -0
  55. data/lib/azure/storage/common/service/user_delegation_key.rb +50 -0
  56. data/lib/azure/storage/common/version.rb +49 -0
  57. metadata +57 -2
@@ -0,0 +1,43 @@
1
+ # frozen_string_literal: true
2
+
3
+ #-------------------------------------------------------------------------
4
+ # # Copyright (c) Microsoft and contributors. All rights reserved.
5
+ #
6
+ # The MIT License(MIT)
7
+
8
+ # Permission is hereby granted, free of charge, to any person obtaining a copy
9
+ # of this software and associated documentation files(the "Software"), to deal
10
+ # in the Software without restriction, including without limitation the rights
11
+ # to use, copy, modify, merge, publish, distribute, sublicense, and / or sell
12
+ # copies of the Software, and to permit persons to whom the Software is
13
+ # furnished to do so, subject to the following conditions :
14
+
15
+ # The above copyright notice and this permission notice shall be included in
16
+ # all copies or substantial portions of the Software.
17
+
18
+ # THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
19
+ # IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
20
+ # FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.IN NO EVENT SHALL THE
21
+ # AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
22
+ # LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
23
+ # OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
24
+ # THE SOFTWARE.
25
+ #--------------------------------------------------------------------------
26
+ require "azure/core"
27
+
28
+ module Azure::Storage::Common::Core
29
+ # Superclass for errors generated from this library, so people can
30
+ # just rescue this for generic error handling
31
+ class StorageError < StandardError
32
+ # attr_reader :description
33
+ # attr_reader :status_code
34
+ # attr_reader :type
35
+
36
+ # def initialize(description, type, status)
37
+ # @type = type
38
+ # @status_code = status
39
+ # @description = description
40
+ # super("#{type} (#{status_code}): #{description}")
41
+ # end
42
+ end
43
+ end
@@ -0,0 +1,64 @@
1
+ # frozen_string_literal: true
2
+
3
+ #-------------------------------------------------------------------------
4
+ # # Copyright (c) Microsoft and contributors. All rights reserved.
5
+ #
6
+ # The MIT License(MIT)
7
+
8
+ # Permission is hereby granted, free of charge, to any person obtaining a copy
9
+ # of this software and associated documentation files(the "Software"), to deal
10
+ # in the Software without restriction, including without limitation the rights
11
+ # to use, copy, modify, merge, publish, distribute, sublicense, and / or sell
12
+ # copies of the Software, and to permit persons to whom the Software is
13
+ # furnished to do so, subject to the following conditions :
14
+
15
+ # The above copyright notice and this permission notice shall be included in
16
+ # all copies or substantial portions of the Software.
17
+
18
+ # THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
19
+ # IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
20
+ # FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.IN NO EVENT SHALL THE
21
+ # AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
22
+ # LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
23
+ # OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
24
+ # THE SOFTWARE.
25
+ #--------------------------------------------------------------------------
26
+ require "azure/core"
27
+ require "azure/core/http/retry_policy"
28
+
29
+ module Azure::Storage::Common::Core::Filter
30
+ class ExponentialRetryPolicyFilter < RetryPolicyFilter
31
+ def initialize(retry_count = nil, min_retry_interval = nil, max_retry_interval = nil)
32
+ @retry_count = retry_count || ExponentialRetryPolicyFilter::DEFAULT_RETRY_COUNT
33
+ @min_retry_interval = min_retry_interval || ExponentialRetryPolicyFilter::DEFAULT_MIN_RETRY_INTERVAL
34
+ @max_retry_interval = max_retry_interval || ExponentialRetryPolicyFilter::DEFAULT_MAX_RETRY_INTERVAL
35
+
36
+ super @retry_count, @min_retry_interval
37
+ end
38
+
39
+ attr_reader :min_retry_interval,
40
+ :max_retry_interval
41
+
42
+ DEFAULT_RETRY_COUNT = 3
43
+ DEFAULT_MIN_RETRY_INTERVAL = 10
44
+ DEFAULT_MAX_RETRY_INTERVAL = 90
45
+
46
+ # Overrides the base class implementation of call to determine
47
+ # how the HTTP request should continue retrying
48
+ #
49
+ # retry_data - Hash. Stores stateful retry data
50
+ #
51
+ # The retry_data is a Hash which can be used to store
52
+ # stateful data about the request execution context (such as an
53
+ # incrementing counter, timestamp, etc). The retry_data object
54
+ # will be the same instance throughout the lifetime of the request
55
+ def apply_retry_policy(retry_data)
56
+ # Adjust retry count
57
+ retry_data[:count] = retry_data[:count] === nil ? 1 : retry_data[:count] + 1
58
+
59
+ # Adjust retry interval
60
+ increment_delta = (@max_retry_interval - @min_retry_interval).fdiv(2**(@retry_count - 1)) * (2**(retry_data[:count] - 1));
61
+ retry_data[:interval] = retry_data[:interval] === nil ? @min_retry_interval : [@min_retry_interval + increment_delta, @max_retry_interval].min;
62
+ end
63
+ end
64
+ end
@@ -0,0 +1,55 @@
1
+ # frozen_string_literal: true
2
+
3
+ #-------------------------------------------------------------------------
4
+ # # Copyright (c) Microsoft and contributors. All rights reserved.
5
+ #
6
+ # The MIT License(MIT)
7
+
8
+ # Permission is hereby granted, free of charge, to any person obtaining a copy
9
+ # of this software and associated documentation files(the "Software"), to deal
10
+ # in the Software without restriction, including without limitation the rights
11
+ # to use, copy, modify, merge, publish, distribute, sublicense, and / or sell
12
+ # copies of the Software, and to permit persons to whom the Software is
13
+ # furnished to do so, subject to the following conditions :
14
+
15
+ # The above copyright notice and this permission notice shall be included in
16
+ # all copies or substantial portions of the Software.
17
+
18
+ # THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
19
+ # IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
20
+ # FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.IN NO EVENT SHALL THE
21
+ # AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
22
+ # LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
23
+ # OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
24
+ # THE SOFTWARE.
25
+ #--------------------------------------------------------------------------
26
+ require "azure/core"
27
+ require "azure/core/http/retry_policy"
28
+
29
+ module Azure::Storage::Common::Core::Filter
30
+ class LinearRetryPolicyFilter < RetryPolicyFilter
31
+ def initialize(retry_count = nil, retry_interval = nil)
32
+ @retry_count = retry_count || LinearRetryPolicyFilter::DEFAULT_RETRY_COUNT
33
+ @retry_interval = retry_interval || LinearRetryPolicyFilter::DEFAULT_RETRY_INTERVAL
34
+
35
+ super @retry_count, @retry_interval
36
+ end
37
+
38
+ DEFAULT_RETRY_COUNT = 3
39
+ DEFAULT_RETRY_INTERVAL = 30
40
+
41
+ # Overrides the base class implementation of call to determine
42
+ # how the HTTP request should continue retrying
43
+ #
44
+ # retry_data - Hash. Stores stateful retry data
45
+ #
46
+ # The retry_data is a Hash which can be used to store
47
+ # stateful data about the request execution context (such as an
48
+ # incrementing counter, timestamp, etc). The retry_data object
49
+ # will be the same instance throughout the lifetime of the request
50
+ def apply_retry_policy(retry_data)
51
+ retry_data[:count] = retry_data[:count] == nil ? 1 : retry_data[:count] + 1
52
+ retry_data[:interval] = @retry_interval
53
+ end
54
+ end
55
+ end
@@ -0,0 +1,300 @@
1
+ # frozen_string_literal: true
2
+
3
+ #-------------------------------------------------------------------------
4
+ # # Copyright (c) Microsoft and contributors. All rights reserved.
5
+ #
6
+ # The MIT License(MIT)
7
+
8
+ # Permission is hereby granted, free of charge, to any person obtaining a copy
9
+ # of this software and associated documentation files(the "Software"), to deal
10
+ # in the Software without restriction, including without limitation the rights
11
+ # to use, copy, modify, merge, publish, distribute, sublicense, and / or sell
12
+ # copies of the Software, and to permit persons to whom the Software is
13
+ # furnished to do so, subject to the following conditions :
14
+
15
+ # The above copyright notice and this permission notice shall be included in
16
+ # all copies or substantial portions of the Software.
17
+
18
+ # THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
19
+ # IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
20
+ # FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.IN NO EVENT SHALL THE
21
+ # AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
22
+ # LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
23
+ # OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
24
+ # THE SOFTWARE.
25
+ #--------------------------------------------------------------------------
26
+ require "azure/core"
27
+ require "azure/core/http/retry_policy"
28
+
29
+ module Azure::Storage::Common::Core::Filter
30
+ class RetryPolicyFilter < Azure::Core::Http::RetryPolicy
31
+ def initialize(retry_count = nil, retry_interval = nil)
32
+ @retry_count = retry_count
33
+ @retry_interval = retry_interval
34
+ @request_options = {}
35
+
36
+ super &:should_retry?
37
+ end
38
+
39
+ attr_reader :retry_count,
40
+ :retry_interval
41
+
42
+ # Overrides the base class implementation of call to determine
43
+ # whether to retry the operation
44
+ #
45
+ # response - HttpResponse. The response from the active request
46
+ # retry_data - Hash. Stores stateful retry data
47
+ def should_retry?(response, retry_data)
48
+ # Fill necessary information
49
+ init_retry_data retry_data
50
+
51
+ # Applies the logic when there is subclass overrides it
52
+ apply_retry_policy retry_data
53
+
54
+ # Checks the result and count limit
55
+ if retry_data[:retryable].nil?
56
+ retry_data[:retryable] = true
57
+ else
58
+ retry_data[:retryable] &&= retry_data[:count] <= @retry_count
59
+ end
60
+ return false unless retry_data[:retryable]
61
+
62
+ # Checks whether there is a local error
63
+ # Cannot retry immediately when it returns true, as it need check other errors
64
+ should_retry_on_local_error? retry_data
65
+ return false unless should_retry_on_error? response, retry_data
66
+
67
+ # Determined that it needs to retry.
68
+ adjust_retry_request retry_data
69
+
70
+ wait_for_retry
71
+
72
+ retry_data[:retryable]
73
+ end
74
+
75
+ # Apply the retry policy to determine how the HTTP request should continue retrying
76
+ #
77
+ # retry_data - Hash. Stores stateful retry data
78
+ #
79
+ # The retry_data is a Hash which can be used to store
80
+ # stateful data about the request execution context (such as an
81
+ # incrementing counter, timestamp, etc). The retry_data object
82
+ # will be the same instance throughout the lifetime of the request
83
+ #
84
+ # Alternatively, a subclass could override this method.
85
+ def apply_retry_policy(retry_data)
86
+ end
87
+
88
+ # Determines if the HTTP request should continue retrying
89
+ #
90
+ # retry_data - Hash. Stores stateful retry data
91
+ #
92
+ # The retry_data is a Hash which can be used to store
93
+ # stateful data about the request execution context (such as an
94
+ # incrementing counter, timestamp, etc). The retry_data object
95
+ # will be the same instance throughout the lifetime of the request.
96
+ def should_retry_on_local_error?(retry_data)
97
+ unless retry_data[:error]
98
+ retry_data[:retryable] = true;
99
+ return true
100
+ end
101
+
102
+ error_message = retry_data[:error].inspect
103
+
104
+ if error_message.include?("SocketError: Hostname not known")
105
+ # Retry on local DNS resolving
106
+ # When uses resolv-replace.rb to replace the libc resolver
107
+ # Reference:
108
+ # https://makandracards.com/ninjaconcept/30815-fixing-socketerror-getaddrinfo-name-or-service-not-known-with-ruby-s-resolv-replace-rb
109
+ # http://www.subelsky.com/2014/05/fixing-socketerror-getaddrinfo-name-or.html
110
+ retry_data[:retryable] = true;
111
+ elsif error_message.include?("getaddrinfo: Name or service not known")
112
+ # When uses the default resolver
113
+ retry_data[:retryable] = true;
114
+ elsif error_message.downcase.include?("timeout")
115
+ retry_data[:retryable] = true;
116
+ elsif error_message.include?("Errno::ECONNRESET")
117
+ retry_data[:retryable] = true;
118
+ elsif error_message.include?("Errno::EACCES")
119
+ retry_data[:retryable] = false;
120
+ elsif error_message.include?("NOSUPPORT")
121
+ retry_data[:retryable] = false;
122
+ end
123
+
124
+ retry_data[:retryable]
125
+ end
126
+
127
+ # Determines if the HTTP request should continue retrying
128
+ #
129
+ # response - Azure::Core::Http::HttpResponse. The response from the active request
130
+ # retry_data - Hash. Stores stateful retry data
131
+ #
132
+ # The retry_data is a Hash which can be used to store
133
+ # stateful data about the request execution context (such as an
134
+ # incrementing counter, timestamp, etc). The retry_data object
135
+ # will be the same instance throughout the lifetime of the request.
136
+ def should_retry_on_error?(response, retry_data)
137
+ response = response || retry_data[:error].http_response if retry_data[:error] && retry_data[:error].respond_to?("http_response")
138
+ unless response
139
+ retry_data[:retryable] = false unless retry_data[:error]
140
+ return retry_data[:retryable]
141
+ end
142
+
143
+ check_location(response, retry_data)
144
+
145
+ check_status_code(retry_data)
146
+
147
+ retry_data[:retryable]
148
+ end
149
+
150
+ # Adjust the retry parameter and wait for retry
151
+ def wait_for_retry
152
+ sleep @retry_interval if @retry_interval > 0
153
+ end
154
+
155
+ # Adjust the retry request
156
+ #
157
+ # retry_data - Hash. Stores stateful retry data
158
+ def adjust_retry_request(retry_data)
159
+ # Adjust the location first
160
+ next_location = @request_options[:target_location].nil? ? get_next_location(retry_data) : @request_options[:target_location]
161
+ retry_data[:current_location] = next_location
162
+
163
+ retry_data[:uri] =
164
+ if next_location == Azure::Storage::Common::StorageLocation::PRIMARY
165
+ @request_options[:primary_uri]
166
+ else
167
+ @request_options[:secondary_uri]
168
+ end
169
+
170
+ # Now is the time to calculate the exact retry interval. ShouldRetry call above already
171
+ # returned back how long two requests to the same location should be apart from each other.
172
+ # However, for the reasons explained above, the time spent between the last attempt to
173
+ # the target location and current time must be subtracted from the total retry interval
174
+ # that ShouldRetry returned.
175
+ lastAttemptTime =
176
+ if retry_data[:current_location] == Azure::Storage::Common::StorageLocation::PRIMARY
177
+ retry_data[:last_primary_attempt]
178
+ else
179
+ retry_data[:last_secondary_attempt]
180
+ end
181
+
182
+ @retry_interval =
183
+ if lastAttemptTime.nil?
184
+ 0
185
+ else
186
+ since_last_attempt = Time.now - lastAttemptTime
187
+ remainder = retry_data[:interval] - since_last_attempt
188
+ remainder > 0 ? remainder : 0
189
+ end
190
+ end
191
+
192
+ # Initialize the retry data
193
+ #
194
+ # retry_data - Hash. Stores stateful retry data
195
+ def init_retry_data(retry_data)
196
+ @request_options = retry_data[:request_options] unless retry_data[:request_options].nil?
197
+
198
+ if retry_data[:current_location].nil?
199
+ retry_data[:current_location] = Azure::Storage::Common::Service::StorageService.get_location(@request_options[:location_mode], @request_options[:request_location_mode])
200
+ end
201
+
202
+ if retry_data[:current_location] == Azure::Storage::Common::StorageLocation::PRIMARY
203
+ retry_data[:last_primary_attempt] = Time.now
204
+ else
205
+ retry_data[:last_secondary_attempt] = Time.now
206
+ end
207
+ end
208
+
209
+ # Check the location
210
+ #
211
+ # retry_data - Hash. Stores stateful retry data
212
+ def check_location(response, retry_data)
213
+ # If a request sent to the secondary location fails with 404 (Not Found), it is possible
214
+ # that the resource replication is not finished yet. So, in case of 404 only in the secondary
215
+ # location, the failure should still be retryable.
216
+ retry_data[:secondary_not_found] =
217
+ ((retry_data[:current_location] === Azure::Storage::Common::StorageLocation::SECONDARY) &&
218
+ response.status_code === 404);
219
+
220
+ if retry_data[:secondary_not_found]
221
+ retry_data[:status_code] = 500
222
+ else
223
+ if (response.status_code)
224
+ retry_data[:status_code] = response.status_code
225
+ else
226
+ retry_data[:status_code] = nil
227
+ end
228
+ end
229
+ end
230
+
231
+ # Check the status code
232
+ #
233
+ # retry_data - Hash. Stores stateful retry data
234
+ def check_status_code(retry_data)
235
+ if (retry_data[:status_code] < 400)
236
+ retry_data[:retryable] = false;
237
+ # Non-timeout Cases
238
+ elsif (retry_data[:status_code] != 408)
239
+ # Always no retry on "not implemented" and "version not supported"
240
+ if (retry_data[:status_code] == 501 || retry_data[:status_code] == 505)
241
+ retry_data[:retryable] = false;
242
+ end
243
+
244
+ # When absorb_conditional_errors_on_retry is set (for append blob)
245
+ if (@request_options[:absorb_conditional_errors_on_retry])
246
+ if (retry_data[:status_code] == 412)
247
+ # When appending block with precondition failure and their was a server error before, we ignore the error.
248
+ if (retry_data[:last_server_error])
249
+ retry_data[:error] = nil;
250
+ retry_data[:retryable] = true;
251
+ else
252
+ retry_data[:retryable] = false;
253
+ end
254
+ elsif (retry_data[:retryable] && retry_data[:status_code] >= 500 && retry_data[:status_code] < 600)
255
+ # Retry on the server error
256
+ retry_data[:retryable] = true;
257
+ retry_data[:last_server_error] = true;
258
+ end
259
+ elsif (retry_data[:status_code] < 500)
260
+ # No retry on the client error
261
+ retry_data[:retryable] = false;
262
+ end
263
+ end
264
+ end
265
+
266
+ # Get retry request destination
267
+ #
268
+ # retry_data - Hash. Stores stateful retry data
269
+ def get_next_location(retry_data)
270
+ # In case of 404 when trying the secondary location, instead of retrying on the
271
+ # secondary, further requests should be sent only to the primary location, as it most
272
+ # probably has a higher chance of succeeding there.
273
+ if retry_data[:secondary_not_found] && @request_options[:location_mode] != Azure::Storage::Common::LocationMode::SECONDARY_ONLY
274
+ @request_options[:location_mode] = Azure::Storage::Common::LocationMode::PRIMARY_ONLY;
275
+ return Azure::Storage::Common::StorageLocation::PRIMARY
276
+ end
277
+
278
+ case @request_options[:location_mode]
279
+ when Azure::Storage::Common::LocationMode::PRIMARY_ONLY
280
+ Azure::Storage::Common::StorageLocation::PRIMARY
281
+ when Azure::Storage::Common::LocationMode::SECONDARY_ONLY
282
+ Azure::Storage::Common::StorageLocation::SECONDARY
283
+ else
284
+ # request_location_mode cannot be SECONDARY_ONLY because it will be blocked at the first time
285
+ if @request_options[:request_location_mode] == Azure::Storage::Common::RequestLocationMode::PRIMARY_ONLY
286
+ Azure::Storage::Common::StorageLocation::PRIMARY
287
+ elsif @request_options[:request_location_mode] == Azure::Storage::Common::RequestLocationMode::SECONDARY_ONLY
288
+ Azure::Storage::Common::StorageLocation::SECONDARY
289
+ else
290
+ if retry_data[:current_location] === Azure::Storage::Common::StorageLocation::PRIMARY
291
+ Azure::Storage::Common::StorageLocation::SECONDARY
292
+ else
293
+ Azure::Storage::Common::StorageLocation::PRIMARY
294
+ end
295
+ end
296
+ end
297
+ end
298
+
299
+ end
300
+ end
@@ -0,0 +1,82 @@
1
+ # frozen_string_literal: true
2
+
3
+ #-------------------------------------------------------------------------
4
+ # # Copyright (c) Microsoft and contributors. All rights reserved.
5
+ #
6
+ # The MIT License(MIT)
7
+
8
+ # Permission is hereby granted, free of charge, to any person obtaining a copy
9
+ # of this software and associated documentation files(the "Software"), to deal
10
+ # in the Software without restriction, including without limitation the rights
11
+ # to use, copy, modify, merge, publish, distribute, sublicense, and / or sell
12
+ # copies of the Software, and to permit persons to whom the Software is
13
+ # furnished to do so, subject to the following conditions :
14
+
15
+ # The above copyright notice and this permission notice shall be included in
16
+ # all copies or substantial portions of the Software.
17
+
18
+ # THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
19
+ # IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
20
+ # FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.IN NO EVENT SHALL THE
21
+ # AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
22
+ # LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
23
+ # OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
24
+ # THE SOFTWARE.
25
+ #--------------------------------------------------------------------------
26
+
27
+ module Azure::Storage::Common::Core
28
+ module HttpClient
29
+ # Returns the http agent based on uri
30
+ # @param uri [URI|String] the base uri (scheme, host, port) of the http endpoint
31
+ # @return [Net::HTTP] http agent for a given uri
32
+ def agents(uri)
33
+ uri = URI(uri) unless uri.is_a? URI
34
+ key = uri.host
35
+
36
+ @agents ||= {}
37
+ unless @agents.key?(key)
38
+ @agents[key] = build_http(uri)
39
+ else
40
+ reuse_agent!(@agents[key])
41
+ end
42
+ @agents[key]
43
+ end
44
+
45
+ # Empties all the http agents
46
+ def reset_agents!
47
+ @agents = nil
48
+ end
49
+
50
+ private
51
+
52
+ # Empties all information that cannot be reused.
53
+ def reuse_agent!(agent)
54
+ agent.params.clear
55
+ agent.headers.clear
56
+ end
57
+
58
+ def build_http(uri)
59
+ ssl_options = {}
60
+ if uri.is_a?(URI) && uri.scheme.downcase == "https"
61
+ ssl_options[:version] = self.ssl_version if self.ssl_version
62
+ # min_version and max_version only supported in ruby 2.5
63
+ ssl_options[:min_version] = self.ssl_min_version if self.ssl_min_version
64
+ ssl_options[:max_version] = self.ssl_max_version if self.ssl_max_version
65
+ ssl_options[:ca_file] = self.ca_file if self.ca_file
66
+ ssl_options[:verify] = true
67
+ end
68
+ proxy_options = if ENV["HTTP_PROXY"]
69
+ URI::parse(ENV["HTTP_PROXY"])
70
+ elsif ENV["HTTPS_PROXY"]
71
+ URI::parse(ENV["HTTPS_PROXY"])
72
+ end || nil
73
+ Faraday.new(uri, ssl: ssl_options, proxy: proxy_options) do |conn|
74
+ conn.response :follow_redirects #use Faraday::FollowRedirects::Middleware
75
+ conn.adapter :net_http_persistent, pool_size: 5 do |http|
76
+ # yields Net::HTTP::Persistent
77
+ http.idle_timeout = 100
78
+ end
79
+ end
80
+ end
81
+ end
82
+ end
@@ -0,0 +1,85 @@
1
+ # frozen_string_literal: true
2
+
3
+ #-------------------------------------------------------------------------
4
+ # # Copyright (c) Microsoft and contributors. All rights reserved.
5
+ #
6
+ # The MIT License(MIT)
7
+
8
+ # Permission is hereby granted, free of charge, to any person obtaining a copy
9
+ # of this software and associated documentation files(the "Software"), to deal
10
+ # in the Software without restriction, including without limitation the rights
11
+ # to use, copy, modify, merge, publish, distribute, sublicense, and / or sell
12
+ # copies of the Software, and to permit persons to whom the Software is
13
+ # furnished to do so, subject to the following conditions :
14
+
15
+ # The above copyright notice and this permission notice shall be included in
16
+ # all copies or substantial portions of the Software.
17
+
18
+ # THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
19
+ # IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
20
+ # FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.IN NO EVENT SHALL THE
21
+ # AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
22
+ # LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
23
+ # OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
24
+ # THE SOFTWARE.
25
+ #--------------------------------------------------------------------------
26
+
27
+
28
+ module Azure::Storage::Common::Core
29
+ module SR
30
+ ANONYMOUS_ACCESS_BLOBSERVICE_ONLY = "Anonymous access is only valid for the BlobService."
31
+ ARGUMENT_NULL_OR_EMPTY = "The argument must not be null or an empty string. Argument name: %s."
32
+ ARGUMENT_NULL_OR_UNDEFINED = "The argument must not be null or undefined. Argument name: %s."
33
+ ARGUMENT_OUT_OF_RANGE_ERROR = "The argument is out of range. Argument name: %s, Value passed: %s."
34
+ BATCH_ONE_PARTITION_KEY = "All entities in the batch must have the same PartitionKey value."
35
+ BATCH_ONE_RETRIEVE = "If a retrieve operation is part of a batch, it must be the only operation in the batch."
36
+ BATCH_TOO_LARGE = "Batches must not contain more than 100 operations."
37
+ BLOB_INVALID_SEQUENCE_NUMBER = "The sequence number may not be specified for an increment operation."
38
+ BLOB_TYPE_MISMATCH = 'Blob type of the blob reference doesn\'t match blob type of the blob.'
39
+ CANNOT_CREATE_SAS_WITHOUT_ACCOUNT_KEY = "Cannot create Shared Access Signature unless the Account Name and Key are used to create the ServiceClient."
40
+ CONTENT_LENGTH_MISMATCH = "An incorrect number of bytes was read from the connection. The connection may have been closed."
41
+ CONTENT_TYPE_MISSING = "Content-Type response header is missing or invalid."
42
+ EMPTY_BATCH = "Batch must not be empty."
43
+ EXCEEDED_SIZE_LIMITATION = "Upload exceeds the size limitation. Max size is %s but the current size is %s"
44
+ HASH_MISMATCH = "Hash mismatch (integrity check failed), Expected value is %s, retrieved %s."
45
+ INCORRECT_ENTITY_KEYS = "PartitionKey and RowKey must be specified as strings in the entity object."
46
+ INVALID_BLOB_LENGTH = "createBlockBlobFromText requires the size of text to be less than 64MB. Please use createBlockBlobFromLocalFile or createBlockBlobFromStream to upload large blobs."
47
+ INVALID_CONNECTION_STRING = 'Connection strings must be of the form "key1=value1;key2=value2".'
48
+ INVALID_CONNECTION_STRING_BAD_KEY = 'Connection string contains unrecognized key: "%s"'
49
+ INVALID_CONNECTION_STRING_DUPLICATE_KEY = 'Connection string contains duplicate key: "%s"'
50
+ INVALID_CONNECTION_STRING_EMPTY_KEY = "Connection strings must not contain empty keys."
51
+ INVALID_CLIENT_OPTIONS = "Storage client options are invalid"
52
+ INVALID_DELETE_SNAPSHOT_OPTION = "The deleteSnapshots option cannot be included when deleting a specific snapshot using the snapshotId option."
53
+ INVALID_EDM_TYPE = 'The value \'%s\' does not match the type \'%s\'.'
54
+ INVALID_FILE_LENGTH = "createFileFromText requires the size of text to be less than 4MB. Please use createFileFromLocalFile or createFileFromStream to upload large files."
55
+ INVALID_FILE_RANGE_FOR_UPDATE = "Range size should be less than 4MB for a file range update operation."
56
+ INVALID_HEADERS = "Headers are not supported in the 2012-02-12 version."
57
+ INVALID_MESSAGE_ID = "Message ID cannot be null or undefined for deleteMessage and updateMessage operations."
58
+ INVALID_PAGE_BLOB_LENGTH = "Page blob length must be multiple of 512."
59
+ INVALID_PAGE_END_OFFSET = "Page end offset must be multiple of 512."
60
+ INVALID_PAGE_RANGE_FOR_UPDATE = "Page range size should be less than 4MB for a page update operation."
61
+ INVALID_PAGE_START_OFFSET = "Page start offset must be multiple of 512."
62
+ INVALID_POP_RECEIPT = "Pop Receipt cannot be null or undefined for deleteMessage and updateMessage operations."
63
+ INVALID_PROPERTY_RESOLVER = "The specified property resolver returned an invalid type. %s:{_:%s,$:%s }"
64
+ INVALID_RANGE_FOR_MD5 = "The requested range should be less than 4MB when contentMD5 is expected from the server"
65
+ INVALID_SAS_VERSION = "SAS Version ? is invalid. Valid versions include: ?."
66
+ INVALID_SAS_TOKEN = "The SAS token should not contain api-version."
67
+ INVALID_SIGNED_IDENTIFIERS = "Signed identifiers need to be an array."
68
+ INVALID_STREAM_LENGTH = "The length of the provided stream is invalid."
69
+ INVALID_STRING_ERROR = "Invalid string error."
70
+ INVALID_TABLE_OPERATION = "Operation not found: %s"
71
+ INVALID_TEXT_LENGTH = "The length of the provided text is invalid."
72
+ MAXIMUM_EXECUTION_TIMEOUT_EXCEPTION = "The client could not finish the operation within specified maximum execution timeout."
73
+ MD5_NOT_PRESENT_ERROR = "MD5 does not exist. If you do not want to force validation, please disable useTransactionalMD5."
74
+ METADATA_KEY_INVALID = "The key for one of the metadata key-value pairs is null, empty, or whitespace."
75
+ METADATA_VALUE_INVALID = "The value for one of the metadata key-value pairs is null, empty, or whitespace."
76
+ NO_CREDENTIALS_PROVIDED = "Credentials must be provided when creating a service client."
77
+ PRIMARY_ONLY_COMMAND = "This operation can only be executed against the primary storage location."
78
+ QUERY_OPERATOR_REQUIRES_WHERE = "%s operator needs to be used after where."
79
+ SECONDARY_ONLY_COMMAND = "This operation can only be executed against the secondary storage location."
80
+ STORAGE_HOST_LOCATION_REQUIRED = "The host for the storage service must be specified."
81
+ STORAGE_HOST_MISSING_LOCATION = 'The host for the target storage location is not specified. Please consider changing the request\'s location mode.'
82
+ TYPE_NOT_SUPPORTED = "Type not supported when sending data to the service: "
83
+ MAX_BLOB_SIZE_CONDITION_NOT_MEET = "The max blob size condition specified was not met."
84
+ end
85
+ end