gapic-common 0.15.0 → 0.18.0

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.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 5902b53f0f5a46b4682ff855fb89a6a3162af38523fa273f273abeeeed0d3a3d
4
- data.tar.gz: a1e9bb69d31725768f00b152efcaf29042657fbb304c2ba2f25de485831fe187
3
+ metadata.gz: 609c468f1e8a7e60f8b4ba911901dd99f8816cb367371dd5479d79dcd06bca82
4
+ data.tar.gz: 23a01faa58af17577e262852d434a6746b33f090247b05ea9dc8ce2ae07772bb
5
5
  SHA512:
6
- metadata.gz: 84d77cc3d943714b8a3578ecabf3fea3a321dfe0929ee108233d4dcd8fede90a37be21a81e121142739aa3dca102ffff0826a003906bec16f03749beddf59ab2
7
- data.tar.gz: 27e2815be724399a4c01ca1d47c7b2e9291ee4583018251f45a2a0162f1d5cd8298d0ca3b8a4cf90fc4ba6f2e410240439e61a22a66fbeae89c5a3e9dc223879
6
+ metadata.gz: 7fc2a7f8c0fdcc79434966a1e6431c29d957dd1a646cae5a8cd023da1320b7f5253b69f4edd915c98656b12e681aac66bf11713c2bb47f0482798601635ba948
7
+ data.tar.gz: 49a6c6aaa7fca24979d8707bc7a6ba2b8daed51951539d2235be32f932e73a02fa4cd8d7699f811b358bd216ca99ffbe63dab0469196b1815cdf37eb6ad4055c
data/CHANGELOG.md CHANGED
@@ -1,5 +1,35 @@
1
1
  # Release History
2
2
 
