aws-sdk-core 3.39.0 → 3.54.2
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 +4 -4
- data/VERSION +1 -1
- data/lib/aws-sdk-core/async_client_stubs.rb +80 -0
- data/lib/aws-sdk-core/binary/decode_handler.rb +9 -1
- data/lib/aws-sdk-core/binary/encode_handler.rb +32 -0
- data/lib/aws-sdk-core/binary/event_builder.rb +122 -0
- data/lib/aws-sdk-core/binary/event_parser.rb +48 -18
- data/lib/aws-sdk-core/binary/event_stream_decoder.rb +5 -2
- data/lib/aws-sdk-core/binary/event_stream_encoder.rb +53 -0
- data/lib/aws-sdk-core/binary.rb +3 -0
- data/lib/aws-sdk-core/client_side_monitoring/request_metrics.rb +63 -9
- data/lib/aws-sdk-core/client_stubs.rb +1 -1
- data/lib/aws-sdk-core/ecs_credentials.rb +12 -8
- data/lib/aws-sdk-core/errors.rb +38 -2
- data/lib/aws-sdk-core/event_emitter.rb +42 -0
- data/lib/aws-sdk-core/instance_profile_credentials.rb +12 -8
- data/lib/aws-sdk-core/json/error_handler.rb +19 -2
- data/lib/aws-sdk-core/json/handler.rb +19 -1
- data/lib/aws-sdk-core/log/param_filter.rb +1 -1
- data/lib/aws-sdk-core/param_validator.rb +9 -1
- data/lib/aws-sdk-core/plugins/client_metrics_plugin.rb +22 -3
- data/lib/aws-sdk-core/plugins/client_metrics_send_plugin.rb +5 -1
- data/lib/aws-sdk-core/plugins/event_stream_configuration.rb +14 -0
- data/lib/aws-sdk-core/plugins/invocation_id.rb +33 -0
- data/lib/aws-sdk-core/plugins/retry_errors.rb +2 -0
- data/lib/aws-sdk-core/plugins/stub_responses.rb +19 -7
- data/lib/aws-sdk-core/plugins/transfer_encoding.rb +53 -0
- data/lib/aws-sdk-core/plugins/user_agent.rb +6 -0
- data/lib/aws-sdk-core/process_credentials.rb +7 -1
- data/lib/aws-sdk-core/query/handler.rb +6 -1
- data/lib/aws-sdk-core/refreshing_credentials.rb +1 -1
- data/lib/aws-sdk-core/resources/collection.rb +1 -1
- data/lib/aws-sdk-core/structure.rb +6 -2
- data/lib/aws-sdk-core/stubbing/protocols/rest.rb +19 -0
- data/lib/aws-sdk-core/stubbing/stub_data.rb +13 -4
- data/lib/aws-sdk-core/waiters/waiter.rb +2 -2
- data/lib/aws-sdk-core/xml/error_handler.rb +26 -3
- data/lib/aws-sdk-core.rb +1 -0
- data/lib/aws-sdk-sts/client.rb +622 -427
- data/lib/aws-sdk-sts/client_api.rb +35 -0
- data/lib/aws-sdk-sts/errors.rb +128 -0
- data/lib/aws-sdk-sts/types.rb +498 -165
- data/lib/aws-sdk-sts.rb +1 -1
- data/lib/seahorse/client/async_base.rb +50 -0
- data/lib/seahorse/client/async_response.rb +62 -0
- data/lib/seahorse/client/base.rb +1 -1
- data/lib/seahorse/client/configuration.rb +4 -2
- data/lib/seahorse/client/events.rb +1 -1
- data/lib/seahorse/client/h2/connection.rb +244 -0
- data/lib/seahorse/client/h2/handler.rb +151 -0
- data/lib/seahorse/client/http/async_response.rb +42 -0
- data/lib/seahorse/client/http/response.rb +13 -8
- data/lib/seahorse/client/net_http/patches.rb +7 -1
- data/lib/seahorse/client/networking_error.rb +28 -0
- data/lib/seahorse/client/plugin.rb +1 -1
- data/lib/seahorse/client/plugins/content_length.rb +7 -2
- data/lib/seahorse/client/plugins/h2.rb +64 -0
- data/lib/seahorse/model/api.rb +4 -0
- data/lib/seahorse/model/operation.rb +4 -0
- data/lib/seahorse/model/shapes.rb +2 -2
- data/lib/seahorse.rb +9 -0
- metadata +23 -5
data/lib/aws-sdk-core/errors.rb
CHANGED
@@ -13,9 +13,12 @@ module Aws
|
|
13
13
|
|
14
14
|
# @param [Seahorse::Client::RequestContext] context
|
15
15
|
# @param [String] message
|
16
|
-
|
16
|
+
# @param [Aws::Structure] data
|
17
|
+
def initialize(context, message, data = Aws::EmptyStructure.new)
|
17
18
|
@code = self.class.code
|
19
|
+
@message = message if message && !message.empty?
|
18
20
|
@context = context
|
21
|
+
@data = data
|
19
22
|
super(message)
|
20
23
|
end
|
21
24
|
|
@@ -26,6 +29,9 @@ module Aws
|
|
26
29
|
# that triggered the remote service to return this error.
|
27
30
|
attr_reader :context
|
28
31
|
|
32
|
+
# @return [Aws::Structure]
|
33
|
+
attr_reader :data
|
34
|
+
|
29
35
|
class << self
|
30
36
|
|
31
37
|
# @return [String]
|
@@ -34,6 +40,24 @@ module Aws
|
|
34
40
|
end
|
35
41
|
end
|
36
42
|
|
43
|
+
# Raised when InstanceProfileCredentialsProvider or
|
44
|
+
# EcsCredentialsProvider fails to parse the metadata response after retries
|
45
|
+
class MetadataParserError < RuntimeError
|
46
|
+
def initialize(*args)
|
47
|
+
msg = "Failed to parse metadata service response."
|
48
|
+
super(msg)
|
49
|
+
end
|
50
|
+
end
|
51
|
+
|
52
|
+
# Raised when a `streaming` operation has `requiresLength` trait
|
53
|
+
# enabled but request payload size/length cannot be calculated
|
54
|
+
class MissingContentLength < RuntimeError
|
55
|
+
def initialize(*args)
|
56
|
+
msg = 'Required `Content-Length` value missing for the request.'
|
57
|
+
super(msg)
|
58
|
+
end
|
59
|
+
end
|
60
|
+
|
37
61
|
# Rasied when endpoint discovery failed for operations
|
38
62
|
# that requires endpoints from endpoint discovery
|
39
63
|
class EndpointDiscoveryError < RuntimeError
|
@@ -58,10 +82,18 @@ module Aws
|
|
58
82
|
|
59
83
|
end
|
60
84
|
|
85
|
+
# Raised when attempting to #signal an event before
|
86
|
+
# making an async request
|
87
|
+
class SignalEventError < RuntimeError; end
|
88
|
+
|
61
89
|
# Raised when EventStream Parser failed to parse
|
62
90
|
# a raw event message
|
63
91
|
class EventStreamParserError < RuntimeError; end
|
64
92
|
|
93
|
+
# Raise when EventStream Builder failed to build
|
94
|
+
# an event message with parameters provided
|
95
|
+
class EventStreamBuilderError < RuntimeError; end
|
96
|
+
|
65
97
|
# Error event in an event stream which has event_type :error
|
66
98
|
# error code and error message can be retrieved when available.
|
67
99
|
#
|
@@ -223,7 +255,11 @@ Known AWS regions include (not specific to this service):
|
|
223
255
|
def error_class(error_code)
|
224
256
|
constant = error_class_constant(error_code)
|
225
257
|
if error_const_set?(constant)
|
226
|
-
|
258
|
+
# modeled error class exist
|
259
|
+
# set code attribute
|
260
|
+
err_class = const_get(constant)
|
261
|
+
err_class.code = constant.to_s
|
262
|
+
err_class
|
227
263
|
else
|
228
264
|
set_error_constant(constant)
|
229
265
|
end
|
@@ -3,8 +3,19 @@ module Aws
|
|
3
3
|
|
4
4
|
def initialize
|
5
5
|
@listeners = {}
|
6
|
+
@validate_event = true
|
7
|
+
@status = :sleep
|
8
|
+
@signal_queue = Queue.new
|
6
9
|
end
|
7
10
|
|
11
|
+
attr_accessor :stream
|
12
|
+
|
13
|
+
attr_accessor :encoder
|
14
|
+
|
15
|
+
attr_accessor :validate_event
|
16
|
+
|
17
|
+
attr_accessor :signal_queue
|
18
|
+
|
8
19
|
def on(type, callback)
|
9
20
|
(@listeners[type] ||= []) << callback
|
10
21
|
end
|
@@ -16,5 +27,36 @@ module Aws
|
|
16
27
|
end
|
17
28
|
end
|
18
29
|
|
30
|
+
def emit(type, params)
|
31
|
+
unless @stream
|
32
|
+
raise Aws::Errors::SignalEventError.new(
|
33
|
+
"Singaling events before making async request"\
|
34
|
+
" is not allowed."
|
35
|
+
)
|
36
|
+
end
|
37
|
+
if @validate_event && type != :end_stream
|
38
|
+
Aws::ParamValidator.validate!(
|
39
|
+
@encoder.rules.shape.member(type), params)
|
40
|
+
end
|
41
|
+
_ready_for_events?
|
42
|
+
@stream.data(
|
43
|
+
@encoder.encode(type, params),
|
44
|
+
end_stream: type == :end_stream
|
45
|
+
)
|
46
|
+
end
|
47
|
+
|
48
|
+
private
|
49
|
+
|
50
|
+
def _ready_for_events?
|
51
|
+
return true if @status == :ready
|
52
|
+
|
53
|
+
# blocked until once initial 200 response is received
|
54
|
+
# signal will be available in @signal_queue
|
55
|
+
# and this check will no longer be blocked
|
56
|
+
@signal_queue.pop
|
57
|
+
@status = :ready
|
58
|
+
true
|
59
|
+
end
|
60
|
+
|
19
61
|
end
|
20
62
|
end
|
@@ -69,14 +69,18 @@ module Aws
|
|
69
69
|
# Retry loading credentials up to 3 times is the instance metadata
|
70
70
|
# service is responding but is returning invalid JSON documents
|
71
71
|
# in response to the GET profile credentials call.
|
72
|
-
|
73
|
-
|
74
|
-
|
75
|
-
|
76
|
-
|
77
|
-
|
78
|
-
|
79
|
-
|
72
|
+
begin
|
73
|
+
retry_errors([JSON::ParserError, StandardError], max_retries: 3) do
|
74
|
+
c = JSON.parse(get_credentials.to_s)
|
75
|
+
@credentials = Credentials.new(
|
76
|
+
c['AccessKeyId'],
|
77
|
+
c['SecretAccessKey'],
|
78
|
+
c['Token']
|
79
|
+
)
|
80
|
+
@expiration = c['Expiration'] ? Time.iso8601(c['Expiration']) : nil
|
81
|
+
end
|
82
|
+
rescue JSON::ParserError
|
83
|
+
raise Aws::Errors::MetadataParserError.new
|
80
84
|
end
|
81
85
|
end
|
82
86
|
|
@@ -17,9 +17,10 @@ module Aws
|
|
17
17
|
json = Json.load(body)
|
18
18
|
code = error_code(json, context)
|
19
19
|
message = error_message(code, json)
|
20
|
-
|
20
|
+
data = parse_error_data(context, code)
|
21
|
+
[code, message, data]
|
21
22
|
rescue Json::ParseError
|
22
|
-
[http_status_error_code(context), '']
|
23
|
+
[http_status_error_code(context), '', EmptyStructure.new]
|
23
24
|
end
|
24
25
|
|
25
26
|
def error_code(json, context)
|
@@ -41,6 +42,22 @@ module Aws
|
|
41
42
|
end
|
42
43
|
end
|
43
44
|
|
45
|
+
def parse_error_data(context, code)
|
46
|
+
data = EmptyStructure.new
|
47
|
+
if error_rules = context.operation.errors
|
48
|
+
error_rules.each do |rule|
|
49
|
+
# match modeled shape name with the type(code) only
|
50
|
+
# some type(code) might contains invalid characters
|
51
|
+
# such as ':' (efs) etc
|
52
|
+
match = rule.shape.name == code.gsub(/[^^a-zA-Z0-9]/, '')
|
53
|
+
if match && rule.shape.members.any?
|
54
|
+
data = Parser.new(rule).parse(context.http_response.body_contents)
|
55
|
+
end
|
56
|
+
end
|
57
|
+
end
|
58
|
+
data
|
59
|
+
end
|
60
|
+
|
44
61
|
end
|
45
62
|
end
|
46
63
|
end
|
@@ -40,7 +40,25 @@ module Aws
|
|
40
40
|
Json.load(context.http_response.body_contents)
|
41
41
|
elsif rules = context.operation.output
|
42
42
|
json = context.http_response.body_contents
|
43
|
-
|
43
|
+
if json.is_a?(Array)
|
44
|
+
# an array of emitted events
|
45
|
+
if json[0].respond_to?(:response)
|
46
|
+
# initial response exists
|
47
|
+
# it must be the first event arrived
|
48
|
+
resp_struct = json.shift.response
|
49
|
+
else
|
50
|
+
resp_struct = context.operation.output.shape.struct_class.new
|
51
|
+
end
|
52
|
+
|
53
|
+
rules.shape.members.each do |name, ref|
|
54
|
+
if ref.eventstream
|
55
|
+
resp_struct.send("#{name}=", json.to_enum)
|
56
|
+
end
|
57
|
+
end
|
58
|
+
resp_struct
|
59
|
+
else
|
60
|
+
Parser.new(rules).parse(json == '' ? '{}' : json)
|
61
|
+
end
|
44
62
|
else
|
45
63
|
EmptyStructure.new
|
46
64
|
end
|
@@ -11,7 +11,7 @@ module Aws
|
|
11
11
|
#
|
12
12
|
# @api private
|
13
13
|
# begin
|
14
|
-
SENSITIVE = [:access_token, :account_name, :account_password, :address, :admin_contact, :artifact_credentials, :auth_code, :authentication_token, :authorization_result, :base_32_string_seed, :body, :bot_configuration, :client_id, :client_secret, :configuration, :copy_source_sse_customer_key, :credentials, :custom_attributes, :db_password, :description, :display_name, :email, :email_address, :email_message, :embed_url, :feedback_token, :first_name, :id, :id_token, :input, :input_text, :key_id, :kms_key_id, :kms_master_key_id, :last_name, :local_console_password, :master_account_email, :master_user_password, :message, :name, :new_password, :notes, :old_password, :owner_information, :parameters, :passphrase, :password, :payload, :plaintext, :previous_password, :primary_email, :private_key, :proposed_password, :public_key, :qr_code_png, :query, :refresh_token, :registrant_contact, :request_attributes, :search_query, :secret_access_key, :secret_binary, :secret_code, :secret_hash, :secret_string, :service_password, :session_attributes, :share_notes, :shared_secret, :slots, :sse_customer_key, :ssekms_key_id, :status_message, :task_parameters, :tech_contact, :temporary_password, :text, :token, :trust_password, :upload_credentials, :upload_url, :user_email, :user_name, :username, :value, :values, :variables, :zip_file]
|
14
|
+
SENSITIVE = [:access_token, :account_name, :account_password, :address, :admin_contact, :admin_password, :artifact_credentials, :auth_code, :authentication_token, :authorization_result, :backup_plan_tags, :backup_vault_tags, :base_32_string_seed, :body, :bot_configuration, :bot_email, :cause, :client_id, :client_secret, :configuration, :copy_source_sse_customer_key, :credentials, :current_password, :custom_attributes, :db_password, :default_phone_number, :definition, :description, :display_name, :e164_phone_number, :email, :email_address, :email_message, :embed_url, :error, :feedback_token, :file, :first_name, :id, :id_token, :input, :input_text, :key_id, :key_store_password, :kms_key_id, :kms_master_key_id, :lambda_function_arn, :last_name, :local_console_password, :master_account_email, :master_user_password, :message, :name, :new_password, :next_password, :notes, :old_password, :outbound_events_https_endpoint, :output, :owner_information, :parameters, :passphrase, :password, :payload, :phone_number, :plaintext, :previous_password, :primary_email, :primary_provisioned_number, :private_key, :proposed_password, :public_key, :qr_code_png, :query, :recovery_point_tags, :refresh_token, :registrant_contact, :request_attributes, :search_query, :secret_access_key, :secret_binary, :secret_code, :secret_hash, :secret_string, :secret_to_authenticate_initiator, :secret_to_authenticate_target, :security_token, :service_password, :session_attributes, :share_notes, :shared_secret, :slots, :sse_customer_key, :ssekms_key_id, :status_message, :tag_key_list, :tags, :task_parameters, :tech_contact, :temporary_password, :text, :token, :trust_password, :upload_credentials, :upload_url, :user_email, :user_name, :username, :value, :values, :variables, :zip_file]
|
15
15
|
# end
|
16
16
|
|
17
17
|
def initialize(options = {})
|
@@ -22,6 +22,7 @@ module Aws
|
|
22
22
|
ShapeRef.new(shape: shape)
|
23
23
|
end
|
24
24
|
@validate_required = options[:validate_required] != false
|
25
|
+
@input = options[:input].nil? ? true : !!options[:input]
|
25
26
|
end
|
26
27
|
|
27
28
|
# @param [Hash] params
|
@@ -39,6 +40,7 @@ module Aws
|
|
39
40
|
return unless correct_type?(ref, values, errors, context)
|
40
41
|
|
41
42
|
if ref.eventstream
|
43
|
+
# input eventstream is provided from event signals
|
42
44
|
values.each do |value|
|
43
45
|
# each event is structure type
|
44
46
|
case value[:message_type]
|
@@ -58,7 +60,8 @@ module Aws
|
|
58
60
|
# ensure required members are present
|
59
61
|
if @validate_required
|
60
62
|
shape.required.each do |member_name|
|
61
|
-
|
63
|
+
input_eventstream = ref.shape.member(member_name).eventstream && @input
|
64
|
+
if values[member_name].nil? && !input_eventstream
|
62
65
|
param = "#{context}[#{member_name.inspect}]"
|
63
66
|
errors << "missing required parameter #{param}"
|
64
67
|
end
|
@@ -147,6 +150,11 @@ module Aws
|
|
147
150
|
end
|
148
151
|
|
149
152
|
def correct_type?(ref, value, errors, context)
|
153
|
+
if ref.eventstream && @input
|
154
|
+
errors << "instead of providing value directly for eventstreams at input,"\
|
155
|
+
" expected to use #signal events per stream"
|
156
|
+
return false
|
157
|
+
end
|
150
158
|
case value
|
151
159
|
when Hash then true
|
152
160
|
when ref.shape.struct_class then true
|
@@ -109,6 +109,10 @@ all generated client side metrics. Defaults to an empty string.
|
|
109
109
|
context.metadata[:client_metrics] = request_metrics
|
110
110
|
start_time = Aws::Util.monotonic_milliseconds
|
111
111
|
final_error_retryable = false
|
112
|
+
final_aws_exception = nil
|
113
|
+
final_aws_exception_message = nil
|
114
|
+
final_sdk_exception = nil
|
115
|
+
final_sdk_exception_message = nil
|
112
116
|
begin
|
113
117
|
@handler.call(context)
|
114
118
|
rescue StandardError => e
|
@@ -137,14 +141,29 @@ all generated client side metrics. Defaults to an empty string.
|
|
137
141
|
attempt.sdk_exception = e.class.to_s
|
138
142
|
attempt.sdk_exception_msg = e.message
|
139
143
|
end # Else we don't have an SDK exception and are done.
|
144
|
+
final_attempt = request_metrics.api_call_attempts.last
|
145
|
+
final_aws_exception = final_attempt.aws_exception
|
146
|
+
final_aws_exception_message = final_attempt.aws_exception_msg
|
147
|
+
final_sdk_exception = final_attempt.sdk_exception
|
148
|
+
final_sdk_exception_message = final_attempt.sdk_exception_msg
|
140
149
|
raise e
|
141
150
|
ensure
|
142
151
|
end_time = Aws::Util.monotonic_milliseconds
|
143
|
-
|
152
|
+
complete_opts = {
|
144
153
|
latency: end_time - start_time,
|
145
154
|
attempt_count: context.retries + 1,
|
146
|
-
|
147
|
-
|
155
|
+
user_agent: context.http_request.headers["user-agent"],
|
156
|
+
final_error_retryable: final_error_retryable,
|
157
|
+
final_http_status_code: context.http_response.status_code,
|
158
|
+
final_aws_exception: final_aws_exception,
|
159
|
+
final_aws_exception_message: final_aws_exception_message,
|
160
|
+
final_sdk_exception: final_sdk_exception,
|
161
|
+
final_sdk_exception_message: final_sdk_exception_message
|
162
|
+
}
|
163
|
+
if context.metadata[:redirect_region]
|
164
|
+
complete_opts[:region] = context.metadata[:redirect_region]
|
165
|
+
end
|
166
|
+
request_metrics.api_call.complete(complete_opts)
|
148
167
|
# Report the metrics by passing the complete RequestMetrics object
|
149
168
|
if publisher
|
150
169
|
publisher.publish(request_metrics)
|
@@ -7,7 +7,8 @@ module Aws
|
|
7
7
|
def add_handlers(handlers, config)
|
8
8
|
if config.client_side_monitoring && config.client_side_monitoring_port
|
9
9
|
# AttemptHandler comes just before we would retry an error.
|
10
|
-
|
10
|
+
# Or before we would follow redirects.
|
11
|
+
handlers.add(AttemptHandler, step: :sign, priority: 39)
|
11
12
|
# LatencyHandler is as close to sending as possible.
|
12
13
|
handlers.add(LatencyHandler, step: :sign, priority: 0)
|
13
14
|
end
|
@@ -45,6 +46,9 @@ module Aws
|
|
45
46
|
context.metadata[:current_call_attempt] = call_attempt
|
46
47
|
|
47
48
|
resp = @handler.call(context)
|
49
|
+
if context.metadata[:redirect_region]
|
50
|
+
call_attempt.region = context.metadata[:redirect_region]
|
51
|
+
end
|
48
52
|
headers = context.http_response.headers
|
49
53
|
if headers.include?("x-amz-id-2")
|
50
54
|
call_attempt.x_amz_id_2 = headers["x-amz-id-2"]
|
@@ -10,6 +10,20 @@ module Aws
|
|
10
10
|
When an EventStream or Proc object is provided, it will be used as callback for each chunk of event stream response received along the way.
|
11
11
|
DOCS
|
12
12
|
|
13
|
+
option(:input_event_stream_handler,
|
14
|
+
default: nil,
|
15
|
+
doc_type: 'Proc',
|
16
|
+
docstring: <<-DOCS)
|
17
|
+
When an EventStream or Proc object is provided, it can be used for sending events for the event stream.
|
18
|
+
DOCS
|
19
|
+
|
20
|
+
option(:output_event_stream_handler,
|
21
|
+
default: nil,
|
22
|
+
doc_type: 'Proc',
|
23
|
+
docstring: <<-DOCS)
|
24
|
+
When an EventStream or Proc object is provided, it will be used as callback for each chunk of event stream response received along the way.
|
25
|
+
DOCS
|
26
|
+
|
13
27
|
end
|
14
28
|
|
15
29
|
end
|
@@ -0,0 +1,33 @@
|
|
1
|
+
require 'securerandom'
|
2
|
+
|
3
|
+
module Aws
|
4
|
+
module Plugins
|
5
|
+
|
6
|
+
# @api private
|
7
|
+
class InvocationId < Seahorse::Client::Plugin
|
8
|
+
|
9
|
+
# @api private
|
10
|
+
class Handler < Seahorse::Client::Handler
|
11
|
+
|
12
|
+
def call(context)
|
13
|
+
apply_invocation_id(context)
|
14
|
+
@handler.call(context)
|
15
|
+
end
|
16
|
+
|
17
|
+
private
|
18
|
+
|
19
|
+
def apply_invocation_id(context)
|
20
|
+
context.http_request.headers['amz-sdk-invocation-id'] = SecureRandom.uuid
|
21
|
+
if context[:input_event_emitter]
|
22
|
+
# only used for eventstreaming at input
|
23
|
+
context.http_request.headers['x-amz-content-sha256'] = 'STREAMING-AWS4-HMAC-SHA256-EVENTS'
|
24
|
+
end
|
25
|
+
end
|
26
|
+
|
27
|
+
end
|
28
|
+
|
29
|
+
handler(Handler, step: :initialize)
|
30
|
+
|
31
|
+
end
|
32
|
+
end
|
33
|
+
end
|
@@ -78,12 +78,14 @@ A delay randomiser function used by the default backoff function. Some predefine
|
|
78
78
|
'Throttling', # query services
|
79
79
|
'ThrottlingException', # json services
|
80
80
|
'RequestThrottled', # sqs
|
81
|
+
'RequestThrottledException',
|
81
82
|
'ProvisionedThroughputExceededException', # dynamodb
|
82
83
|
'TransactionInProgressException', # dynamodb
|
83
84
|
'RequestLimitExceeded', # ec2
|
84
85
|
'BandwidthLimitExceeded', # cloud search
|
85
86
|
'LimitExceededException', # kinesis
|
86
87
|
'TooManyRequestsException', # batch
|
88
|
+
'PriorRequestNotComplete', # route53
|
87
89
|
])
|
88
90
|
|
89
91
|
CHECKSUM_ERRORS = Set.new([
|
@@ -45,15 +45,18 @@ requests are made, and retries are disabled.
|
|
45
45
|
def call(context)
|
46
46
|
stub = context.client.next_stub(context)
|
47
47
|
resp = Seahorse::Client::Response.new(context: context)
|
48
|
-
|
49
|
-
resp
|
48
|
+
async_mode = context.client.is_a? Seahorse::Client::AsyncBase
|
49
|
+
apply_stub(stub, resp, async_mode)
|
50
|
+
|
51
|
+
async_mode ? Seahorse::Client::AsyncResponse.new(
|
52
|
+
context: context, stream: context[:input_event_stream_handler].event_emitter.stream, sync_queue: Queue.new) : resp
|
50
53
|
end
|
51
54
|
|
52
|
-
def apply_stub(stub, response)
|
55
|
+
def apply_stub(stub, response, async_mode = false)
|
53
56
|
http_resp = response.context.http_response
|
54
57
|
case
|
55
58
|
when stub[:error] then signal_error(stub[:error], http_resp)
|
56
|
-
when stub[:http] then signal_http(stub[:http], http_resp)
|
59
|
+
when stub[:http] then signal_http(stub[:http], http_resp, async_mode)
|
57
60
|
when stub[:data] then response.data = stub[:data]
|
58
61
|
end
|
59
62
|
end
|
@@ -67,9 +70,18 @@ requests are made, and retries are disabled.
|
|
67
70
|
end
|
68
71
|
|
69
72
|
# @param [Seahorse::Client::Http::Response] stub
|
70
|
-
# @param [Seahorse::Client::Http::Response] http_resp
|
71
|
-
|
72
|
-
|
73
|
+
# @param [Seahorse::Client::Http::Response | Seahorse::Client::Http::AsyncResponse] http_resp
|
74
|
+
# @param [Boolean] async_mode
|
75
|
+
def signal_http(stub, http_resp, async_mode = false)
|
76
|
+
if async_mode
|
77
|
+
h2_headers = stub.headers.to_h.inject([]) do |arr, (k, v)|
|
78
|
+
arr << [k, v]
|
79
|
+
end
|
80
|
+
h2_headers << [":status", stub.status_code]
|
81
|
+
http_resp.signal_headers(h2_headers)
|
82
|
+
else
|
83
|
+
http_resp.signal_headers(stub.status_code, stub.headers.to_h)
|
84
|
+
end
|
73
85
|
while chunk = stub.body.read(1024 * 1024)
|
74
86
|
http_resp.signal_data(chunk)
|
75
87
|
end
|
@@ -0,0 +1,53 @@
|
|
1
|
+
module Aws
|
2
|
+
module Plugins
|
3
|
+
|
4
|
+
# For Streaming Input Operations, when `requiresLength` is enabled
|
5
|
+
# checking whether `Content-Length` header can be set,
|
6
|
+
# for `v4-unsigned-body` operations, set `Transfer-Encoding` header
|
7
|
+
class TransferEncoding < Seahorse::Client::Plugin
|
8
|
+
|
9
|
+
# @api private
|
10
|
+
class Handler < Seahorse::Client::Handler
|
11
|
+
|
12
|
+
def call(context)
|
13
|
+
if streaming?(context.operation.input)
|
14
|
+
begin
|
15
|
+
context.http_request.body.size
|
16
|
+
rescue
|
17
|
+
if requires_length?(context.operation.input)
|
18
|
+
# if size of the IO is not available but required
|
19
|
+
raise Aws::Errors::MissingContentLength.new
|
20
|
+
elsif context.operation['authtype'] == "v4-unsigned-body"
|
21
|
+
context.http_request.headers['Transfer-Encoding'] = 'chunked'
|
22
|
+
end
|
23
|
+
end
|
24
|
+
end
|
25
|
+
|
26
|
+
@handler.call(context)
|
27
|
+
end
|
28
|
+
|
29
|
+
private
|
30
|
+
|
31
|
+
def streaming?(ref)
|
32
|
+
if payload = ref[:payload_member]
|
33
|
+
payload["streaming"] || # checking ref and shape
|
34
|
+
payload.shape["streaming"]
|
35
|
+
else
|
36
|
+
false
|
37
|
+
end
|
38
|
+
end
|
39
|
+
|
40
|
+
def requires_length?(ref)
|
41
|
+
payload = ref[:payload_member]
|
42
|
+
payload["requiresLength"] || # checking ref and shape
|
43
|
+
payload.shape["requiresLength"]
|
44
|
+
end
|
45
|
+
|
46
|
+
end
|
47
|
+
|
48
|
+
handler(Handler, step: :sign)
|
49
|
+
|
50
|
+
end
|
51
|
+
|
52
|
+
end
|
53
|
+
end
|
@@ -14,6 +14,8 @@ module Aws
|
|
14
14
|
end
|
15
15
|
|
16
16
|
def set_user_agent(context)
|
17
|
+
execution_env = ENV["AWS_EXECUTION_ENV"]
|
18
|
+
|
17
19
|
ua = "aws-sdk-ruby3/#{CORE_GEM_VERSION}"
|
18
20
|
|
19
21
|
begin
|
@@ -28,6 +30,10 @@ module Aws
|
|
28
30
|
ua += " #{context[:gem_name]}/#{context[:gem_version]}"
|
29
31
|
end
|
30
32
|
|
33
|
+
if execution_env
|
34
|
+
ua += " exec-env/#{execution_env}"
|
35
|
+
end
|
36
|
+
|
31
37
|
ua += " #{context.config.user_agent_suffix}" if context.config.user_agent_suffix
|
32
38
|
|
33
39
|
context.http_request.headers['User-Agent'] = ua.strip
|
@@ -27,6 +27,8 @@ module Aws
|
|
27
27
|
def initialize(process)
|
28
28
|
@process = process
|
29
29
|
@credentials = credentials_from_process(@process)
|
30
|
+
|
31
|
+
super
|
30
32
|
end
|
31
33
|
|
32
34
|
private
|
@@ -38,7 +40,11 @@ module Aws
|
|
38
40
|
end
|
39
41
|
|
40
42
|
if process_status.success?
|
41
|
-
|
43
|
+
begin
|
44
|
+
creds_json = JSON.parse(raw_out)
|
45
|
+
rescue JSON::ParserError
|
46
|
+
raise Errors::InvalidProcessCredentialsPayload.new("Invalid JSON response")
|
47
|
+
end
|
42
48
|
payload_version = creds_json['Version']
|
43
49
|
if payload_version == 1
|
44
50
|
_parse_payload_format_v1(creds_json)
|
@@ -27,7 +27,12 @@ module Aws
|
|
27
27
|
build_request(context)
|
28
28
|
@handler.call(context).on_success do |response|
|
29
29
|
response.error = nil
|
30
|
-
|
30
|
+
parsed = parse_xml(context)
|
31
|
+
if parsed.nil? || parsed == EmptyStructure
|
32
|
+
response.data = EmptyStructure.new
|
33
|
+
else
|
34
|
+
response.data = parsed
|
35
|
+
end
|
31
36
|
end
|
32
37
|
end
|
33
38
|
|
@@ -3,7 +3,7 @@ require 'thread'
|
|
3
3
|
module Aws
|
4
4
|
|
5
5
|
# Base class used credential classes that can be refreshed. This
|
6
|
-
# provides basic refresh logic in a thread-safe
|
6
|
+
# provides basic refresh logic in a thread-safe manner. Classes mixing in
|
7
7
|
# this module are expected to implement a #refresh method that populates
|
8
8
|
# the following instance variables:
|
9
9
|
#
|
@@ -29,8 +29,7 @@ module Aws
|
|
29
29
|
def to_h(obj = self)
|
30
30
|
case obj
|
31
31
|
when Struct
|
32
|
-
obj.
|
33
|
-
value = obj[member]
|
32
|
+
obj.each_pair.with_object({}) do |(member, value), hash|
|
34
33
|
hash[member] = to_hash(value) unless value.nil?
|
35
34
|
end
|
36
35
|
when Hash
|
@@ -45,6 +44,11 @@ module Aws
|
|
45
44
|
end
|
46
45
|
alias to_hash to_h
|
47
46
|
|
47
|
+
# Wraps the default #to_s logic with filtering of sensitive parameters.
|
48
|
+
def to_s(obj = self)
|
49
|
+
Aws::Log::ParamFilter.new.filter(obj).to_s
|
50
|
+
end
|
51
|
+
|
48
52
|
class << self
|
49
53
|
|
50
54
|
# @api private
|
@@ -118,6 +118,25 @@ module Aws
|
|
118
118
|
|
119
119
|
def encode_event(opts, rules, event_data, builder)
|
120
120
|
event_ref = rules.shape.member(event_data.delete(:event_type))
|
121
|
+
explicit_payload = false
|
122
|
+
implicit_payload_members = {}
|
123
|
+
event_ref.shape.members.each do |name, ref|
|
124
|
+
if ref.eventpayload
|
125
|
+
explicit_payload = true
|
126
|
+
else
|
127
|
+
implicit_payload_members[name] = ref
|
128
|
+
end
|
129
|
+
end
|
130
|
+
|
131
|
+
if !explicit_payload && !implicit_payload_members.empty?
|
132
|
+
unless implicit_payload_members.size > 1
|
133
|
+
m_name, _ = implicit_payload_members.first
|
134
|
+
value = {}
|
135
|
+
value[m_name] = event_data[m_name]
|
136
|
+
opts[:payload] = StringIO.new(builder.new(event_ref).serialize(value))
|
137
|
+
end
|
138
|
+
end
|
139
|
+
|
121
140
|
event_data.each do |k, v|
|
122
141
|
member_ref = event_ref.shape.member(k)
|
123
142
|
if member_ref.eventheader
|