aws_runtime/
endpoint_override.rs1use aws_smithy_runtime_api::box_error::BoxError;
9use aws_smithy_runtime_api::client::interceptors::context::BeforeSerializationInterceptorContextRef;
10use aws_smithy_runtime_api::client::interceptors::Intercept;
11use aws_smithy_runtime_api::client::runtime_plugin::RuntimePlugin;
12use aws_smithy_types::config_bag::{ConfigBag, FrozenLayer};
13
14use crate::sdk_feature::AwsSdkFeature;
15
16#[derive(Debug, Default)]
18#[non_exhaustive]
19pub struct EndpointOverrideInterceptor;
20
21impl EndpointOverrideInterceptor {
22 pub fn new() -> Self {
24 Self
25 }
26}
27
28impl Intercept for EndpointOverrideInterceptor {
29 fn name(&self) -> &'static str {
30 "EndpointOverrideInterceptor"
31 }
32
33 fn read_before_execution(
34 &self,
35 _context: &BeforeSerializationInterceptorContextRef<'_>,
36 cfg: &mut ConfigBag,
37 ) -> Result<(), BoxError> {
38 if cfg
40 .load::<aws_types::endpoint_config::EndpointUrl>()
41 .is_some()
42 {
43 cfg.interceptor_state()
44 .store_append(AwsSdkFeature::EndpointOverride);
45 }
46 Ok(())
47 }
48}
49
50#[derive(Debug)]
58#[non_exhaustive]
59pub struct EndpointOverrideRuntimePlugin {
60 config: Option<FrozenLayer>,
61}
62
63impl EndpointOverrideRuntimePlugin {
64 pub fn new(config: Option<FrozenLayer>) -> Self {
66 Self { config }
67 }
68}
69
70impl Default for EndpointOverrideRuntimePlugin {
71 fn default() -> Self {
72 Self { config: None }
73 }
74}
75
76impl RuntimePlugin for EndpointOverrideRuntimePlugin {
77 fn config(&self) -> Option<FrozenLayer> {
78 self.config.clone()
79 }
80}
81
82#[cfg(test)]
83mod tests {
84 use super::*;
85 use crate::sdk_feature::AwsSdkFeature;
86 use aws_smithy_runtime_api::client::interceptors::context::{
87 BeforeSerializationInterceptorContextRef, Input, InterceptorContext,
88 };
89 use aws_smithy_types::config_bag::ConfigBag;
90
91 #[test]
92 fn test_plugin_with_no_config() {
93 let plugin = EndpointOverrideRuntimePlugin::default();
94 assert!(plugin.config().is_none());
95 }
96
97 #[test]
98 fn test_interceptor_detects_endpoint_url_when_present() {
99 let interceptor = EndpointOverrideInterceptor::new();
100 let mut cfg = ConfigBag::base();
101
102 let endpoint_url =
104 aws_types::endpoint_config::EndpointUrl("https://custom.example.com".to_string());
105 cfg.interceptor_state().store_put(endpoint_url);
106
107 let input = Input::doesnt_matter();
109 let ctx = InterceptorContext::new(input);
110 let context = BeforeSerializationInterceptorContextRef::from(&ctx);
111
112 interceptor
114 .read_before_execution(&context, &mut cfg)
115 .unwrap();
116
117 let features: Vec<_> = cfg
119 .interceptor_state()
120 .load::<AwsSdkFeature>()
121 .cloned()
122 .collect();
123 assert_eq!(features.len(), 1);
124 assert_eq!(features[0], AwsSdkFeature::EndpointOverride);
125 }
126
127 #[test]
128 fn test_interceptor_does_not_set_flag_when_endpoint_url_absent() {
129 let interceptor = EndpointOverrideInterceptor::new();
130 let mut cfg = ConfigBag::base();
131
132 let input = Input::doesnt_matter();
134 let ctx = InterceptorContext::new(input);
135 let context = BeforeSerializationInterceptorContextRef::from(&ctx);
136
137 interceptor
139 .read_before_execution(&context, &mut cfg)
140 .unwrap();
141
142 let features: Vec<_> = cfg
144 .interceptor_state()
145 .load::<AwsSdkFeature>()
146 .cloned()
147 .collect();
148 assert_eq!(features.len(), 0);
149 }
150}