Skip to content

Commit 885693b

Browse files
authored
aws: Removed runtime flag use_http_client_to_fetch_aws_credentials (envoyproxy#37513)
Risk Level: Low Testing: Adjusted tests Docs Changes: Release Notes: added Progress towards envoyproxy#11816 Signed-off-by: Greg Greenway <[email protected]>
1 parent d822e8a commit 885693b

File tree

11 files changed

+37
-63
lines changed

11 files changed

+37
-63
lines changed

changelogs/current.yaml

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -171,6 +171,9 @@ removed_config_or_runtime:
171171
- area: upstream
172172
change: |
173173
Removed runtime flag ``envoy.restart_features.allow_client_socket_creation_failure`` and legacy code paths.
174+
- area: aws
175+
change: |
176+
Removed runtime flag ``envoy.reloadable_features.use_http_client_to_fetch_aws_credentials``.
174177
- area: upstream
175178
change: |
176179
Removed runtime flag ``envoy.reloadable_features.exclude_host_in_eds_status_draining``.

source/common/runtime/runtime_features.cc

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -98,7 +98,6 @@ RUNTIME_GUARD(envoy_reloadable_features_uhv_allow_malformed_url_encoding);
9898
RUNTIME_GUARD(envoy_reloadable_features_upstream_remote_address_use_connection);
9999
RUNTIME_GUARD(envoy_reloadable_features_use_config_in_happy_eyeballs);
100100
RUNTIME_GUARD(envoy_reloadable_features_use_filter_manager_state_for_downstream_end_stream);
101-
RUNTIME_GUARD(envoy_reloadable_features_use_http_client_to_fetch_aws_credentials);
102101
RUNTIME_GUARD(envoy_reloadable_features_use_route_host_mutation_for_auto_sni_san);
103102
RUNTIME_GUARD(envoy_reloadable_features_use_typed_metadata_in_proxy_protocol_listener);
104103
RUNTIME_GUARD(envoy_reloadable_features_validate_connect);

source/extensions/common/aws/credentials_provider_impl.cc

Lines changed: 16 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -132,8 +132,15 @@ MetadataCredentialsProviderBase::MetadataCredentialsProviderBase(
132132
cluster_name_(std::string(cluster_name)), cluster_type_(cluster_type), uri_(std::string(uri)),
133133
cache_duration_(getCacheDuration()), refresh_state_(refresh_state),
134134
initialization_timer_(initialization_timer), debug_name_(cluster_name) {
135+
136+
// Most code sets the context and uses the async http client, except for one extension
137+
// which is scheduled to be deprecated and deleted. Modes can no longer be switched via runtime,
138+
// so each caller should only pass parameters to support a single mode.
139+
// https://github.com/envoyproxy/envoy/issues/36910
140+
ASSERT((context.has_value() ^ (fetch_metadata_using_curl != nullptr)));
141+
135142
// Async provider cluster setup
136-
if (useHttpAsyncClient() && context_) {
143+
if (context_) {
137144
// Set up metadata credentials statistics
138145
scope_ = api.rootScope().createScope(
139146
fmt::format("aws.metadata_credentials_provider.{}.", cluster_name_));
@@ -249,7 +256,7 @@ void MetadataCredentialsProviderBase::ThreadLocalCredentialsCache::onClusterRemo
249256

250257
// Async provider uses its own refresh mechanism. Calling refreshIfNeeded() here is not thread safe.
251258
Credentials MetadataCredentialsProviderBase::getCredentials() {
252-
if (useHttpAsyncClient()) {
259+
if (context_) {
253260
if (tls_slot_) {
254261
return *(*tls_slot_)->credentials_.get();
255262
} else {
@@ -269,7 +276,7 @@ std::chrono::seconds MetadataCredentialsProviderBase::getCacheDuration() {
269276
}
270277

271278
void MetadataCredentialsProviderBase::handleFetchDone() {
272-
if (useHttpAsyncClient() && context_) {
279+
if (context_) {
273280
if (cache_duration_timer_ && !cache_duration_timer_->enabled()) {
274281
// Receiver state handles the initial credential refresh scenario. If for some reason we are
275282
// unable to perform credential refresh after cluster initialization has completed, we use a
@@ -317,11 +324,6 @@ void MetadataCredentialsProviderBase::setCredentialsToAllThreads(
317324
}
318325
}
319326

320-
bool MetadataCredentialsProviderBase::useHttpAsyncClient() {
321-
return Runtime::runtimeFeatureEnabled(
322-
"envoy.reloadable_features.use_http_client_to_fetch_aws_credentials");
323-
}
324-
325327
bool CredentialsFileCredentialsProvider::needsRefresh() {
326328
return api_.timeSource().systemTime() - last_updated_ > REFRESH_INTERVAL;
327329
}
@@ -403,7 +405,7 @@ void InstanceProfileCredentialsProvider::refresh() {
403405
token_req_message.headers().setCopy(Http::LowerCaseString(EC2_IMDS_TOKEN_TTL_HEADER),
404406
EC2_IMDS_TOKEN_TTL_DEFAULT_VALUE);
405407

406-
if (!useHttpAsyncClient() || !context_) {
408+
if (!context_) {
407409
// Using curl to fetch the AWS credentials where we first get the token.
408410
const auto token_string = fetch_metadata_using_curl_(token_req_message);
409411
if (token_string) {
@@ -555,7 +557,7 @@ void InstanceProfileCredentialsProvider::extractCredentials(
555557
session_token.empty() ? "" : "*****");
556558

557559
last_updated_ = api_.timeSource().systemTime();
558-
if (useHttpAsyncClient() && context_) {
560+
if (context_) {
559561
setCredentialsToAllThreads(
560562
std::make_unique<Credentials>(access_key_id, secret_access_key, session_token));
561563
stats_->credential_refreshes_succeeded_.inc();
@@ -642,7 +644,7 @@ void ContainerCredentialsProvider::refresh() {
642644
message.headers().setHost(host);
643645
message.headers().setPath(path);
644646
message.headers().setCopy(Http::CustomHeaders::get().Authorization, authorization_header);
645-
if (!useHttpAsyncClient() || !context_) {
647+
if (!context_) {
646648
// Using curl to fetch the AWS credentials.
647649
const auto credential_document = fetch_metadata_using_curl_(message);
648650
if (!credential_document) {
@@ -708,7 +710,7 @@ void ContainerCredentialsProvider::extractCredentials(
708710
}
709711

710712
last_updated_ = api_.timeSource().systemTime();
711-
if (useHttpAsyncClient() && context_) {
713+
if (context_) {
712714
setCredentialsToAllThreads(
713715
std::make_unique<Credentials>(access_key_id, secret_access_key, session_token));
714716
ENVOY_LOG(debug, "Metadata receiver {} moving to Ready state", cluster_name_);
@@ -760,12 +762,6 @@ bool WebIdentityCredentialsProvider::needsRefresh() {
760762
}
761763

762764
void WebIdentityCredentialsProvider::refresh() {
763-
// If http async client is not enabled then just set empty credentials and return.
764-
if (!useHttpAsyncClient()) {
765-
cached_credentials_ = Credentials();
766-
return;
767-
}
768-
769765
ENVOY_LOG(debug, "Getting AWS web identity credentials from STS: {}", sts_endpoint_);
770766

771767
std::string identity_token = token_;
@@ -1085,9 +1081,8 @@ absl::StatusOr<CredentialsProviderSharedPtr> createCredentialsProviderFromConfig
10851081
// This "two seconds" is a bit arbitrary, but matches the other places in the codebase.
10861082
const auto initialization_timer = std::chrono::seconds(2);
10871083
return std::make_shared<WebIdentityCredentialsProvider>(
1088-
context.api(), context, Extensions::Common::Aws::Utility::fetchMetadata,
1089-
MetadataFetcher::create, "", token, sts_endpoint, role_arn, role_session_name,
1090-
refresh_state, initialization_timer, cluster_name);
1084+
context.api(), context, nullptr, MetadataFetcher::create, "", token, sts_endpoint, role_arn,
1085+
role_session_name, refresh_state, initialization_timer, cluster_name);
10911086
} else {
10921087
return absl::InvalidArgumentError("No AWS credential provider specified");
10931088
}

source/extensions/common/aws/credentials_provider_impl.h

Lines changed: 0 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -190,10 +190,6 @@ class MetadataCredentialsProviderBase : public CachedCredentialsProviderBase {
190190
// Set Credentials shared_ptr on all threads.
191191
void setCredentialsToAllThreads(CredentialsConstUniquePtr&& creds);
192192

193-
// Returns true if http async client can be used instead of libcurl to fetch the aws credentials,
194-
// else false.
195-
bool useHttpAsyncClient();
196-
197193
Api::Api& api_;
198194
// The optional server factory context.
199195
ServerFactoryContextOptRef context_;

source/extensions/common/aws/utility.cc

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -331,7 +331,7 @@ static size_t curlCallback(char* ptr, size_t, size_t nmemb, void* data) {
331331
return nmemb;
332332
}
333333

334-
absl::optional<std::string> Utility::fetchMetadata(Http::RequestMessage& message) {
334+
absl::optional<std::string> Utility::fetchMetadataWithCurl(Http::RequestMessage& message) {
335335
static const size_t MAX_RETRIES = 4;
336336
static const std::chrono::milliseconds RETRY_DELAY{1000};
337337
static const std::chrono::seconds TIMEOUT{5};

source/extensions/common/aws/utility.h

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -92,7 +92,7 @@ class Utility {
9292
static std::string getSTSEndpoint(absl::string_view region);
9393

9494
/**
95-
* Fetch AWS instance or task metadata.
95+
* Fetch AWS instance or task metadata with curl.
9696
*
9797
* @param message An HTTP request.
9898
* @return Metadata document or nullopt in case if unable to fetch it.
@@ -102,7 +102,7 @@ class Utility {
102102
* @note This is not main loop safe method as it is blocking. It is intended to be used from the
103103
* gRPC auth plugins that are able to schedule blocking plugins on a different thread.
104104
*/
105-
static absl::optional<std::string> fetchMetadata(Http::RequestMessage& message);
105+
static absl::optional<std::string> fetchMetadataWithCurl(Http::RequestMessage& message);
106106

107107
/**
108108
* @brief Creates the prototype for a static cluster towards a credentials provider

source/extensions/filters/http/aws_lambda/config.cc

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -60,7 +60,7 @@ AwsLambdaFilterFactory::getCredentialsProvider(
6060
}
6161
return std::make_shared<Extensions::Common::Aws::DefaultCredentialsProviderChain>(
6262
server_context.api(), makeOptRef(server_context), server_context.singletonManager(), region,
63-
Extensions::Common::Aws::Utility::fetchMetadata);
63+
nullptr);
6464
}
6565

6666
absl::StatusOr<Http::FilterFactoryCb> AwsLambdaFilterFactory::createFilterFactoryFromProtoTyped(

source/extensions/filters/http/aws_request_signing/config.cc

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -67,8 +67,7 @@ AwsRequestSigningFilterFactory::createFilterFactoryFromProtoTyped(
6767
server_context, region, config.credential_provider())
6868
: std::make_shared<Extensions::Common::Aws::DefaultCredentialsProviderChain>(
6969
server_context.api(), makeOptRef(server_context),
70-
server_context.singletonManager(), region,
71-
Extensions::Common::Aws::Utility::fetchMetadata);
70+
server_context.singletonManager(), region, nullptr);
7271
if (!credentials_provider.ok()) {
7372
return credentials_provider.status();
7473
}
@@ -137,7 +136,7 @@ AwsRequestSigningFilterFactory::createRouteSpecificFilterConfigTyped(
137136
context, region, per_route_config.aws_request_signing().credential_provider())
138137
: std::make_shared<Extensions::Common::Aws::DefaultCredentialsProviderChain>(
139138
context.api(), makeOptRef(context), context.singletonManager(), region,
140-
Extensions::Common::Aws::Utility::fetchMetadata);
139+
nullptr);
141140
if (!credentials_provider.ok()) {
142141
throw EnvoyException(std::string(credentials_provider.status().message()));
143142
}

source/extensions/grpc_credentials/aws_iam/config.cc

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -69,7 +69,7 @@ std::shared_ptr<grpc::ChannelCredentials> AwsIamGrpcCredentialsFactory::getChann
6969

7070
auto credentials_provider = std::make_shared<Common::Aws::DefaultCredentialsProviderChain>(
7171
context.api(), absl::nullopt /*Empty factory context*/, context.singletonManager(),
72-
region, Common::Aws::Utility::fetchMetadata);
72+
region, Common::Aws::Utility::fetchMetadataWithCurl);
7373
auto signer = std::make_unique<Common::Aws::SigV4SignerImpl>(
7474
config.service_name(), region, credentials_provider, context,
7575
// TODO: extend API to allow specifying header exclusion. ref:

test/extensions/common/aws/aws_metadata_fetcher_integration_test.cc

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -102,7 +102,7 @@ TEST_F(AwsMetadataIntegrationTestSuccess, Success) {
102102
auto headers = Http::RequestHeaderMapPtr{new Http::TestRequestHeaderMapImpl{
103103
{":path", "/"}, {":authority", authority}, {":scheme", "http"}, {":method", "GET"}}};
104104
Http::RequestMessageImpl message(std::move(headers));
105-
const auto response = Utility::fetchMetadata(message);
105+
const auto response = Utility::fetchMetadataWithCurl(message);
106106

107107
ASSERT_TRUE(response.has_value());
108108
EXPECT_EQ("METADATA_VALUE", *response);
@@ -121,7 +121,7 @@ TEST_F(AwsMetadataIntegrationTestSuccess, AuthToken) {
121121
{":method", "GET"},
122122
{"authorization", "AUTH_TOKEN"}}};
123123
Http::RequestMessageImpl message(std::move(headers));
124-
const auto response = Utility::fetchMetadata(message);
124+
const auto response = Utility::fetchMetadataWithCurl(message);
125125

126126
ASSERT_TRUE(response.has_value());
127127
EXPECT_EQ("METADATA_VALUE_WITH_AUTH", *response);
@@ -140,7 +140,7 @@ TEST_F(AwsMetadataIntegrationTestSuccess, FetchTokenHttpPut) {
140140
{":method", "PUT"},
141141
{"X-aws-ec2-metadata-token-ttl-seconds", "21600"}}};
142142
Http::RequestMessageImpl message(std::move(headers));
143-
const auto response = Utility::fetchMetadata(message);
143+
const auto response = Utility::fetchMetadataWithCurl(message);
144144

145145
ASSERT_TRUE(response.has_value());
146146
EXPECT_EQ("TOKEN_VALUE", *response);
@@ -161,7 +161,7 @@ TEST_F(AwsMetadataIntegrationTestSuccess, Redirect) {
161161
{":method", "GET"},
162162
{"authorization", "AUTH_TOKEN"}}};
163163
Http::RequestMessageImpl message(std::move(headers));
164-
const auto response = Utility::fetchMetadata(message);
164+
const auto response = Utility::fetchMetadataWithCurl(message);
165165

166166
ASSERT_TRUE(response.has_value());
167167
EXPECT_EQ("METADATA_VALUE_WITH_AUTH", *response);
@@ -191,7 +191,7 @@ TEST_F(AwsMetadataIntegrationTestFailure, Failure) {
191191

192192
Http::RequestMessageImpl message(std::move(headers));
193193
const auto start_time = timeSystem().monotonicTime();
194-
const auto response = Utility::fetchMetadata(message);
194+
const auto response = Utility::fetchMetadataWithCurl(message);
195195
const auto end_time = timeSystem().monotonicTime();
196196

197197
EXPECT_FALSE(response.has_value());
@@ -218,7 +218,7 @@ TEST_F(AwsMetadataIntegrationTestTimeout, Timeout) {
218218
Http::RequestMessageImpl message(std::move(headers));
219219

220220
const auto start_time = timeSystem().monotonicTime();
221-
const auto response = Utility::fetchMetadata(message);
221+
const auto response = Utility::fetchMetadataWithCurl(message);
222222
const auto end_time = timeSystem().monotonicTime();
223223

224224
EXPECT_FALSE(response.has_value());

0 commit comments

Comments
 (0)