aws_types/
sdk_config.rs

1/*
2 * Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved.
3 * SPDX-License-Identifier: Apache-2.0
4 */
5
6#![deny(missing_docs)]
7
8//! AWS Shared Config
9//!
10//! This module contains a shared configuration representation that is agnostic from a specific service.
11
12use crate::app_name::AppName;
13use crate::docs_for;
14use crate::endpoint_config::AccountIdEndpointMode;
15use crate::origin::Origin;
16use crate::region::{Region, SigningRegionSet};
17use crate::service_config::LoadServiceConfig;
18use aws_credential_types::provider::token::SharedTokenProvider;
19pub use aws_credential_types::provider::SharedCredentialsProvider;
20use aws_smithy_async::rt::sleep::AsyncSleep;
21pub use aws_smithy_async::rt::sleep::SharedAsyncSleep;
22pub use aws_smithy_async::time::{SharedTimeSource, TimeSource};
23use aws_smithy_runtime_api::client::auth::AuthSchemePreference;
24use aws_smithy_runtime_api::client::behavior_version::BehaviorVersion;
25use aws_smithy_runtime_api::client::http::HttpClient;
26pub use aws_smithy_runtime_api::client::http::SharedHttpClient;
27use aws_smithy_runtime_api::client::identity::{ResolveCachedIdentity, SharedIdentityCache};
28pub use aws_smithy_runtime_api::client::stalled_stream_protection::StalledStreamProtectionConfig;
29use aws_smithy_runtime_api::shared::IntoShared;
30use aws_smithy_schema::protocol::SharedClientProtocol;
31pub use aws_smithy_types::checksum_config::{
32    RequestChecksumCalculation, ResponseChecksumValidation,
33};
34pub use aws_smithy_types::retry::RetryConfig;
35pub use aws_smithy_types::timeout::TimeoutConfig;
36use std::collections::HashMap;
37use std::sync::Arc;
38
39/// Unified docstrings to keep crates in sync. Not intended for public use
40pub mod unified_docs {
41    /// A macro that generates docs for selected fields of `SdkConfig`.
42    #[macro_export]
43    macro_rules! docs_for {
44        (use_fips) => {
45"When true, send this request to the FIPS-compliant regional endpoint.
46
47If no FIPS-compliant endpoint can be determined, dispatching the request will return an error."
48        };
49        (use_dual_stack) => {
50"When true, send this request to the dual-stack endpoint.
51
52If no dual-stack endpoint is available the request MAY return an error.
53
54**Note**: Some services do not offer dual-stack as a configurable parameter (e.g. Code Catalyst). For
55these services, this setting has no effect"
56        };
57        (time_source) => {
58"The time source use to use for this client.
59
60This only needs to be required for creating deterministic tests or platforms where `SystemTime::now()` is not supported."};
61        (disable_request_compression) => {
62"When `true`, disable request compression. Defaults to `false`.
63
64**Only some services support request compression.** For services
65that don't support request compression, this setting does nothing.
66" };
67        (request_min_compression_size_bytes) => {
68"The minimum size of request that should be compressed. Defaults to `10240` bytes.
69
70When a request body's size is lower than this, request compression will be skipped.
71This is useful for request bodies because, for small request bodies, compression may actually increase their size.
72
73**Only some services support request compression.** For services
74that don't support request compression, this setting does nothing.
75" };
76        (account_id_endpoint_mode) => {
77"Controls the account ID-based routing behavior.
78
79By default, the routing behavior is set to `preferred`.
80Customers can adjust this setting to other values to switch between different routing patterns or temporarily disable the feature.
81
82See the developer guide on [account-based endpoints](https://docs.aws.amazon.com/sdkref/latest/guide/feature-account-endpoints.html)
83for more information.
84
85For services that do not use the account-based endpoints, this setting does nothing.
86" };
87        (auth_scheme_preference) => {
88"Set the auth scheme preference for an auth scheme resolver
89(typically the default auth scheme resolver).
90
91Each operation has a predefined order of auth schemes, as determined by the service,
92for auth scheme resolution. By using the auth scheme preference, customers
93can reorder the schemes resolved by the auth scheme resolver.
94
95The preference list is intended as a hint rather than a strict override.
96Any schemes not present in the originally resolved auth schemes will be ignored.
97" };
98        (sigv4a_signing_region_set) => {
99"Set the signing region set for SigV4a authentication.
100
101When using SigV4a (asymmetric) signing, this specifies which regions the request
102signature is valid for. Use `*` for a universal signature valid in all regions.
103" };
104    }
105}
106
107/// AWS Shared Configuration
108#[derive(Debug, Clone)]
109pub struct SdkConfig {
110    app_name: Option<AppName>,
111    auth_scheme_preference: Option<AuthSchemePreference>,
112    sigv4a_signing_region_set: Option<SigningRegionSet>,
113    identity_cache: Option<SharedIdentityCache>,
114    credentials_provider: Option<SharedCredentialsProvider>,
115    token_provider: Option<SharedTokenProvider>,
116    region: Option<Region>,
117    account_id_endpoint_mode: Option<AccountIdEndpointMode>,
118    endpoint_url: Option<String>,
119    retry_config: Option<RetryConfig>,
120    sleep_impl: Option<SharedAsyncSleep>,
121    time_source: Option<SharedTimeSource>,
122    timeout_config: Option<TimeoutConfig>,
123    stalled_stream_protection_config: Option<StalledStreamProtectionConfig>,
124    http_client: Option<SharedHttpClient>,
125    use_fips: Option<bool>,
126    use_dual_stack: Option<bool>,
127    behavior_version: Option<BehaviorVersion>,
128    service_config: Option<Arc<dyn LoadServiceConfig>>,
129    config_origins: HashMap<&'static str, Origin>,
130    disable_request_compression: Option<bool>,
131    request_min_compression_size_bytes: Option<u32>,
132    request_checksum_calculation: Option<RequestChecksumCalculation>,
133    response_checksum_validation: Option<ResponseChecksumValidation>,
134    protocol: Option<SharedClientProtocol>,
135}
136
137/// Builder for AWS Shared Configuration
138///
139/// _Important:_ Using the `aws-config` crate to configure the SDK is preferred to invoking this
140/// builder directly. Using this builder directly won't pull in any AWS recommended default
141/// configuration values.
142#[derive(Debug, Default)]
143pub struct Builder {
144    app_name: Option<AppName>,
145    auth_scheme_preference: Option<AuthSchemePreference>,
146    sigv4a_signing_region_set: Option<SigningRegionSet>,
147    identity_cache: Option<SharedIdentityCache>,
148    credentials_provider: Option<SharedCredentialsProvider>,
149    token_provider: Option<SharedTokenProvider>,
150    region: Option<Region>,
151    account_id_endpoint_mode: Option<AccountIdEndpointMode>,
152    endpoint_url: Option<String>,
153    retry_config: Option<RetryConfig>,
154    sleep_impl: Option<SharedAsyncSleep>,
155    time_source: Option<SharedTimeSource>,
156    timeout_config: Option<TimeoutConfig>,
157    stalled_stream_protection_config: Option<StalledStreamProtectionConfig>,
158    http_client: Option<SharedHttpClient>,
159    use_fips: Option<bool>,
160    use_dual_stack: Option<bool>,
161    behavior_version: Option<BehaviorVersion>,
162    service_config: Option<Arc<dyn LoadServiceConfig>>,
163    config_origins: HashMap<&'static str, Origin>,
164    disable_request_compression: Option<bool>,
165    request_min_compression_size_bytes: Option<u32>,
166    request_checksum_calculation: Option<RequestChecksumCalculation>,
167    response_checksum_validation: Option<ResponseChecksumValidation>,
168    protocol: Option<SharedClientProtocol>,
169}
170
171impl Builder {
172    /// Set the region for the builder
173    ///
174    /// # Examples
175    /// ```rust
176    /// use aws_types::SdkConfig;
177    /// use aws_types::region::Region;
178    /// let config = SdkConfig::builder().region(Region::new("us-east-1")).build();
179    /// ```
180    pub fn region(mut self, region: impl Into<Option<Region>>) -> Self {
181        self.set_region(region);
182        self
183    }
184
185    /// Set the region for the builder
186    ///
187    /// # Examples
188    /// ```rust
189    /// fn region_override() -> Option<Region> {
190    ///     // ...
191    ///     # None
192    /// }
193    /// use aws_types::SdkConfig;
194    /// use aws_types::region::Region;
195    /// let mut builder = SdkConfig::builder();
196    /// if let Some(region) = region_override() {
197    ///     builder.set_region(region);
198    /// }
199    /// let config = builder.build();
200    /// ```
201    pub fn set_region(&mut self, region: impl Into<Option<Region>>) -> &mut Self {
202        self.region = region.into();
203        self
204    }
205
206    #[doc = docs_for!(account_id_endpoint_mode)]
207    pub fn account_id_endpoint_mode(
208        mut self,
209        account_id_endpoint_mode: AccountIdEndpointMode,
210    ) -> Self {
211        self.set_account_id_endpoint_mode(Some(account_id_endpoint_mode));
212        self
213    }
214
215    #[doc = docs_for!(account_id_endpoint_mode)]
216    pub fn set_account_id_endpoint_mode(
217        &mut self,
218        account_id_endpoint_mode: Option<AccountIdEndpointMode>,
219    ) -> &mut Self {
220        self.account_id_endpoint_mode = account_id_endpoint_mode;
221        self
222    }
223
224    /// Set the endpoint URL to use when making requests.
225    /// # Examples
226    /// ```
227    /// use aws_types::SdkConfig;
228    /// let config = SdkConfig::builder().endpoint_url("http://localhost:8080").build();
229    /// ```
230    pub fn endpoint_url(mut self, endpoint_url: impl Into<String>) -> Self {
231        self.set_endpoint_url(Some(endpoint_url.into()));
232        self
233    }
234
235    /// Set the endpoint URL to use when making requests.
236    pub fn set_endpoint_url(&mut self, endpoint_url: Option<String>) -> &mut Self {
237        self.endpoint_url = endpoint_url;
238        self
239    }
240
241    /// Set the checksum calculation strategy to use when making requests.
242    /// # Examples
243    /// ```
244    /// use aws_types::SdkConfig;
245    /// use aws_smithy_types::checksum_config::RequestChecksumCalculation;
246    /// let config = SdkConfig::builder().request_checksum_calculation(RequestChecksumCalculation::WhenSupported).build();
247    /// ```
248    pub fn request_checksum_calculation(
249        mut self,
250        request_checksum_calculation: RequestChecksumCalculation,
251    ) -> Self {
252        self.set_request_checksum_calculation(Some(request_checksum_calculation));
253        self
254    }
255
256    /// Set the checksum calculation strategy to use when making requests.
257    pub fn set_request_checksum_calculation(
258        &mut self,
259        request_checksum_calculation: Option<RequestChecksumCalculation>,
260    ) -> &mut Self {
261        self.request_checksum_calculation = request_checksum_calculation;
262        self
263    }
264
265    /// Set the checksum calculation strategy to use for responses.
266    /// # Examples
267    /// ```
268    /// use aws_types::SdkConfig;
269    /// use aws_smithy_types::checksum_config::ResponseChecksumValidation;
270    /// let config = SdkConfig::builder().response_checksum_validation(ResponseChecksumValidation::WhenSupported).build();
271    /// ```
272    pub fn response_checksum_validation(
273        mut self,
274        response_checksum_validation: ResponseChecksumValidation,
275    ) -> Self {
276        self.set_response_checksum_validation(Some(response_checksum_validation));
277        self
278    }
279
280    /// Set the checksum calculation strategy to use for responses.
281    pub fn set_response_checksum_validation(
282        &mut self,
283        response_checksum_validation: Option<ResponseChecksumValidation>,
284    ) -> &mut Self {
285        self.response_checksum_validation = response_checksum_validation;
286        self
287    }
288
289    /// Set the retry_config for the builder
290    ///
291    /// _Note:_ Retries require a sleep implementation in order to work. When enabling retry, make
292    /// sure to set one with [Self::sleep_impl] or [Self::set_sleep_impl].
293    ///
294    /// # Examples
295    /// ```rust
296    /// use aws_types::SdkConfig;
297    /// use aws_smithy_types::retry::RetryConfig;
298    ///
299    /// let retry_config = RetryConfig::standard().with_max_attempts(5);
300    /// let config = SdkConfig::builder().retry_config(retry_config).build();
301    /// ```
302    pub fn retry_config(mut self, retry_config: RetryConfig) -> Self {
303        self.set_retry_config(Some(retry_config));
304        self
305    }
306
307    /// Set the retry_config for the builder
308    ///
309    /// _Note:_ Retries require a sleep implementation in order to work. When enabling retry, make
310    /// sure to set one with [Self::sleep_impl] or [Self::set_sleep_impl].
311    ///
312    /// # Examples
313    /// ```rust
314    /// use aws_types::sdk_config::{SdkConfig, Builder};
315    /// use aws_smithy_types::retry::RetryConfig;
316    ///
317    /// fn disable_retries(builder: &mut Builder) {
318    ///     let retry_config = RetryConfig::standard().with_max_attempts(1);
319    ///     builder.set_retry_config(Some(retry_config));
320    /// }
321    ///
322    /// let mut builder = SdkConfig::builder();
323    /// disable_retries(&mut builder);
324    /// ```
325    pub fn set_retry_config(&mut self, retry_config: Option<RetryConfig>) -> &mut Self {
326        self.retry_config = retry_config;
327        self
328    }
329
330    /// Set the [`TimeoutConfig`] for the builder
331    ///
332    /// _Note:_ Timeouts require a sleep implementation in order to work.
333    /// When enabling timeouts, be sure to set one with [Self::sleep_impl] or
334    /// [Self::set_sleep_impl].
335    ///
336    /// # Examples
337    ///
338    /// ```rust
339    /// # use std::time::Duration;
340    /// use aws_types::SdkConfig;
341    /// use aws_smithy_types::timeout::TimeoutConfig;
342    ///
343    /// let timeout_config = TimeoutConfig::builder()
344    ///     .operation_attempt_timeout(Duration::from_secs(2))
345    ///     .operation_timeout(Duration::from_secs(5))
346    ///     .build();
347    /// let config = SdkConfig::builder()
348    ///     .timeout_config(timeout_config)
349    ///     .build();
350    /// ```
351    pub fn timeout_config(mut self, timeout_config: TimeoutConfig) -> Self {
352        self.set_timeout_config(Some(timeout_config));
353        self
354    }
355
356    /// Set the [`TimeoutConfig`] for the builder
357    ///
358    /// _Note:_ Timeouts require a sleep implementation in order to work.
359    /// When enabling timeouts, be sure to set one with [Self::sleep_impl] or
360    /// [Self::set_sleep_impl].
361    ///
362    /// # Examples
363    /// ```rust
364    /// # use std::time::Duration;
365    /// use aws_types::sdk_config::{SdkConfig, Builder};
366    /// use aws_smithy_types::timeout::TimeoutConfig;
367    ///
368    /// fn set_preferred_timeouts(builder: &mut Builder) {
369    ///     let timeout_config = TimeoutConfig::builder()
370    ///         .operation_attempt_timeout(Duration::from_secs(2))
371    ///         .operation_timeout(Duration::from_secs(5))
372    ///         .build();
373    ///     builder.set_timeout_config(Some(timeout_config));
374    /// }
375    ///
376    /// let mut builder = SdkConfig::builder();
377    /// set_preferred_timeouts(&mut builder);
378    /// let config = builder.build();
379    /// ```
380    pub fn set_timeout_config(&mut self, timeout_config: Option<TimeoutConfig>) -> &mut Self {
381        self.timeout_config = timeout_config;
382        self
383    }
384
385    /// Set the sleep implementation for the builder.
386    ///
387    /// The sleep implementation is used to create timeout futures.
388    ///
389    /// _Note:_ If you're using the Tokio runtime, a `TokioSleep` implementation is available in
390    /// the `aws-smithy-async` crate.
391    ///
392    /// # Examples
393    ///
394    /// ```rust
395    /// use aws_smithy_async::rt::sleep::{AsyncSleep, SharedAsyncSleep, Sleep};
396    /// use aws_types::SdkConfig;
397    ///
398    /// ##[derive(Debug)]
399    /// pub struct ForeverSleep;
400    ///
401    /// impl AsyncSleep for ForeverSleep {
402    ///     fn sleep(&self, duration: std::time::Duration) -> Sleep {
403    ///         Sleep::new(std::future::pending())
404    ///     }
405    /// }
406    ///
407    /// let sleep_impl = SharedAsyncSleep::new(ForeverSleep);
408    /// let config = SdkConfig::builder().sleep_impl(sleep_impl).build();
409    /// ```
410    pub fn sleep_impl(mut self, sleep_impl: impl AsyncSleep + 'static) -> Self {
411        self.set_sleep_impl(Some(sleep_impl.into_shared()));
412        self
413    }
414
415    /// Set the sleep implementation for the builder. The sleep implementation is used to create
416    /// timeout futures.
417    ///
418    /// _Note:_ If you're using the Tokio runtime, a `TokioSleep` implementation is available in
419    /// the `aws-smithy-async` crate.
420    ///
421    /// # Examples
422    /// ```rust
423    /// # use aws_smithy_async::rt::sleep::{AsyncSleep, SharedAsyncSleep, Sleep};
424    /// # use aws_types::sdk_config::{Builder, SdkConfig};
425    /// #[derive(Debug)]
426    /// pub struct ForeverSleep;
427    ///
428    /// impl AsyncSleep for ForeverSleep {
429    ///     fn sleep(&self, duration: std::time::Duration) -> Sleep {
430    ///         Sleep::new(std::future::pending())
431    ///     }
432    /// }
433    ///
434    /// fn set_never_ending_sleep_impl(builder: &mut Builder) {
435    ///     let sleep_impl = SharedAsyncSleep::new(ForeverSleep);
436    ///     builder.set_sleep_impl(Some(sleep_impl));
437    /// }
438    ///
439    /// let mut builder = SdkConfig::builder();
440    /// set_never_ending_sleep_impl(&mut builder);
441    /// let config = builder.build();
442    /// ```
443    pub fn set_sleep_impl(&mut self, sleep_impl: Option<SharedAsyncSleep>) -> &mut Self {
444        self.sleep_impl = sleep_impl;
445        self
446    }
447
448    /// Set the identity cache for caching credentials and SSO tokens.
449    ///
450    /// The default identity cache will wait until the first request that requires authentication
451    /// to load an identity. Once the identity is loaded, it is cached until shortly before it
452    /// expires.
453    ///
454    /// # Examples
455    /// Disabling identity caching:
456    /// ```rust
457    /// # use aws_types::SdkConfig;
458    /// use aws_smithy_runtime::client::identity::IdentityCache;
459    /// let config = SdkConfig::builder()
460    ///     .identity_cache(IdentityCache::no_cache())
461    ///     .build();
462    /// ```
463    /// Changing settings on the default cache implementation:
464    /// ```rust
465    /// # use aws_types::SdkConfig;
466    /// use aws_smithy_runtime::client::identity::IdentityCache;
467    /// use std::time::Duration;
468    ///
469    /// let config = SdkConfig::builder()
470    ///     .identity_cache(
471    ///         IdentityCache::lazy()
472    ///             .load_timeout(Duration::from_secs(10))
473    ///             .build()
474    ///     )
475    ///     .build();
476    /// ```
477    pub fn identity_cache(mut self, cache: impl ResolveCachedIdentity + 'static) -> Self {
478        self.set_identity_cache(Some(cache.into_shared()));
479        self
480    }
481
482    /// Set the identity cache for caching credentials and SSO tokens.
483    ///
484    /// The default identity cache will wait until the first request that requires authentication
485    /// to load an identity. Once the identity is loaded, it is cached until shortly before it
486    /// expires.
487    ///
488    /// # Examples
489    /// ```rust
490    /// # use aws_types::SdkConfig;
491    /// use aws_smithy_runtime::client::identity::IdentityCache;
492    ///
493    /// fn override_identity_cache() -> bool {
494    ///   // ...
495    ///   # true
496    /// }
497    ///
498    /// let mut builder = SdkConfig::builder();
499    /// if override_identity_cache() {
500    ///     builder.set_identity_cache(Some(IdentityCache::lazy().build()));
501    /// }
502    /// let config = builder.build();
503    /// ```
504    pub fn set_identity_cache(&mut self, cache: Option<SharedIdentityCache>) -> &mut Self {
505        self.identity_cache = cache;
506        self
507    }
508
509    /// Set the credentials provider for the builder
510    ///
511    /// # Examples
512    /// ```rust
513    /// use aws_credential_types::provider::{ProvideCredentials, SharedCredentialsProvider};
514    /// use aws_types::SdkConfig;
515    /// fn make_provider() -> impl ProvideCredentials {
516    ///   // ...
517    ///   # use aws_credential_types::Credentials;
518    ///   # Credentials::new("test", "test", None, None, "example")
519    /// }
520    ///
521    /// let config = SdkConfig::builder()
522    ///     .credentials_provider(SharedCredentialsProvider::new(make_provider()))
523    ///     .build();
524    /// ```
525    pub fn credentials_provider(mut self, provider: SharedCredentialsProvider) -> Self {
526        self.set_credentials_provider(Some(provider));
527        self
528    }
529
530    /// Set the credentials provider for the builder
531    ///
532    /// # Examples
533    /// ```rust
534    /// use aws_credential_types::provider::{ProvideCredentials, SharedCredentialsProvider};
535    /// use aws_types::SdkConfig;
536    /// fn make_provider() -> impl ProvideCredentials {
537    ///   // ...
538    ///   # use aws_credential_types::Credentials;
539    ///   # Credentials::new("test", "test", None, None, "example")
540    /// }
541    ///
542    /// fn override_provider() -> bool {
543    ///   // ...
544    ///   # true
545    /// }
546    ///
547    /// let mut builder = SdkConfig::builder();
548    /// if override_provider() {
549    ///     builder.set_credentials_provider(Some(SharedCredentialsProvider::new(make_provider())));
550    /// }
551    /// let config = builder.build();
552    /// ```
553    pub fn set_credentials_provider(
554        &mut self,
555        provider: Option<SharedCredentialsProvider>,
556    ) -> &mut Self {
557        self.credentials_provider = provider;
558        self
559    }
560
561    /// Set the bearer auth token provider for the builder
562    ///
563    /// # Examples
564    /// ```rust
565    /// use aws_credential_types::provider::token::{ProvideToken, SharedTokenProvider};
566    /// use aws_types::SdkConfig;
567    ///
568    /// fn make_provider() -> impl ProvideToken {
569    ///   // ...
570    ///   # aws_credential_types::Token::new("example", None)
571    /// }
572    ///
573    /// let config = SdkConfig::builder()
574    ///     .token_provider(SharedTokenProvider::new(make_provider()))
575    ///     .build();
576    /// ```
577    pub fn token_provider(mut self, provider: SharedTokenProvider) -> Self {
578        self.set_token_provider(Some(provider));
579        self
580    }
581
582    /// Set the bearer auth token provider for the builder
583    ///
584    /// # Examples
585    /// ```rust
586    /// use aws_credential_types::provider::token::{ProvideToken, SharedTokenProvider};
587    /// use aws_types::SdkConfig;
588    ///
589    /// fn make_provider() -> impl ProvideToken {
590    ///   // ...
591    ///   # aws_credential_types::Token::new("example", None)
592    /// }
593    ///
594    /// fn override_provider() -> bool {
595    ///   // ...
596    ///   # true
597    /// }
598    ///
599    /// let mut builder = SdkConfig::builder();
600    /// if override_provider() {
601    ///     builder.set_token_provider(Some(SharedTokenProvider::new(make_provider())));
602    /// }
603    /// let config = builder.build();
604    /// ```
605    pub fn set_token_provider(&mut self, provider: Option<SharedTokenProvider>) -> &mut Self {
606        self.token_provider = provider;
607        self
608    }
609
610    /// Sets the name of the app that is using the client.
611    ///
612    /// This _optional_ name is used to identify the application in the user agent that
613    /// gets sent along with requests.
614    pub fn app_name(mut self, app_name: AppName) -> Self {
615        self.set_app_name(Some(app_name));
616        self
617    }
618
619    /// Sets the name of the app that is using the client.
620    ///
621    /// This _optional_ name is used to identify the application in the user agent that
622    /// gets sent along with requests.
623    pub fn set_app_name(&mut self, app_name: Option<AppName>) -> &mut Self {
624        self.app_name = app_name;
625        self
626    }
627
628    /// Sets the HTTP client to use when making requests.
629    ///
630    /// ## Examples
631    /// ```no_run
632    /// # #[cfg(feature = "examples")]
633    /// # fn example() {
634    /// use aws_types::sdk_config::{SdkConfig, TimeoutConfig};
635    /// use aws_smithy_runtime::client::http::hyper_014::HyperClientBuilder;
636    /// use std::time::Duration;
637    ///
638    /// // Create a connector that will be used to establish TLS connections
639    /// let tls_connector = hyper_rustls::HttpsConnectorBuilder::new()
640    ///     .with_webpki_roots()
641    ///     .https_only()
642    ///     .enable_http1()
643    ///     .enable_http2()
644    ///     .build();
645    /// // Create a HTTP client that uses the TLS connector. This client is
646    /// // responsible for creating and caching a HttpConnector when given HttpConnectorSettings.
647    /// // This hyper client will create HttpConnectors backed by hyper and the tls_connector.
648    /// let http_client = HyperClientBuilder::new().build(tls_connector);
649    /// let sdk_config = SdkConfig::builder()
650    ///     .http_client(http_client)
651    ///     // Connect/read timeouts are passed to the HTTP client when servicing a request
652    ///     .timeout_config(
653    ///         TimeoutConfig::builder()
654    ///             .connect_timeout(Duration::from_secs(5))
655    ///             .build()
656    ///     )
657    ///     .build();
658    /// # }
659    /// ```
660    pub fn http_client(mut self, http_client: impl HttpClient + 'static) -> Self {
661        self.set_http_client(Some(http_client.into_shared()));
662        self
663    }
664
665    /// Sets the HTTP client to use when making requests.
666    ///
667    /// ## Examples
668    /// ```no_run
669    /// # #[cfg(feature = "examples")]
670    /// # fn example() {
671    /// use aws_types::sdk_config::{Builder, SdkConfig, TimeoutConfig};
672    /// use aws_smithy_runtime::client::http::hyper_014::HyperClientBuilder;
673    /// use std::time::Duration;
674    ///
675    /// fn override_http_client(builder: &mut Builder) {
676    ///     // Create a connector that will be used to establish TLS connections
677    ///     let tls_connector = hyper_rustls::HttpsConnectorBuilder::new()
678    ///         .with_webpki_roots()
679    ///         .https_only()
680    ///         .enable_http1()
681    ///         .enable_http2()
682    ///         .build();
683    ///     // Create a HTTP client that uses the TLS connector. This client is
684    ///     // responsible for creating and caching a HttpConnector when given HttpConnectorSettings.
685    ///     // This hyper client will create HttpConnectors backed by hyper and the tls_connector.
686    ///     let http_client = HyperClientBuilder::new().build(tls_connector);
687    ///
688    ///     builder.set_http_client(Some(http_client));
689    /// }
690    ///
691    /// let mut builder = SdkConfig::builder();
692    /// override_http_client(&mut builder);
693    /// let config = builder.build();
694    /// # }
695    /// ```
696    pub fn set_http_client(&mut self, http_client: Option<SharedHttpClient>) -> &mut Self {
697        self.http_client = http_client;
698        self
699    }
700
701    /// Sets the client protocol to use for serialization and deserialization.
702    ///
703    /// This overrides the default protocol determined by the service model,
704    /// enabling runtime protocol selection.
705    ///
706    /// # Transport
707    ///
708    /// This setter is HTTP-specific. The whole pipeline — the `self.protocol`
709    /// field (typed `Option<SharedClientProtocol>`, which elides to the HTTP
710    /// specialization via [`SharedClientProtocol`]'s
711    /// default type parameters) and its `Storable` impl (keyed only to
712    /// `SharedClientProtocol<http::Request, http::Response>`) — commits to
713    /// HTTP. The `impl ClientProtocol + 'static` bound you see here is
714    /// consistent with that: it elides to
715    /// `impl ClientProtocol<http::Request, http::Response>`.
716    ///
717    /// `ClientProtocolInner` / `ClientProtocol<Req, Res>` /
718    /// `SharedClientProtocol<Req, Res>` are themselves transport-generic — a
719    /// user can write `impl ClientProtocol<MqttMessage, MqttMessage>` — but
720    /// such an impl cannot be passed here because it won't round-trip through
721    /// the HTTP-typed config-bag storage. A future non-HTTP transport would
722    /// ship its own dedicated setter (e.g., `mqtt_protocol(…)`) paired with
723    /// its own `Storable` newtype rather than generalizing this one.
724    pub fn protocol(
725        mut self,
726        protocol: impl aws_smithy_schema::protocol::ClientProtocol + 'static,
727    ) -> Self {
728        self.set_protocol(Some(SharedClientProtocol::new(protocol)));
729        self
730    }
731
732    /// Sets the client protocol to use for serialization and deserialization.
733    pub fn set_protocol(&mut self, protocol: Option<SharedClientProtocol>) -> &mut Self {
734        self.protocol = protocol;
735        self
736    }
737
738    #[doc = docs_for!(use_fips)]
739    pub fn use_fips(mut self, use_fips: bool) -> Self {
740        self.set_use_fips(Some(use_fips));
741        self
742    }
743
744    #[doc = docs_for!(use_fips)]
745    pub fn set_use_fips(&mut self, use_fips: Option<bool>) -> &mut Self {
746        self.use_fips = use_fips;
747        self
748    }
749
750    #[doc = docs_for!(use_dual_stack)]
751    pub fn use_dual_stack(mut self, use_dual_stack: bool) -> Self {
752        self.set_use_dual_stack(Some(use_dual_stack));
753        self
754    }
755
756    #[doc = docs_for!(use_dual_stack)]
757    pub fn set_use_dual_stack(&mut self, use_dual_stack: Option<bool>) -> &mut Self {
758        self.use_dual_stack = use_dual_stack;
759        self
760    }
761
762    #[doc = docs_for!(time_source)]
763    pub fn time_source(mut self, time_source: impl TimeSource + 'static) -> Self {
764        self.set_time_source(Some(SharedTimeSource::new(time_source)));
765        self
766    }
767
768    #[doc = docs_for!(time_source)]
769    pub fn set_time_source(&mut self, time_source: Option<SharedTimeSource>) -> &mut Self {
770        self.time_source = time_source;
771        self
772    }
773
774    #[doc = docs_for!(disable_request_compression)]
775    pub fn disable_request_compression(mut self, disable_request_compression: bool) -> Self {
776        self.set_disable_request_compression(Some(disable_request_compression));
777        self
778    }
779
780    #[doc = docs_for!(disable_request_compression)]
781    pub fn set_disable_request_compression(
782        &mut self,
783        disable_request_compression: Option<bool>,
784    ) -> &mut Self {
785        self.disable_request_compression = disable_request_compression;
786        self
787    }
788
789    #[doc = docs_for!(request_min_compression_size_bytes)]
790    pub fn request_min_compression_size_bytes(
791        mut self,
792        request_min_compression_size_bytes: u32,
793    ) -> Self {
794        self.set_request_min_compression_size_bytes(Some(request_min_compression_size_bytes));
795        self
796    }
797
798    #[doc = docs_for!(request_min_compression_size_bytes)]
799    pub fn set_request_min_compression_size_bytes(
800        &mut self,
801        request_min_compression_size_bytes: Option<u32>,
802    ) -> &mut Self {
803        self.request_min_compression_size_bytes = request_min_compression_size_bytes;
804        self
805    }
806
807    /// Sets the [`BehaviorVersion`] for the [`SdkConfig`]
808    pub fn behavior_version(mut self, behavior_version: BehaviorVersion) -> Self {
809        self.set_behavior_version(Some(behavior_version));
810        self
811    }
812
813    /// Sets the [`BehaviorVersion`] for the [`SdkConfig`]
814    pub fn set_behavior_version(&mut self, behavior_version: Option<BehaviorVersion>) -> &mut Self {
815        self.behavior_version = behavior_version;
816        self
817    }
818
819    /// Sets the service config provider for the [`SdkConfig`].
820    ///
821    /// This provider is used when creating a service-specific config from an
822    /// `SdkConfig` and provides access to config defined in the environment
823    /// which would otherwise be inaccessible.
824    pub fn service_config(mut self, service_config: impl LoadServiceConfig + 'static) -> Self {
825        self.set_service_config(Some(service_config));
826        self
827    }
828
829    /// Sets the service config provider for the [`SdkConfig`].
830    ///
831    /// This provider is used when creating a service-specific config from an
832    /// `SdkConfig` and provides access to config defined in the environment
833    /// which would otherwise be inaccessible.
834    pub fn set_service_config(
835        &mut self,
836        service_config: Option<impl LoadServiceConfig + 'static>,
837    ) -> &mut Self {
838        self.service_config = service_config.map(|it| Arc::new(it) as Arc<dyn LoadServiceConfig>);
839        self
840    }
841
842    #[doc = docs_for!(auth_scheme_preference)]
843    pub fn auth_scheme_preference(
844        mut self,
845        auth_scheme_preference: impl Into<AuthSchemePreference>,
846    ) -> Self {
847        self.set_auth_scheme_preference(Some(auth_scheme_preference));
848        self
849    }
850
851    #[doc = docs_for!(auth_scheme_preference)]
852    pub fn set_auth_scheme_preference(
853        &mut self,
854        auth_scheme_preference: Option<impl Into<AuthSchemePreference>>,
855    ) -> &mut Self {
856        self.auth_scheme_preference = auth_scheme_preference.map(|pref| pref.into());
857        self
858    }
859
860    #[doc = docs_for!(sigv4a_signing_region_set)]
861    pub fn sigv4a_signing_region_set(
862        mut self,
863        sigv4a_signing_region_set: impl Into<SigningRegionSet>,
864    ) -> Self {
865        self.set_sigv4a_signing_region_set(Some(sigv4a_signing_region_set));
866        self
867    }
868
869    #[doc = docs_for!(sigv4a_signing_region_set)]
870    pub fn set_sigv4a_signing_region_set(
871        &mut self,
872        sigv4a_signing_region_set: Option<impl Into<SigningRegionSet>>,
873    ) -> &mut Self {
874        self.sigv4a_signing_region_set = sigv4a_signing_region_set.map(|v| v.into());
875        self
876    }
877
878    /// Set the origin of a setting.
879    ///
880    /// This is used internally to understand how to merge config structs while
881    /// respecting precedence of origins.
882    pub fn insert_origin(&mut self, setting: &'static str, origin: Origin) {
883        self.config_origins.insert(setting, origin);
884    }
885
886    /// Build a [`SdkConfig`] from this builder.
887    pub fn build(self) -> SdkConfig {
888        SdkConfig {
889            app_name: self.app_name,
890            auth_scheme_preference: self.auth_scheme_preference,
891            sigv4a_signing_region_set: self.sigv4a_signing_region_set,
892            identity_cache: self.identity_cache,
893            credentials_provider: self.credentials_provider,
894            token_provider: self.token_provider,
895            region: self.region,
896            account_id_endpoint_mode: self.account_id_endpoint_mode,
897            endpoint_url: self.endpoint_url,
898            retry_config: self.retry_config,
899            sleep_impl: self.sleep_impl,
900            timeout_config: self.timeout_config,
901            http_client: self.http_client,
902            use_fips: self.use_fips,
903            use_dual_stack: self.use_dual_stack,
904            time_source: self.time_source,
905            behavior_version: self.behavior_version,
906            stalled_stream_protection_config: self.stalled_stream_protection_config,
907            service_config: self.service_config,
908            config_origins: self.config_origins,
909            disable_request_compression: self.disable_request_compression,
910            request_min_compression_size_bytes: self.request_min_compression_size_bytes,
911            request_checksum_calculation: self.request_checksum_calculation,
912            response_checksum_validation: self.response_checksum_validation,
913            protocol: self.protocol,
914        }
915    }
916}
917
918impl Builder {
919    /// Set the [`StalledStreamProtectionConfig`] to configure protection for stalled streams.
920    ///
921    /// This configures stalled stream protection. When enabled, download streams
922    /// that stall (stream no data) for longer than a configured grace period will return an error.
923    ///
924    /// _Note:_ Stalled stream protection requires both a sleep implementation and a time source
925    /// in order to work. When enabling stalled stream protection, make sure to set
926    /// - A sleep impl with [Self::sleep_impl] or [Self::set_sleep_impl].
927    /// - A time source with [Self::time_source] or [Self::set_time_source].
928    ///
929    /// # Examples
930    /// ```rust
931    /// use std::time::Duration;
932    /// use aws_types::SdkConfig;
933    /// pub use aws_smithy_runtime_api::client::stalled_stream_protection::StalledStreamProtectionConfig;
934    ///
935    /// let stalled_stream_protection_config = StalledStreamProtectionConfig::enabled()
936    ///     .grace_period(Duration::from_secs(1))
937    ///     .build();
938    /// let config = SdkConfig::builder()
939    ///     .stalled_stream_protection(stalled_stream_protection_config)
940    ///     .build();
941    /// ```
942    pub fn stalled_stream_protection(
943        mut self,
944        stalled_stream_protection_config: StalledStreamProtectionConfig,
945    ) -> Self {
946        self.set_stalled_stream_protection(Some(stalled_stream_protection_config));
947        self
948    }
949
950    /// Set the [`StalledStreamProtectionConfig`] to configure protection for stalled streams.
951    ///
952    /// This configures stalled stream protection. When enabled, download streams
953    /// that stall (stream no data) for longer than a configured grace period will return an error.
954    ///
955    /// By default, streams that transmit less than one byte per-second for five seconds will
956    /// be cancelled.
957    ///
958    /// _Note:_ Stalled stream protection requires both a sleep implementation and a time source
959    /// in order to work. When enabling stalled stream protection, make sure to set
960    /// - A sleep impl with [Self::sleep_impl] or [Self::set_sleep_impl].
961    /// - A time source with [Self::time_source] or [Self::set_time_source].
962    ///
963    /// # Examples
964    /// ```rust
965    /// use std::time::Duration;
966    /// use aws_types::sdk_config::{SdkConfig, Builder};
967    /// pub use aws_smithy_runtime_api::client::stalled_stream_protection::StalledStreamProtectionConfig;
968    ///
969    /// fn set_stalled_stream_protection(builder: &mut Builder) {
970    ///     let stalled_stream_protection_config = StalledStreamProtectionConfig::enabled()
971    ///         .grace_period(Duration::from_secs(1))
972    ///         .build();
973    ///     builder.set_stalled_stream_protection(Some(stalled_stream_protection_config));
974    /// }
975    ///
976    /// let mut builder = SdkConfig::builder();
977    /// set_stalled_stream_protection(&mut builder);
978    /// let config = builder.build();
979    /// ```
980    pub fn set_stalled_stream_protection(
981        &mut self,
982        stalled_stream_protection_config: Option<StalledStreamProtectionConfig>,
983    ) -> &mut Self {
984        self.stalled_stream_protection_config = stalled_stream_protection_config;
985        self
986    }
987}
988
989impl SdkConfig {
990    /// Configured region
991    pub fn region(&self) -> Option<&Region> {
992        self.region.as_ref()
993    }
994
995    /// Configured account ID endpoint mode
996    pub fn account_id_endpoint_mode(&self) -> Option<&AccountIdEndpointMode> {
997        self.account_id_endpoint_mode.as_ref()
998    }
999
1000    /// Configured auth scheme preference
1001    pub fn auth_scheme_preference(&self) -> Option<&AuthSchemePreference> {
1002        self.auth_scheme_preference.as_ref()
1003    }
1004
1005    /// Configured SigV4a signing region set
1006    pub fn sigv4a_signing_region_set(&self) -> Option<&SigningRegionSet> {
1007        self.sigv4a_signing_region_set.as_ref()
1008    }
1009
1010    /// Configured endpoint URL
1011    pub fn endpoint_url(&self) -> Option<&str> {
1012        self.endpoint_url.as_deref()
1013    }
1014
1015    /// Configured retry config
1016    pub fn retry_config(&self) -> Option<&RetryConfig> {
1017        self.retry_config.as_ref()
1018    }
1019
1020    /// Configured timeout config
1021    pub fn timeout_config(&self) -> Option<&TimeoutConfig> {
1022        self.timeout_config.as_ref()
1023    }
1024
1025    /// Configured sleep implementation
1026    pub fn sleep_impl(&self) -> Option<SharedAsyncSleep> {
1027        self.sleep_impl.clone()
1028    }
1029
1030    /// Configured identity cache
1031    pub fn identity_cache(&self) -> Option<SharedIdentityCache> {
1032        self.identity_cache.clone()
1033    }
1034
1035    /// Configured credentials provider
1036    pub fn credentials_provider(&self) -> Option<SharedCredentialsProvider> {
1037        self.credentials_provider.clone()
1038    }
1039
1040    /// Configured bearer auth token provider
1041    pub fn token_provider(&self) -> Option<SharedTokenProvider> {
1042        self.token_provider.clone()
1043    }
1044
1045    /// Configured time source
1046    pub fn time_source(&self) -> Option<SharedTimeSource> {
1047        self.time_source.clone()
1048    }
1049
1050    /// Configured app name
1051    pub fn app_name(&self) -> Option<&AppName> {
1052        self.app_name.as_ref()
1053    }
1054
1055    /// Configured HTTP client
1056    pub fn http_client(&self) -> Option<SharedHttpClient> {
1057        self.http_client.clone()
1058    }
1059
1060    /// Configured client protocol for serialization and deserialization
1061    pub fn protocol(&self) -> Option<SharedClientProtocol> {
1062        self.protocol.clone()
1063    }
1064
1065    /// Use FIPS endpoints
1066    pub fn use_fips(&self) -> Option<bool> {
1067        self.use_fips
1068    }
1069
1070    /// Use dual-stack endpoint
1071    pub fn use_dual_stack(&self) -> Option<bool> {
1072        self.use_dual_stack
1073    }
1074
1075    /// When true, request compression is disabled.
1076    pub fn disable_request_compression(&self) -> Option<bool> {
1077        self.disable_request_compression
1078    }
1079
1080    /// Configured checksum request behavior.
1081    pub fn request_checksum_calculation(&self) -> Option<RequestChecksumCalculation> {
1082        self.request_checksum_calculation
1083    }
1084
1085    /// Configured checksum response behavior.
1086    pub fn response_checksum_validation(&self) -> Option<ResponseChecksumValidation> {
1087        self.response_checksum_validation
1088    }
1089
1090    /// Configured minimum request compression size.
1091    pub fn request_min_compression_size_bytes(&self) -> Option<u32> {
1092        self.request_min_compression_size_bytes
1093    }
1094
1095    /// Configured stalled stream protection
1096    pub fn stalled_stream_protection(&self) -> Option<StalledStreamProtectionConfig> {
1097        self.stalled_stream_protection_config.clone()
1098    }
1099
1100    /// Behavior version configured for this client
1101    pub fn behavior_version(&self) -> Option<BehaviorVersion> {
1102        self.behavior_version
1103    }
1104
1105    /// Return an immutable reference to the service config provider configured for this client.
1106    pub fn service_config(&self) -> Option<&dyn LoadServiceConfig> {
1107        self.service_config.as_deref()
1108    }
1109
1110    /// Config builder
1111    ///
1112    /// _Important:_ Using the `aws-config` crate to configure the SDK is preferred to invoking this
1113    /// builder directly. Using this builder directly won't pull in any AWS recommended default
1114    /// configuration values.
1115    pub fn builder() -> Builder {
1116        Builder::default()
1117    }
1118
1119    /// Convert this [`SdkConfig`] into a [`Builder`] by cloning it first
1120    pub fn to_builder(&self) -> Builder {
1121        self.clone().into_builder()
1122    }
1123
1124    /// Get the origin of a setting.
1125    ///
1126    /// This is used internally to understand how to merge config structs while
1127    /// respecting precedence of origins.
1128    pub fn get_origin(&self, setting: &'static str) -> Origin {
1129        self.config_origins
1130            .get(setting)
1131            .cloned()
1132            .unwrap_or_default()
1133    }
1134
1135    /// Convert this [`SdkConfig`] back to a builder to enable modification
1136    pub fn into_builder(self) -> Builder {
1137        Builder {
1138            app_name: self.app_name,
1139            auth_scheme_preference: self.auth_scheme_preference,
1140            sigv4a_signing_region_set: self.sigv4a_signing_region_set,
1141            identity_cache: self.identity_cache,
1142            credentials_provider: self.credentials_provider,
1143            token_provider: self.token_provider,
1144            region: self.region,
1145            account_id_endpoint_mode: self.account_id_endpoint_mode,
1146            endpoint_url: self.endpoint_url,
1147            retry_config: self.retry_config,
1148            sleep_impl: self.sleep_impl,
1149            time_source: self.time_source,
1150            timeout_config: self.timeout_config,
1151            http_client: self.http_client,
1152            use_fips: self.use_fips,
1153            use_dual_stack: self.use_dual_stack,
1154            behavior_version: self.behavior_version,
1155            stalled_stream_protection_config: self.stalled_stream_protection_config,
1156            service_config: self.service_config,
1157            config_origins: self.config_origins,
1158            disable_request_compression: self.disable_request_compression,
1159            request_min_compression_size_bytes: self.request_min_compression_size_bytes,
1160            request_checksum_calculation: self.request_checksum_calculation,
1161            response_checksum_validation: self.response_checksum_validation,
1162            protocol: self.protocol,
1163        }
1164    }
1165}