3
+ ### 0.18.0 (2023-02-27)
4
+
5
+ #### Features
6
+
7
+ * add alias for details field in Rest Error ([#928](https://github.com/googleapis/gapic-generator-ruby/issues/928))
8
+
9
+ ### 0.17.1 (2023-02-09)
10
+
11
+ #### Bug Fixes
12
+
13
+ * add new class to the rest imports ([#913](https://github.com/googleapis/gapic-generator-ruby/issues/913))
14
+
15
+ ### 0.17.0 (2023-02-09)
16
+
17
+ #### Features
18
+
19
+ * add a transport operation class in Rest ([#911](https://github.com/googleapis/gapic-generator-ruby/issues/911))
20
+
21
+ ### 0.16.0 (2022-12-12)
22
+
23
+ #### Features
24
+
25
+ * custom regapic exception wrapping ([#866](https://github.com/googleapis/gapic-generator-ruby/issues/866))
26
+
27
+ ### 0.15.1 (2022-11-18)
28
+
29
+ #### Bug Fixes
30
+
31
+ * Fixed uninitialized constant when checking retry policy for a REST call ([#857](https://github.com/googleapis/gapic-generator-ruby/issues/857))
32
+
3
33
  ### 0.15.0 (2022-11-17)
4
34
 
5
35
  #### Features
@@ -45,26 +45,29 @@ module Gapic
45
45
  # @private
46
46
  ERROR_STRING_MAPPING = error_code_mapping.each_with_index.to_h.freeze
47
47
 
48
+ # @private
49
+ HTTP_GRPC_CODE_MAP = {
50
+ 400 => 3, # InvalidArgumentError
51
+ 401 => 16, # UnauthenticatedError
52
+ 403 => 7, # PermissionDeniedError
53
+ 404 => 5, # NotFoundError
54
+ 409 => 6, # AlreadyExistsError
55
+ 412 => 9, # FailedPreconditionError
56
+ 429 => 8, # ResourceExhaustedError
57
+ 499 => 1, # CanceledError
58
+ 500 => 13, # InternalError
59
+ 501 => 12, # UnimplementedError
60
+ 503 => 14, # UnavailableError
61
+ 504 => 4 # DeadlineExceededError
62
+ }.freeze
63
+
48
64
  # @private
49
65
  # Converts http error codes into corresponding gRPC ones
50
66
  def self.grpc_error_for http_error_code
51
67
  return 2 unless http_error_code
52
68
 
53
69
  # The http status codes mapped to their error classes.
54
- {
55
- 400 => 3, # InvalidArgumentError
56
- 401 => 16, # UnauthenticatedError
57
- 403 => 7, # PermissionDeniedError
58
- 404 => 5, # NotFoundError
59
- 409 => 6, # AlreadyExistsError
60
- 412 => 9, # FailedPreconditionError
61
- 429 => 8, # ResourceExhaustedError
62
- 499 => 1, # CanceledError
63
- 500 => 13, # InternalError
64
- 501 => 12, # UnimplementedError
65
- 503 => 14, # UnavailableError
66
- 504 => 4 # DeadlineExceededError
67
- }[http_error_code] || 2 # UnknownError
70
+ HTTP_GRPC_CODE_MAP[http_error_code] || 2 # UnknownError
68
71
  end
69
72
  end
70
73
  end
@@ -106,7 +106,7 @@ module Gapic
106
106
  private
107
107
 
108
108
  def retry? error
109
- (error.is_a?(::GRPC::BadStatus) && retry_codes.include?(error.code)) ||
109
+ (defined?(::GRPC) && error.is_a?(::GRPC::BadStatus) && retry_codes.include?(error.code)) ||
110
110
  (error.respond_to?(:response_status) &&
111
111
  retry_codes.include?(ErrorCodes.grpc_error_for(error.response_status)))
112
112
  end
@@ -14,6 +14,6 @@
14
14
 
15
15
  module Gapic
16
16
  module Common
17
- VERSION = "0.15.0".freeze
17
+ VERSION = "0.18.0".freeze
18
18
  end
19
19
  end
@@ -34,9 +34,15 @@ module Gapic
34
34
  # (see the [googleauth docs](https://googleapis.dev/ruby/googleauth/latest/index.html))
35
35
  # @param numeric_enums [Boolean] Whether to signal the server to JSON-encode enums as ints
36
36
  #
37
+ # @param raise_faraday_errors [Boolean]
38
+ # Whether to raise Faraday errors instead of wrapping them in `Gapic::Rest::Error`
39
+ # Added for backwards compatibility.
40
+ # Default is `true`. All REST clients (except for old versions of `google-cloud-compute-v1`)
41
+ # should explicitly set this parameter to `false`.
42
+ #
37
43
  # @yield [Faraday::Connection]
38
44
  #
39
- def initialize endpoint:, credentials:, numeric_enums: false
45
+ def initialize endpoint:, credentials:, numeric_enums: false, raise_faraday_errors: true
40
46
  @endpoint = endpoint
41
47
  @endpoint = "https://#{endpoint}" unless /^https?:/.match? endpoint
42
48
  @endpoint = @endpoint.sub %r{/$}, ""
@@ -44,6 +50,8 @@ module Gapic
44
50
  @credentials = credentials
45
51
  @numeric_enums = numeric_enums
46
52
 
53
+ @raise_faraday_errors = raise_faraday_errors
54
+
47
55
  @connection = Faraday.new url: @endpoint do |conn|
48
56
  conn.headers = { "Content-Type" => "application/json" }
49
57
  conn.request :google_authorization, @credentials unless @credentials.is_a? ::Symbol
@@ -137,35 +145,31 @@ module Gapic
137
145
  next_timeout = get_timeout deadline
138
146
 
139
147
  begin
140
- base_make_http_request(verb,
141
- uri: uri,
142
- body: body,
143
- params: params,
144
- metadata: options.metadata,
148
+ base_make_http_request(verb: verb, uri: uri, body: body,
149
+ params: params, metadata: options.metadata,
145
150
  timeout: next_timeout,
146
151
  is_server_streaming: is_server_streaming,
147
152
  &block)
153
+ rescue ::Faraday::TimeoutError => e
154
+ raise if @raise_faraday_errors
155
+ raise Gapic::Rest::DeadlineExceededError.wrap_faraday_error e, root_cause: retried_exception
148
156
  rescue ::Faraday::Error => e
149
157
  next_timeout = get_timeout deadline
150
158
 
151
- if next_timeout&.positive? && options.retry_policy.call(e)
159
+ if check_retry?(next_timeout) && options.retry_policy.call(e)
152
160
  retried_exception = e
153
161
  retry
154
162
  end
155
163
 
156
- unless next_timeout&.positive?
157
- raise Gapic::GRPC::DeadlineExceededError.new e.message, root_cause: retried_exception
158
- end
159
-
160
- raise e
164
+ raise if @raise_faraday_errors
165
+ raise ::Gapic::Rest::Error.wrap_faraday_error e
161
166
  end
162
167
  end
163
168
 
164
- private
165
-
166
169
  ##
167
170
  # @private
168
171
  # Sends a http request via Faraday
172
+ #
169
173
  # @param verb [Symbol] http verb
170
174
  # @param uri [String] uri to send this request to
171
175
  # @param body [String, nil] a body to send with the request, nil for requests without a body
@@ -174,7 +178,8 @@ module Gapic
174
178
  # @param is_server_streaming [Boolean] flag if method is streaming
175
179
  # @yieldparam chunk [String] The chunk of data received during server streaming.
176
180
  # @return [Faraday::Response]
177
- def base_make_http_request verb, uri:, body:, params:, metadata:, timeout:, is_server_streaming: false
181
+ def base_make_http_request verb:, uri:, body:, params:, metadata:,
182
+ timeout:, is_server_streaming: false
178
183
  if @numeric_enums && (!params.key?("$alt") || params["$alt"] == "json")
179
184
  params = params.merge({ "$alt" => "json;enum-encoding=int" })
180
185
  end
@@ -192,6 +197,14 @@ module Gapic
192
197
  end
193
198
  end
194
199
 
200
+ private
201
+
202
+ ##
203
+ # Calculates deadline
204
+ #
205
+ # @param options [Gapic::CallOptions] call options for this call
206
+ #
207
+ # @return [Numeric, nil] Deadline against a POSIX clock_gettime()
195
208
  def calculate_deadline options
196
209
  return if options.timeout.nil?
197
210
  return if options.timeout.negative?
@@ -199,10 +212,28 @@ module Gapic
199
212
  Process.clock_gettime(Process::CLOCK_MONOTONIC) + options.timeout
200
213
  end
201
214
 
215
+ ##
216
+ # Calculates timeout (seconds) to use as a Faraday timeout
217
+ #
218
+ # @param deadline [Numeric, nil] deadline
219
+ #
220
+ # @return [Numeric, nil] Timeout (seconds)
202
221
  def get_timeout deadline
203
222
  return if deadline.nil?
204
223
  deadline - Process.clock_gettime(Process::CLOCK_MONOTONIC)
205
224
  end
225
+
226
+ ##
227
+ # Whether the timeout should be retried
228
+ #
229
+ # @param timeout [Numeric, nil]
230
+ #
231
+ # @return [Boolean] whether the timeout should be retried
232
+ def check_retry? timeout
233
+ return true if timeout.nil?
234
+
235
+ timeout.positive?
236
+ end
206
237
  end
207
238
  end
208
239
  end
@@ -14,6 +14,9 @@
14
14
 
15
15
  require "json"
16
16
  require "gapic/common/error"
17
+ require "google/protobuf/well_known_types"
18
+ # Not technically required but GRPC counterpart loads it and so should we for test parity
19
+ require "google/rpc/error_details_pb"
17
20
 
18
21
  module Gapic
19
22
  module Rest
@@ -25,6 +28,8 @@ module Gapic
25
28
  attr_reader :status
26
29
  # @return [Object, nil] the details as parsed from the response body
27
30
  attr_reader :details
31
+ # The Cloud error wrapper expect to see a `status_details` property
32
+ alias status_details details
28
33
  # @return [Object, nil] the headers of the REST error
29
34
  attr_reader :headers
30
35
  # The Cloud error wrapper expect to see a `header` property
@@ -55,6 +60,17 @@ module Gapic
55
60
  #
56
61
  # @return [ Gapic::Rest::Error]
57
62
  def wrap_faraday_error err
63
+ message, status_code, status, details, headers = parse_faraday_error err
64
+ Gapic::Rest::Error.new message, status_code, status: status, details: details, headers: headers
65
+ end
66
+
67
+ ##
68
+ # @private
69
+ # Tries to get the error information from Faraday error
70
+ #
71
+ # @param err [Faraday::Error] the Faraday error to extract information from
72
+ # @return [Array(String, String, String, String, String)]
73
+ def parse_faraday_error err
58
74
  message = err.message
59
75
  status_code = err.response_status
60
76
  status = nil
@@ -67,7 +83,7 @@ module Gapic
67
83
  status_code = code unless code.nil?
68
84
  end
69
85
 
70
- Gapic::Rest::Error.new message, status_code, status: status, details: details, headers: headers
86
+ [message, status_code, status, details, headers]
71
87
  end
72
88
 
73
89
  private
@@ -133,5 +149,62 @@ module Gapic
133
149
  end
134
150
  end
135
151
  end
152
+
153
+ ##
154
+ # An error class that represents DeadlineExceeded error for Rest
155
+ # with an optional retry root cause.
156
+ #
157
+ # If the deadline for making a call was exceeded during the rest calls,
158
+ # this exception is thrown wrapping Faraday::TimeoutError.
159
+ #
160
+ # If there were other exceptions retried before that, the last one will be
161
+ # saved as a "root_cause".
162
+ #
163
+ # @!attribute [r] root_cause
164
+ # @return [Object, nil] The exception that was being retried
165
+ # when the Faraday::TimeoutError error occured.
166
+ #
167
+ class DeadlineExceededError < Error
168
+ attr_reader :root_cause
169
+
170
+ ##
171
+ # @private
172
+ # @param message [String, nil] error message
173
+ # @param status_code [Integer, nil] HTTP status code of this error
174
+ # @param status [String, nil] The text representation of status as parsed from the response body
175
+ # @param details [Object, nil] Details data of this error
176
+ # @param headers [Object, nil] Http headers data of this error
177
+ # @param root_cause [Object, nil] The exception that was being retried
178
+ # when the Faraday::TimeoutError occured.
179
+ #
180
+ def initialize message, status_code, status: nil, details: nil, headers: nil, root_cause: nil
181
+ super message, status_code, status: status, details: details, headers: headers
182
+ @root_cause = root_cause
183
+ end
184
+
185
+ class << self
186
+ ##
187
+ # @private
188
+ # This creates a new error message wrapping the Faraday's one. Additionally
189
+ # it tries to parse and set a detailed message and an error code from
190
+ # from the Google Cloud's response body
191
+ #
192
+ # @param err [Faraday::TimeoutError] the Faraday error to wrap
193
+ #
194
+ # @param root_cause [Object, nil] The exception that was being retried
195
+ # when the Faraday::TimeoutError occured.
196
+ #
197
+ # @return [ Gapic::Rest::DeadlineExceededError]
198
+ def wrap_faraday_error err, root_cause: nil
199
+ message, status_code, status, details, headers = parse_faraday_error err
200
+ Gapic::Rest::DeadlineExceededError.new message,
201
+ status_code,
202
+ status: status,
203
+ details: details,
204
+ headers: headers,
205
+ root_cause: root_cause
206
+ end
207
+ end
208
+ end
136
209
  end
137
210
  end
@@ -50,7 +50,7 @@ module Gapic
50
50
  return enum_for :each unless block_given?
51
51
 
52
52
  loop do
53
- while @ready_objs.length.zero?
53
+ while @ready_objs.empty?
54
54
  begin
55
55
  chunk = @json_enumerator.next
56
56
  next unless chunk
@@ -0,0 +1,38 @@
1
+ # Copyright 2023 Google LLC
2
+ #
3
+ # Licensed under the Apache License, Version 2.0 (the "License");
4
+ # you may not use this file except in compliance with the License.
5
+ # You may obtain a copy of the License at
6
+ #
7
+ # https://www.apache.org/licenses/LICENSE-2.0
8
+ #
9
+ # Unless required by applicable law or agreed to in writing, software
10
+ # distributed under the License is distributed on an "AS IS" BASIS,
11
+ # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12
+ # See the License for the specific language governing permissions and
13
+ # limitations under the License.
14
+
15
+ module Gapic
16
+ module Rest
17
+ ##
18
+ # Surfaces information about the active call
19
+ # from the underlying transport library.
20
+ #
21
+ class TransportOperation
22
+ ##
23
+ # @private
24
+ # The underlying transport's library object that describes the active call, if any.
25
+ # It is not guaranteed to be any specific type, and its value is not guarateed to be stable.
26
+ # @return [::Object, nil, ::Faraday::Response]
27
+ attr_reader :underlying_op
28
+
29
+ ##
30
+ # @private
31
+ # @param request [::Object, nil, ::Faraday::Response]
32
+ # The underlying transport's library object that describes the active call, if any.
33
+ def initialize underlying_op
34
+ @underlying_op = underlying_op
35
+ end
36
+ end
37
+ end
38
+ end
data/lib/gapic/rest.rb CHANGED
@@ -29,4 +29,5 @@ require "gapic/rest/operation"
29
29
  require "gapic/rest/paged_enumerable"
30
30
  require "gapic/rest/server_stream"
31
31
  require "gapic/rest/threaded_enumerator"
32
+ require "gapic/rest/transport_operation"
32
33
  require "json"
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: gapic-common
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.15.0
4
+ version: 0.18.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Google API Authors
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2022-11-18 00:00:00.000000000 Z
11
+ date: 2023-02-27 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: faraday
@@ -317,6 +317,7 @@ files:
317
317
  - lib/gapic/rest/paged_enumerable.rb
318
318
  - lib/gapic/rest/server_stream.rb
319
319
  - lib/gapic/rest/threaded_enumerator.rb
320
+ - lib/gapic/rest/transport_operation.rb
320
321
  - lib/gapic/stream_input.rb
321
322
  homepage: https://github.com/googleapis/gapic-generator-ruby
322
323
  licenses:
@@ -337,7 +338,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
337
338
  - !ruby/object:Gem::Version
338
339
  version: '0'
339
340
  requirements: []
340
- rubygems_version: 3.3.14
341
+ rubygems_version: 3.4.2
341
342
  signing_key:
342
343
  specification_version: 4
343
344
  summary: Common code for GAPIC-generated API clients