Repository navigation
Conversation
9649266 to
714da31
Compare
|
|
||
| namespace | ||
| { | ||
| // Error names the core error mapper classifies as retryable only since Retry Behavior 2.1. |
There was a problem hiding this comment.
This list has to stay in sync with the names CoreErrorsMapper registers in CoreErrors.cpp, and nothing ties the two together. If someone adds a new throttling name there later, legacy mode starts retrying it and nobody notices. Could we keep the list in one place, in a header next to the mapper that we don't install, and use it both to register the entries and here?
There was a problem hiding this comment.
Done in 5ad7a0b. The names now live in one place, internal/RetryErrorClassification.h, which is excluded from install.
CoreErrors.cppregisters the entries from that list, and the check that uses it (IsStandardOnlyRetryableError) lives next to the mapper.DefaultRetryStrategycalls that check instead of keeping its own list.
| // Gate is off: ignore service-specific tuning, use default behavior | ||
| return InitRetryStrategy(retryMode); | ||
| // Legacy mode ignores service-specific tuning. | ||
| return CreateRetryStrategy(ResolveConfiguredMaxAttempts(profileName), retryMode); |
There was a problem hiding this comment.
Legacy ignores max attempts, so this resolves a value only for CreateRetryStrategy to throw it away. Same thing as the -1 on #3849: I'd rather not carry that sentinel through more call paths. Can this just build the DefaultRetryStrategy directly?
There was a problem hiding this comment.
Legacy now builds DefaultRetryStrategy directly, before any max-attempts resolution.
The options path doesn't use the sentinel either: InitRetryStrategyOptions::maxAttempts defaults to 3. The only -1 handling left is in the existing public InitRetryStrategy(int maxRetries, Aws::String retryMode) overload, which behaves as before.
| */ | ||
| AdaptiveRetryStrategy(long maxAttempts = 3); | ||
| AdaptiveRetryStrategy(std::shared_ptr<RetryQuotaContainer> retryQuotaContainer, long maxAttempts = 3); | ||
| AdaptiveRetryStrategy(long maxAttempts, double transientBackoffBaseSec); |
There was a problem hiding this comment.
We already pushed back on a constructor just for the backoff base on #3836 (#3836 (comment)), and now Standard and Adaptive each have three constructors that do almost the same thing. Can we do what we did with QuotaConfig: one options struct on StandardRetryStrategy, the same one taken by Adaptive, with the existing constructors calling it?
struct StandardRetryStrategyOptions {
long maxAttempts = 3;
double transientBackoffBaseSec = 0.05;
std::shared_ptr<RetryQuotaContainer> retryQuotaContainer;
};
explicit StandardRetryStrategy(const StandardRetryStrategyOptions& options);There was a problem hiding this comment.
Added StandardRetryStrategyOptions as suggested, with
explicit StandardRetryStrategy(const StandardRetryStrategyOptions&).
- The existing Standard constructors now delegate to it. I kept
(long, double)since it already shipped in [Feature] New retries codegen changes #3849. - Adaptive takes the same struct instead of the backoff-only constructor, which is removed. Its other constructors go through Standard's.
One side effect: a null retryQuotaContainer now gets the default container instead of being stored as null.
| AWS_CORE_API std::shared_ptr<RetryStrategy> InitRetryStrategy(Aws::String retryMode = ""); | ||
| AWS_CORE_API std::shared_ptr<RetryStrategy> InitRetryStrategy(int maxRetries, Aws::String retryMode = ""); | ||
| AWS_CORE_API std::shared_ptr<RetryStrategy> InitRetryStrategy(int maxRetries, Aws::String retryMode, double transientBackoffBaseSec); | ||
| AWS_CORE_API std::shared_ptr<RetryStrategy> InitRetryStrategy(int maxRetries, Aws::String retryMode, double transientBackoffBaseSec, |
There was a problem hiding this comment.
Same thing here: this is the fourth InitRetryStrategy overload, and each one adds a parameter to the last. Reading from the named profile is the right fix, but I'd rather this took one options struct (max attempts, retry mode, backoff base, profile name) than another overload.
| int m_retryQuota; | ||
| }; | ||
|
|
||
| namespace Internal |
There was a problem hiding this comment.
This header was supposed to be internal to the build (#3836 (comment)), but it's installed with everything else in include/aws/core/internal/. Nothing outside core should include it, so let's just stop installing it. Everything that includes it in this PR is a core .cpp file, so nothing breaks.
|
|
||
| namespace Internal | ||
| { | ||
| AWS_CORE_LOCAL bool UsesRetryBehavior21(const RetryStrategy* retryStrategy); |
There was a problem hiding this comment.
UsesRetryBehavior21 is named after a spec version, which stops meaning anything once this is the default. All it checks is whether the strategy is DefaultRetryStrategy, so I'd name it for that, something like IsLegacyRetryStrategy, and rename m_enableNewRetries to match, since "new" goes stale the same way.
| void SetLegacyClientConfiguration(Aws::Client::ClientConfiguration& clientConfig) | ||
| { | ||
| clientConfig.retryStrategy = Aws::Client::InitRetryStrategy("default"); | ||
| // Leave the retry strategy unset so the client configuration factory resolves it. |
There was a problem hiding this comment.
retryStrategy is already null here, so this line and the comment can go, same as the other modes. That also cleans up the generated ClientConfigurationDefaults.cpp. Same for the empty retryMode branch below: flip the condition to != instead of leaving a comment in it.
| { | ||
| bool UsesRetryBehavior21(const RetryStrategy* retryStrategy) | ||
| { | ||
| // DefaultRetryStrategy is the legacy retry behavior, so it keeps the request handling from before Retry Behavior 2.1. |
There was a problem hiding this comment.
Same as on #3836, please drop the narration comments. This one, the two in DefaultRetryStrategy.cpp, the one in ResolveRetryMode, and the one on the legacy branch of InitRetryStrategy just restate what the code does.
| AWSError<CoreErrors> nonRetryableError(CoreErrors::INCOMPLETE_SIGNATURE, false); | ||
|
|
||
| MockStandardRetryStrategy retryStrategy; | ||
| MockStandardRetryStrategy retryStrategy(Aws::MakeShared<DefaultRetryQuotaContainer>(ALLOCATION_TAG)); |
There was a problem hiding this comment.
This now injects the old DefaultRetryQuotaContainer so the old numbers still pass, which means it tests a setup nobody gets by default anymore. The real standard behavior is already covered in NewRetriesStrategyTest. Can we rewrite this against the default container and merge the two, since "new retries" is just the standard strategy now?
| return mapping->second; | ||
| } | ||
|
|
||
| static std::shared_ptr<RetryStrategy> InitRetryStrategyForProfile(const Aws::String& profileName); |
There was a problem hiding this comment.
nit: same as on #3836, I'd rather these new helpers go in an anonymous namespace above the constructors than be static with a forward declaration.
Makes Retry Behavior 2.1 the default retry behavior and removes the
AWS_NEW_RETRIES_2026opt-in.ClientConfiguration(true)or a profile. These configurations now leaveretryStrategyunset, and the client resolves it when it is created.AWS_RETRY_MODE=legacy/retry_mode = legacy(ordefault) keeps the previousDefaultRetryStrategybehavior unchanged.DefaultRetryStrategyalso keeps that behavior when set directly.retry_modeandmax_attemptsare read from the named profile ofClientConfiguration(profileName).AWS_MAX_ATTEMPTS/max_attemptsstill take precedence.amz-sdk-request, long-polling backoff).AdaptiveRetryStrategy(long maxAttempts, double transientBackoffBaseSec)andInitRetryStrategy(int maxRetries, Aws::String retryMode, double transientBackoffBaseSec, const Aws::String& profileName).Check all that applies:
Check which platforms you have built SDK on to verify the correctness of this PR.
By submitting this pull request, I confirm that you can use, modify, copy, and redistribute this contribution, under the terms of your choice.