-
Notifications
You must be signed in to change notification settings - Fork 1.2k
Description
Describe the feature
I'd suggest that the Aws::InstanceProfileCredentials class would provide a configurable option to shorten "no refresh time" (currently implemented with the @no_refresh_until instance variable).
aws-sdk-ruby/gems/aws-sdk-core/lib/aws-sdk-core/instance_profile_credentials.rb
Lines 173 to 177 in 06e3e15
| def refresh | |
| if @no_refresh_until && @no_refresh_until > Time.now | |
| warn_expired_credentials | |
| return | |
| end |
Use Case
I'm using a single instance of Aws::InstanceProfileCredentials to communicate S3 in a Rails app, e.g.,
# config/initializers/aws.rb
Rails.configuration.x.aws.credentials = Aws::InstanceProfileCredentials.new
Rails.configuration.x.aws.s3_client = Aws::S3::Client.new(
credentials: Rails.configuration.x.aws.credentials
)In my deployment environment, an IMDS service (i.e., http://169.254.169.254) sometimes returns 503 Service Unavailable for some reason.
Once the error is raised, requests to S3 fail with 401 Unauthorized error within about 5 minutes (as Aws::InstanceProfileCredentials implements), since stale credentials are used for the S3 API. These 5-minute failures with S3 downgrade my service quality.
aws-sdk-ruby/gems/aws-sdk-core/lib/aws-sdk-core/instance_profile_credentials.rb
Lines 192 to 194 in 06e3e15
| # credentials are already set, but there was an error getting new credentials | |
| # so don't update the credentials and use stale ones (static stability) | |
| @no_refresh_until = Time.now + rand(300..360) |
To help understand my issue, let me share a few screenshots of APM that I'm using for the app:
Proposed Solution
Although there might be some approaches, I currently have the following idea to provide a new option, such as a :refresh_back Proc object:
class Aws::InstanceProfileCredentials
def initialize(options = {})
# ...
@refresh_backoff = options[:refresh_backoff] || (-> { Time.now + rand(300..360) })
@no_refresh_until = nil
# ...
end
def set_refresh_interval
@no_refresh_until = @refresh_backoff.call
end
endAdditionally, we would need to change the message in the #warn_expired_credentials method to fit the new option:
aws-sdk-ruby/gems/aws-sdk-core/lib/aws-sdk-core/instance_profile_credentials.rb
Lines 319 to 322 in 06e3e15
| def warn_expired_credentials | |
| warn('Attempting credential expiration extension due to a credential service availability issue. '\ | |
| 'A refresh of these credentials will be attempted again in 5 minutes.') | |
| end |
Furthermore, it might be more helpful if this warn (i.e., Kernel#warn) were used with any specific logger object (it'd be optional, though). Since Kernel#warn outputs messages to STDOUT, they're often hard to find. For example:
def warn_expired_credentials
logger.warn("...")
endOther Information
This issue might be related to:
Acknowledgements
- I may be able to implement this feature request
- This feature might incur a breaking change
SDK version used
aws-sdk-core 3.233.0
Environment details (OS name and version, etc.)
- OS: Linux
- Ruby: 3.4.6 (CRuby)

