Loading aws/rust-runtime/aws-inlineable/src/lib.rs +2 −0 Original line number Diff line number Diff line Loading @@ -24,6 +24,8 @@ pub mod no_credentials; /// Support types required for adding presigning to an operation in a generated service. pub mod presigning; // TODO(CrateReorganization): Delete the `old_presigning` module pub mod old_presigning; /// Special logic for extracting request IDs from S3's responses. pub mod s3_request_id; Loading aws/rust-runtime/aws-inlineable/src/old_presigning.rs 0 → 100644 +282 −0 Original line number Diff line number Diff line /* * Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. * SPDX-License-Identifier: Apache-2.0 */ //! Presigned request types and configuration. /// Presigning config and builder pub mod config { use std::fmt; use std::time::{Duration, SystemTime}; const ONE_WEEK: Duration = Duration::from_secs(604800); /// Presigning config values required for creating a presigned request. #[non_exhaustive] #[derive(Debug, Clone)] pub struct PresigningConfig { start_time: SystemTime, expires_in: Duration, } impl PresigningConfig { /// Creates a `PresigningConfig` with the given `expires_in` duration. /// /// The `expires_in` duration is the total amount of time the presigned request should /// be valid for. Other config values are defaulted. /// /// Credential expiration time takes priority over the `expires_in` value. /// If the credentials used to sign the request expire before the presigned request is /// set to expire, then the presigned request will become invalid. pub fn expires_in(expires_in: Duration) -> Result<PresigningConfig, Error> { Self::builder().expires_in(expires_in).build() } /// Creates a new builder for creating a `PresigningConfig`. pub fn builder() -> Builder { Builder::default() } /// Returns the amount of time the presigned request should be valid for. pub fn expires(&self) -> Duration { self.expires_in } /// Returns the start time. The presigned request will be valid between this and the end /// time produced by adding the `expires()` value to it. pub fn start_time(&self) -> SystemTime { self.start_time } } #[derive(Debug)] enum ErrorKind { /// Presigned requests cannot be valid for longer than one week. ExpiresInDurationTooLong, /// The `PresigningConfig` builder requires a value for `expires_in`. ExpiresInRequired, } /// `PresigningConfig` build errors. #[derive(Debug)] pub struct Error { kind: ErrorKind, } impl std::error::Error for Error {} impl fmt::Display for Error { fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { match self.kind { ErrorKind::ExpiresInDurationTooLong => { write!(f, "`expires_in` must be no longer than one week") } ErrorKind::ExpiresInRequired => write!(f, "`expires_in` is required"), } } } impl From<ErrorKind> for Error { fn from(kind: ErrorKind) -> Self { Self { kind } } } /// Builder used to create `PresigningConfig`. #[non_exhaustive] #[derive(Default, Debug)] pub struct Builder { start_time: Option<SystemTime>, expires_in: Option<Duration>, } impl Builder { /// Sets the start time for the presigned request. /// /// The request will start to be valid at this time, and will cease to be valid after /// the end time, which can be determined by adding the `expires_in` duration to this /// start time. If not specified, this will default to the current time. /// /// Optional. pub fn start_time(mut self, start_time: SystemTime) -> Self { self.set_start_time(Some(start_time)); self } /// Sets the start time for the presigned request. /// /// The request will start to be valid at this time, and will cease to be valid after /// the end time, which can be determined by adding the `expires_in` duration to this /// start time. If not specified, this will default to the current time. /// /// Optional. pub fn set_start_time(&mut self, start_time: Option<SystemTime>) { self.start_time = start_time; } /// Sets how long the request should be valid after the `start_time` (which defaults /// to the current time). /// /// Credential expiration time takes priority over the `expires_in` value. /// If the credentials used to sign the request expire before the presigned request is /// set to expire, then the presigned request will become invalid. /// /// Required. pub fn expires_in(mut self, expires_in: Duration) -> Self { self.set_expires_in(Some(expires_in)); self } /// Sets how long the request should be valid after the `start_time` (which defaults /// to the current time). /// /// Credential expiration time takes priority over the `expires_in` value. /// If the credentials used to sign the request expire before the presigned request is /// set to expire, then the presigned request will become invalid. /// /// Required. pub fn set_expires_in(&mut self, expires_in: Option<Duration>) { self.expires_in = expires_in; } /// Builds the `PresigningConfig`. This will error if `expires_in` is not /// given, or if it's longer than one week. pub fn build(self) -> Result<PresigningConfig, Error> { let expires_in = self.expires_in.ok_or(ErrorKind::ExpiresInRequired)?; if expires_in > ONE_WEEK { return Err(ErrorKind::ExpiresInDurationTooLong.into()); } Ok(PresigningConfig { start_time: self.start_time.unwrap_or_else(SystemTime::now), expires_in, }) } } } /// Presigned request pub mod request { use std::fmt::{Debug, Formatter}; /// Represents a presigned request. This only includes the HTTP request method, URI, and headers. /// /// **This struct has conversion convenience functions:** /// /// - [`PresignedRequest::to_http_request<B>`][Self::to_http_request] returns an [`http::Request<B>`](https://docs.rs/http/0.2.6/http/request/struct.Request.html) /// - [`PresignedRequest::into`](#impl-From<PresignedRequest>) returns an [`http::request::Builder`](https://docs.rs/http/0.2.6/http/request/struct.Builder.html) #[non_exhaustive] pub struct PresignedRequest(http::Request<()>); impl PresignedRequest { pub(crate) fn new(inner: http::Request<()>) -> Self { Self(inner) } /// Returns the HTTP request method. pub fn method(&self) -> &http::Method { self.0.method() } /// Returns the HTTP request URI. pub fn uri(&self) -> &http::Uri { self.0.uri() } /// Returns any HTTP headers that need to go along with the request, except for `Host`, /// which should be sent based on the endpoint in the URI by the HTTP client rather than /// added directly. pub fn headers(&self) -> &http::HeaderMap<http::HeaderValue> { self.0.headers() } /// Given a body, convert this `PresignedRequest` into an `http::Request` pub fn to_http_request<B>(self, body: B) -> Result<http::Request<B>, http::Error> { let builder: http::request::Builder = self.into(); builder.body(body) } } impl Debug for PresignedRequest { fn fmt(&self, f: &mut Formatter<'_>) -> std::fmt::Result { f.debug_struct("PresignedRequest") .field("method", self.method()) .field("uri", self.uri()) .field("headers", self.headers()) .finish() } } impl From<PresignedRequest> for http::request::Builder { fn from(req: PresignedRequest) -> Self { let mut builder = http::request::Builder::new() .uri(req.uri()) .method(req.method()); if let Some(headers) = builder.headers_mut() { *headers = req.headers().clone(); } builder } } } /// Tower middleware service for creating presigned requests #[allow(dead_code)] pub(crate) mod service { use super::request::PresignedRequest; use aws_smithy_http::operation; use http::header::USER_AGENT; use std::future::{ready, Ready}; use std::marker::PhantomData; use std::task::{Context, Poll}; /// Tower [`Service`](tower::Service) for generated a [`PresignedRequest`] from the AWS middleware. #[derive(Default, Debug)] #[non_exhaustive] pub(crate) struct PresignedRequestService<E> { _phantom: PhantomData<E>, } // Required because of the derive Clone on MapRequestService. // Manually implemented to avoid requiring errors to implement Clone. impl<E> Clone for PresignedRequestService<E> { fn clone(&self) -> Self { Self { _phantom: Default::default(), } } } impl<E> PresignedRequestService<E> { /// Creates a new `PresignedRequestService` pub(crate) fn new() -> Self { Self { _phantom: Default::default(), } } } impl<E> tower::Service<operation::Request> for PresignedRequestService<E> { type Response = PresignedRequest; type Error = E; type Future = Ready<Result<PresignedRequest, E>>; fn poll_ready(&mut self, _cx: &mut Context<'_>) -> Poll<Result<(), Self::Error>> { Poll::Ready(Ok(())) } fn call(&mut self, req: operation::Request) -> Self::Future { let (mut req, _) = req.into_parts(); // Remove user agent headers since the request will not be executed by the AWS Rust SDK. req.headers_mut().remove(USER_AGENT); req.headers_mut().remove("X-Amz-User-Agent"); ready(Ok(PresignedRequest::new(req.map(|_| ())))) } } } aws/rust-runtime/aws-inlineable/src/presigning.rs +171 −179 Original line number Diff line number Diff line Loading @@ -5,8 +5,6 @@ //! Presigned request types and configuration. /// Presigning config and builder pub mod config { use std::fmt; use std::time::{Duration, SystemTime}; Loading @@ -29,13 +27,13 @@ pub mod config { /// Credential expiration time takes priority over the `expires_in` value. /// If the credentials used to sign the request expire before the presigned request is /// set to expire, then the presigned request will become invalid. pub fn expires_in(expires_in: Duration) -> Result<PresigningConfig, Error> { pub fn expires_in(expires_in: Duration) -> Result<PresigningConfig, PresigningConfigError> { Self::builder().expires_in(expires_in).build() } /// Creates a new builder for creating a `PresigningConfig`. pub fn builder() -> Builder { Builder::default() pub fn builder() -> PresigningConfigBuilder { PresigningConfigBuilder::default() } /// Returns the amount of time the presigned request should be valid for. Loading @@ -61,13 +59,13 @@ pub mod config { /// `PresigningConfig` build errors. #[derive(Debug)] pub struct Error { pub struct PresigningConfigError { kind: ErrorKind, } impl std::error::Error for Error {} impl std::error::Error for PresigningConfigError {} impl fmt::Display for Error { impl fmt::Display for PresigningConfigError { fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { match self.kind { ErrorKind::ExpiresInDurationTooLong => { Loading @@ -78,7 +76,7 @@ pub mod config { } } impl From<ErrorKind> for Error { impl From<ErrorKind> for PresigningConfigError { fn from(kind: ErrorKind) -> Self { Self { kind } } Loading @@ -87,12 +85,12 @@ pub mod config { /// Builder used to create `PresigningConfig`. #[non_exhaustive] #[derive(Default, Debug)] pub struct Builder { pub struct PresigningConfigBuilder { start_time: Option<SystemTime>, expires_in: Option<Duration>, } impl Builder { impl PresigningConfigBuilder { /// Sets the start time for the presigned request. /// /// The request will start to be valid at this time, and will cease to be valid after Loading Loading @@ -143,7 +141,7 @@ pub mod config { /// Builds the `PresigningConfig`. This will error if `expires_in` is not /// given, or if it's longer than one week. pub fn build(self) -> Result<PresigningConfig, Error> { pub fn build(self) -> Result<PresigningConfig, PresigningConfigError> { let expires_in = self.expires_in.ok_or(ErrorKind::ExpiresInRequired)?; if expires_in > ONE_WEEK { return Err(ErrorKind::ExpiresInDurationTooLong.into()); Loading @@ -154,11 +152,6 @@ pub mod config { }) } } } /// Presigned request pub mod request { use std::fmt::{Debug, Formatter}; /// Represents a presigned request. This only includes the HTTP request method, URI, and headers. /// Loading Loading @@ -199,8 +192,8 @@ pub mod request { } } impl Debug for PresignedRequest { fn fmt(&self, f: &mut Formatter<'_>) -> std::fmt::Result { impl fmt::Debug for PresignedRequest { fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { f.debug_struct("PresignedRequest") .field("method", self.method()) .field("uri", self.uri()) Loading @@ -222,12 +215,11 @@ pub mod request { builder } } } /// Tower middleware service for creating presigned requests #[allow(dead_code)] pub(crate) mod service { use crate::presigning::request::PresignedRequest; use super::PresignedRequest; use aws_smithy_http::operation; use http::header::USER_AGENT; use std::future::{ready, Ready}; Loading aws/sdk-codegen/src/main/kotlin/software/amazon/smithy/rustsdk/AwsFluentClientDecorator.kt +3 −2 Original line number Diff line number Diff line Loading @@ -96,9 +96,10 @@ class AwsFluentClientDecorator : ClientCodegenDecorator { val generics = AwsClientGenerics(types) FluentClientGenerator( codegenContext, generics, reexportSmithyClientBuilder = false, generics = generics, customizations = listOf( AwsPresignedFluentBuilderMethod(runtimeConfig), AwsPresignedFluentBuilderMethod(codegenContext, runtimeConfig), AwsFluentClientDocs(codegenContext), ), retryClassifier = AwsRuntimeType.awsHttp(runtimeConfig).resolve("retry::AwsResponseRetryClassifier"), Loading aws/sdk-codegen/src/main/kotlin/software/amazon/smithy/rustsdk/AwsPresigningDecorator.kt +31 −19 Original line number Diff line number Diff line Loading @@ -30,7 +30,6 @@ import software.amazon.smithy.rust.codegen.core.rustlang.rustBlockTemplate import software.amazon.smithy.rust.codegen.core.rustlang.rustTemplate import software.amazon.smithy.rust.codegen.core.rustlang.withBlock import software.amazon.smithy.rust.codegen.core.rustlang.writable import software.amazon.smithy.rust.codegen.core.smithy.CodegenContext import software.amazon.smithy.rust.codegen.core.smithy.RuntimeConfig import software.amazon.smithy.rust.codegen.core.smithy.RuntimeType import software.amazon.smithy.rust.codegen.core.smithy.customize.OperationCustomization Loading Loading @@ -128,23 +127,23 @@ class AwsPresigningDecorator internal constructor( } class AwsInputPresignedMethod( private val codegenContext: CodegenContext, private val codegenContext: ClientCodegenContext, private val operationShape: OperationShape, ) : OperationCustomization() { private val runtimeConfig = codegenContext.runtimeConfig private val symbolProvider = codegenContext.symbolProvider private val codegenScope = arrayOf( "Error" to AwsRuntimeType.Presigning.resolve("config::Error"), "PresignedRequest" to AwsRuntimeType.Presigning.resolve("request::PresignedRequest"), "PresignedRequestService" to AwsRuntimeType.Presigning.resolve("service::PresignedRequestService"), "PresigningConfig" to AwsRuntimeType.Presigning.resolve("config::PresigningConfig"), private val codegenScope = ( presigningTypes(codegenContext) + listOf( "PresignedRequestService" to AwsRuntimeType.presigning(codegenContext) .resolve("service::PresignedRequestService"), "SdkError" to RuntimeType.sdkError(runtimeConfig), "aws_sigv4" to AwsRuntimeType.awsSigv4(runtimeConfig), "sig_auth" to AwsRuntimeType.awsSigAuth(runtimeConfig), "tower" to RuntimeType.Tower, "Middleware" to runtimeConfig.defaultMiddleware(), ) ).toTypedArray() override fun section(section: OperationSection): Writable = writable { Loading Loading @@ -241,14 +240,15 @@ class AwsInputPresignedMethod( } class AwsPresignedFluentBuilderMethod( codegenContext: ClientCodegenContext, runtimeConfig: RuntimeConfig, ) : FluentClientCustomization() { private val codegenScope = arrayOf( "Error" to AwsRuntimeType.Presigning.resolve("config::Error"), "PresignedRequest" to AwsRuntimeType.Presigning.resolve("request::PresignedRequest"), "PresigningConfig" to AwsRuntimeType.Presigning.resolve("config::PresigningConfig"), private val codegenScope = ( presigningTypes(codegenContext) + arrayOf( "Error" to AwsRuntimeType.presigning(codegenContext).resolve("config::Error"), "SdkError" to RuntimeType.sdkError(runtimeConfig), ) ).toTypedArray() override fun section(section: FluentClientSection): Writable = writable { Loading Loading @@ -364,3 +364,15 @@ private fun RustWriter.documentPresignedMethod(hasConfigArg: Boolean) { """, ) } private fun presigningTypes(codegenContext: ClientCodegenContext): List<Pair<String, Any>> = when (codegenContext.settings.codegenConfig.enableNewCrateOrganizationScheme) { true -> listOf( "PresignedRequest" to AwsRuntimeType.presigning(codegenContext).resolve("PresignedRequest"), "PresigningConfig" to AwsRuntimeType.presigning(codegenContext).resolve("PresigningConfig"), ) else -> listOf( "PresignedRequest" to AwsRuntimeType.presigning(codegenContext).resolve("request::PresignedRequest"), "PresigningConfig" to AwsRuntimeType.presigning(codegenContext).resolve("config::PresigningConfig"), ) } Loading
aws/rust-runtime/aws-inlineable/src/lib.rs +2 −0 Original line number Diff line number Diff line Loading @@ -24,6 +24,8 @@ pub mod no_credentials; /// Support types required for adding presigning to an operation in a generated service. pub mod presigning; // TODO(CrateReorganization): Delete the `old_presigning` module pub mod old_presigning; /// Special logic for extracting request IDs from S3's responses. pub mod s3_request_id; Loading
aws/rust-runtime/aws-inlineable/src/old_presigning.rs 0 → 100644 +282 −0 Original line number Diff line number Diff line /* * Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. * SPDX-License-Identifier: Apache-2.0 */ //! Presigned request types and configuration. /// Presigning config and builder pub mod config { use std::fmt; use std::time::{Duration, SystemTime}; const ONE_WEEK: Duration = Duration::from_secs(604800); /// Presigning config values required for creating a presigned request. #[non_exhaustive] #[derive(Debug, Clone)] pub struct PresigningConfig { start_time: SystemTime, expires_in: Duration, } impl PresigningConfig { /// Creates a `PresigningConfig` with the given `expires_in` duration. /// /// The `expires_in` duration is the total amount of time the presigned request should /// be valid for. Other config values are defaulted. /// /// Credential expiration time takes priority over the `expires_in` value. /// If the credentials used to sign the request expire before the presigned request is /// set to expire, then the presigned request will become invalid. pub fn expires_in(expires_in: Duration) -> Result<PresigningConfig, Error> { Self::builder().expires_in(expires_in).build() } /// Creates a new builder for creating a `PresigningConfig`. pub fn builder() -> Builder { Builder::default() } /// Returns the amount of time the presigned request should be valid for. pub fn expires(&self) -> Duration { self.expires_in } /// Returns the start time. The presigned request will be valid between this and the end /// time produced by adding the `expires()` value to it. pub fn start_time(&self) -> SystemTime { self.start_time } } #[derive(Debug)] enum ErrorKind { /// Presigned requests cannot be valid for longer than one week. ExpiresInDurationTooLong, /// The `PresigningConfig` builder requires a value for `expires_in`. ExpiresInRequired, } /// `PresigningConfig` build errors. #[derive(Debug)] pub struct Error { kind: ErrorKind, } impl std::error::Error for Error {} impl fmt::Display for Error { fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { match self.kind { ErrorKind::ExpiresInDurationTooLong => { write!(f, "`expires_in` must be no longer than one week") } ErrorKind::ExpiresInRequired => write!(f, "`expires_in` is required"), } } } impl From<ErrorKind> for Error { fn from(kind: ErrorKind) -> Self { Self { kind } } } /// Builder used to create `PresigningConfig`. #[non_exhaustive] #[derive(Default, Debug)] pub struct Builder { start_time: Option<SystemTime>, expires_in: Option<Duration>, } impl Builder { /// Sets the start time for the presigned request. /// /// The request will start to be valid at this time, and will cease to be valid after /// the end time, which can be determined by adding the `expires_in` duration to this /// start time. If not specified, this will default to the current time. /// /// Optional. pub fn start_time(mut self, start_time: SystemTime) -> Self { self.set_start_time(Some(start_time)); self } /// Sets the start time for the presigned request. /// /// The request will start to be valid at this time, and will cease to be valid after /// the end time, which can be determined by adding the `expires_in` duration to this /// start time. If not specified, this will default to the current time. /// /// Optional. pub fn set_start_time(&mut self, start_time: Option<SystemTime>) { self.start_time = start_time; } /// Sets how long the request should be valid after the `start_time` (which defaults /// to the current time). /// /// Credential expiration time takes priority over the `expires_in` value. /// If the credentials used to sign the request expire before the presigned request is /// set to expire, then the presigned request will become invalid. /// /// Required. pub fn expires_in(mut self, expires_in: Duration) -> Self { self.set_expires_in(Some(expires_in)); self } /// Sets how long the request should be valid after the `start_time` (which defaults /// to the current time). /// /// Credential expiration time takes priority over the `expires_in` value. /// If the credentials used to sign the request expire before the presigned request is /// set to expire, then the presigned request will become invalid. /// /// Required. pub fn set_expires_in(&mut self, expires_in: Option<Duration>) { self.expires_in = expires_in; } /// Builds the `PresigningConfig`. This will error if `expires_in` is not /// given, or if it's longer than one week. pub fn build(self) -> Result<PresigningConfig, Error> { let expires_in = self.expires_in.ok_or(ErrorKind::ExpiresInRequired)?; if expires_in > ONE_WEEK { return Err(ErrorKind::ExpiresInDurationTooLong.into()); } Ok(PresigningConfig { start_time: self.start_time.unwrap_or_else(SystemTime::now), expires_in, }) } } } /// Presigned request pub mod request { use std::fmt::{Debug, Formatter}; /// Represents a presigned request. This only includes the HTTP request method, URI, and headers. /// /// **This struct has conversion convenience functions:** /// /// - [`PresignedRequest::to_http_request<B>`][Self::to_http_request] returns an [`http::Request<B>`](https://docs.rs/http/0.2.6/http/request/struct.Request.html) /// - [`PresignedRequest::into`](#impl-From<PresignedRequest>) returns an [`http::request::Builder`](https://docs.rs/http/0.2.6/http/request/struct.Builder.html) #[non_exhaustive] pub struct PresignedRequest(http::Request<()>); impl PresignedRequest { pub(crate) fn new(inner: http::Request<()>) -> Self { Self(inner) } /// Returns the HTTP request method. pub fn method(&self) -> &http::Method { self.0.method() } /// Returns the HTTP request URI. pub fn uri(&self) -> &http::Uri { self.0.uri() } /// Returns any HTTP headers that need to go along with the request, except for `Host`, /// which should be sent based on the endpoint in the URI by the HTTP client rather than /// added directly. pub fn headers(&self) -> &http::HeaderMap<http::HeaderValue> { self.0.headers() } /// Given a body, convert this `PresignedRequest` into an `http::Request` pub fn to_http_request<B>(self, body: B) -> Result<http::Request<B>, http::Error> { let builder: http::request::Builder = self.into(); builder.body(body) } } impl Debug for PresignedRequest { fn fmt(&self, f: &mut Formatter<'_>) -> std::fmt::Result { f.debug_struct("PresignedRequest") .field("method", self.method()) .field("uri", self.uri()) .field("headers", self.headers()) .finish() } } impl From<PresignedRequest> for http::request::Builder { fn from(req: PresignedRequest) -> Self { let mut builder = http::request::Builder::new() .uri(req.uri()) .method(req.method()); if let Some(headers) = builder.headers_mut() { *headers = req.headers().clone(); } builder } } } /// Tower middleware service for creating presigned requests #[allow(dead_code)] pub(crate) mod service { use super::request::PresignedRequest; use aws_smithy_http::operation; use http::header::USER_AGENT; use std::future::{ready, Ready}; use std::marker::PhantomData; use std::task::{Context, Poll}; /// Tower [`Service`](tower::Service) for generated a [`PresignedRequest`] from the AWS middleware. #[derive(Default, Debug)] #[non_exhaustive] pub(crate) struct PresignedRequestService<E> { _phantom: PhantomData<E>, } // Required because of the derive Clone on MapRequestService. // Manually implemented to avoid requiring errors to implement Clone. impl<E> Clone for PresignedRequestService<E> { fn clone(&self) -> Self { Self { _phantom: Default::default(), } } } impl<E> PresignedRequestService<E> { /// Creates a new `PresignedRequestService` pub(crate) fn new() -> Self { Self { _phantom: Default::default(), } } } impl<E> tower::Service<operation::Request> for PresignedRequestService<E> { type Response = PresignedRequest; type Error = E; type Future = Ready<Result<PresignedRequest, E>>; fn poll_ready(&mut self, _cx: &mut Context<'_>) -> Poll<Result<(), Self::Error>> { Poll::Ready(Ok(())) } fn call(&mut self, req: operation::Request) -> Self::Future { let (mut req, _) = req.into_parts(); // Remove user agent headers since the request will not be executed by the AWS Rust SDK. req.headers_mut().remove(USER_AGENT); req.headers_mut().remove("X-Amz-User-Agent"); ready(Ok(PresignedRequest::new(req.map(|_| ())))) } } }
aws/rust-runtime/aws-inlineable/src/presigning.rs +171 −179 Original line number Diff line number Diff line Loading @@ -5,8 +5,6 @@ //! Presigned request types and configuration. /// Presigning config and builder pub mod config { use std::fmt; use std::time::{Duration, SystemTime}; Loading @@ -29,13 +27,13 @@ pub mod config { /// Credential expiration time takes priority over the `expires_in` value. /// If the credentials used to sign the request expire before the presigned request is /// set to expire, then the presigned request will become invalid. pub fn expires_in(expires_in: Duration) -> Result<PresigningConfig, Error> { pub fn expires_in(expires_in: Duration) -> Result<PresigningConfig, PresigningConfigError> { Self::builder().expires_in(expires_in).build() } /// Creates a new builder for creating a `PresigningConfig`. pub fn builder() -> Builder { Builder::default() pub fn builder() -> PresigningConfigBuilder { PresigningConfigBuilder::default() } /// Returns the amount of time the presigned request should be valid for. Loading @@ -61,13 +59,13 @@ pub mod config { /// `PresigningConfig` build errors. #[derive(Debug)] pub struct Error { pub struct PresigningConfigError { kind: ErrorKind, } impl std::error::Error for Error {} impl std::error::Error for PresigningConfigError {} impl fmt::Display for Error { impl fmt::Display for PresigningConfigError { fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { match self.kind { ErrorKind::ExpiresInDurationTooLong => { Loading @@ -78,7 +76,7 @@ pub mod config { } } impl From<ErrorKind> for Error { impl From<ErrorKind> for PresigningConfigError { fn from(kind: ErrorKind) -> Self { Self { kind } } Loading @@ -87,12 +85,12 @@ pub mod config { /// Builder used to create `PresigningConfig`. #[non_exhaustive] #[derive(Default, Debug)] pub struct Builder { pub struct PresigningConfigBuilder { start_time: Option<SystemTime>, expires_in: Option<Duration>, } impl Builder { impl PresigningConfigBuilder { /// Sets the start time for the presigned request. /// /// The request will start to be valid at this time, and will cease to be valid after Loading Loading @@ -143,7 +141,7 @@ pub mod config { /// Builds the `PresigningConfig`. This will error if `expires_in` is not /// given, or if it's longer than one week. pub fn build(self) -> Result<PresigningConfig, Error> { pub fn build(self) -> Result<PresigningConfig, PresigningConfigError> { let expires_in = self.expires_in.ok_or(ErrorKind::ExpiresInRequired)?; if expires_in > ONE_WEEK { return Err(ErrorKind::ExpiresInDurationTooLong.into()); Loading @@ -154,11 +152,6 @@ pub mod config { }) } } } /// Presigned request pub mod request { use std::fmt::{Debug, Formatter}; /// Represents a presigned request. This only includes the HTTP request method, URI, and headers. /// Loading Loading @@ -199,8 +192,8 @@ pub mod request { } } impl Debug for PresignedRequest { fn fmt(&self, f: &mut Formatter<'_>) -> std::fmt::Result { impl fmt::Debug for PresignedRequest { fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { f.debug_struct("PresignedRequest") .field("method", self.method()) .field("uri", self.uri()) Loading @@ -222,12 +215,11 @@ pub mod request { builder } } } /// Tower middleware service for creating presigned requests #[allow(dead_code)] pub(crate) mod service { use crate::presigning::request::PresignedRequest; use super::PresignedRequest; use aws_smithy_http::operation; use http::header::USER_AGENT; use std::future::{ready, Ready}; Loading
aws/sdk-codegen/src/main/kotlin/software/amazon/smithy/rustsdk/AwsFluentClientDecorator.kt +3 −2 Original line number Diff line number Diff line Loading @@ -96,9 +96,10 @@ class AwsFluentClientDecorator : ClientCodegenDecorator { val generics = AwsClientGenerics(types) FluentClientGenerator( codegenContext, generics, reexportSmithyClientBuilder = false, generics = generics, customizations = listOf( AwsPresignedFluentBuilderMethod(runtimeConfig), AwsPresignedFluentBuilderMethod(codegenContext, runtimeConfig), AwsFluentClientDocs(codegenContext), ), retryClassifier = AwsRuntimeType.awsHttp(runtimeConfig).resolve("retry::AwsResponseRetryClassifier"), Loading
aws/sdk-codegen/src/main/kotlin/software/amazon/smithy/rustsdk/AwsPresigningDecorator.kt +31 −19 Original line number Diff line number Diff line Loading @@ -30,7 +30,6 @@ import software.amazon.smithy.rust.codegen.core.rustlang.rustBlockTemplate import software.amazon.smithy.rust.codegen.core.rustlang.rustTemplate import software.amazon.smithy.rust.codegen.core.rustlang.withBlock import software.amazon.smithy.rust.codegen.core.rustlang.writable import software.amazon.smithy.rust.codegen.core.smithy.CodegenContext import software.amazon.smithy.rust.codegen.core.smithy.RuntimeConfig import software.amazon.smithy.rust.codegen.core.smithy.RuntimeType import software.amazon.smithy.rust.codegen.core.smithy.customize.OperationCustomization Loading Loading @@ -128,23 +127,23 @@ class AwsPresigningDecorator internal constructor( } class AwsInputPresignedMethod( private val codegenContext: CodegenContext, private val codegenContext: ClientCodegenContext, private val operationShape: OperationShape, ) : OperationCustomization() { private val runtimeConfig = codegenContext.runtimeConfig private val symbolProvider = codegenContext.symbolProvider private val codegenScope = arrayOf( "Error" to AwsRuntimeType.Presigning.resolve("config::Error"), "PresignedRequest" to AwsRuntimeType.Presigning.resolve("request::PresignedRequest"), "PresignedRequestService" to AwsRuntimeType.Presigning.resolve("service::PresignedRequestService"), "PresigningConfig" to AwsRuntimeType.Presigning.resolve("config::PresigningConfig"), private val codegenScope = ( presigningTypes(codegenContext) + listOf( "PresignedRequestService" to AwsRuntimeType.presigning(codegenContext) .resolve("service::PresignedRequestService"), "SdkError" to RuntimeType.sdkError(runtimeConfig), "aws_sigv4" to AwsRuntimeType.awsSigv4(runtimeConfig), "sig_auth" to AwsRuntimeType.awsSigAuth(runtimeConfig), "tower" to RuntimeType.Tower, "Middleware" to runtimeConfig.defaultMiddleware(), ) ).toTypedArray() override fun section(section: OperationSection): Writable = writable { Loading Loading @@ -241,14 +240,15 @@ class AwsInputPresignedMethod( } class AwsPresignedFluentBuilderMethod( codegenContext: ClientCodegenContext, runtimeConfig: RuntimeConfig, ) : FluentClientCustomization() { private val codegenScope = arrayOf( "Error" to AwsRuntimeType.Presigning.resolve("config::Error"), "PresignedRequest" to AwsRuntimeType.Presigning.resolve("request::PresignedRequest"), "PresigningConfig" to AwsRuntimeType.Presigning.resolve("config::PresigningConfig"), private val codegenScope = ( presigningTypes(codegenContext) + arrayOf( "Error" to AwsRuntimeType.presigning(codegenContext).resolve("config::Error"), "SdkError" to RuntimeType.sdkError(runtimeConfig), ) ).toTypedArray() override fun section(section: FluentClientSection): Writable = writable { Loading Loading @@ -364,3 +364,15 @@ private fun RustWriter.documentPresignedMethod(hasConfigArg: Boolean) { """, ) } private fun presigningTypes(codegenContext: ClientCodegenContext): List<Pair<String, Any>> = when (codegenContext.settings.codegenConfig.enableNewCrateOrganizationScheme) { true -> listOf( "PresignedRequest" to AwsRuntimeType.presigning(codegenContext).resolve("PresignedRequest"), "PresigningConfig" to AwsRuntimeType.presigning(codegenContext).resolve("PresigningConfig"), ) else -> listOf( "PresignedRequest" to AwsRuntimeType.presigning(codegenContext).resolve("request::PresignedRequest"), "PresigningConfig" to AwsRuntimeType.presigning(codegenContext).resolve("config::PresigningConfig"), ) }