mirror of
https://github.com/minio/minio-rs.git
synced 2025-12-06 23:36:52 +08:00
Add documentation and few enhancements (#45)
Signed-off-by: Bala.FA <bala@minio.io>
This commit is contained in:
parent
aee702f337
commit
28e7fee8fa
1
.github/workflows/rust.yml
vendored
1
.github/workflows/rust.yml
vendored
@ -24,6 +24,7 @@ jobs:
|
|||||||
|
|
||||||
- name: Run tests
|
- name: Run tests
|
||||||
run: |
|
run: |
|
||||||
|
truncate --size=6M asiaphotos-2015.zip
|
||||||
./tests/start-server.sh
|
./tests/start-server.sh
|
||||||
export SERVER_ENDPOINT=localhost:9000
|
export SERVER_ENDPOINT=localhost:9000
|
||||||
export ACCESS_KEY=minioadmin
|
export ACCESS_KEY=minioadmin
|
||||||
|
|||||||
697
src/s3/args.rs
697
src/s3/args.rs
File diff suppressed because it is too large
Load Diff
@ -13,6 +13,8 @@
|
|||||||
// See the License for the specific language governing permissions and
|
// See the License for the specific language governing permissions and
|
||||||
// limitations under the License.
|
// limitations under the License.
|
||||||
|
|
||||||
|
//! S3 client to perform bucket and object operations
|
||||||
|
|
||||||
use crate::s3::args::*;
|
use crate::s3::args::*;
|
||||||
use crate::s3::creds::Provider;
|
use crate::s3::creds::Provider;
|
||||||
use crate::s3::error::{Error, ErrorResponse};
|
use crate::s3::error::{Error, ErrorResponse};
|
||||||
@ -201,6 +203,10 @@ fn parse_list_objects_common_prefixes(
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Debug, Default)]
|
#[derive(Clone, Debug, Default)]
|
||||||
|
/// Simple Storage Service (aka S3) client to perform bucket and object operations.
|
||||||
|
///
|
||||||
|
/// If credential provider is passed, all S3 operation requests are signed using AWS Signature
|
||||||
|
/// Version 4; else they are performed anonymously.
|
||||||
pub struct Client<'a> {
|
pub struct Client<'a> {
|
||||||
client: reqwest::Client,
|
client: reqwest::Client,
|
||||||
base_url: BaseUrl,
|
base_url: BaseUrl,
|
||||||
@ -209,6 +215,22 @@ pub struct Client<'a> {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl<'a> Client<'a> {
|
impl<'a> Client<'a> {
|
||||||
|
/// Returns a S3 client with given base URL.
|
||||||
|
///
|
||||||
|
/// # Examples
|
||||||
|
///
|
||||||
|
/// ```
|
||||||
|
/// use minio::s3::client::Client;
|
||||||
|
/// use minio::s3::creds::StaticProvider;
|
||||||
|
/// use minio::s3::http::BaseUrl;
|
||||||
|
/// let mut base_url = BaseUrl::from_string("play.min.io".to_string()).unwrap();
|
||||||
|
/// let static_provider = StaticProvider::new(
|
||||||
|
/// "Q3AM3UQ867SPQQA43P2F",
|
||||||
|
/// "zuf+tfteSlswRu7BJ86wekitnifILbZam1KYY3TG",
|
||||||
|
/// None,
|
||||||
|
/// );
|
||||||
|
/// let client = Client::new(base_url.clone(), Some(&static_provider), None, None).unwrap();
|
||||||
|
/// ```
|
||||||
pub fn new(
|
pub fn new(
|
||||||
base_url: BaseUrl,
|
base_url: BaseUrl,
|
||||||
provider: Option<&(dyn Provider + Send + Sync)>,
|
provider: Option<&(dyn Provider + Send + Sync)>,
|
||||||
@ -626,6 +648,7 @@ impl<'a> Client<'a> {
|
|||||||
Ok(location)
|
Ok(location)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Executes [AbortMultipartUpload](https://docs.aws.amazon.com/AmazonS3/latest/API/API_AbortMultipartUpload.html) S3 API
|
||||||
pub async fn abort_multipart_upload(
|
pub async fn abort_multipart_upload(
|
||||||
&self,
|
&self,
|
||||||
args: &AbortMultipartUploadArgs<'_>,
|
args: &AbortMultipartUploadArgs<'_>,
|
||||||
@ -712,6 +735,7 @@ impl<'a> Client<'a> {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Executes [CompleteMultipartUpload](https://docs.aws.amazon.com/AmazonS3/latest/API/API_CompleteMultipartUpload.html) S3 API
|
||||||
pub async fn complete_multipart_upload(
|
pub async fn complete_multipart_upload(
|
||||||
&self,
|
&self,
|
||||||
args: &CompleteMultipartUploadArgs<'_>,
|
args: &CompleteMultipartUploadArgs<'_>,
|
||||||
@ -1131,6 +1155,7 @@ impl<'a> Client<'a> {
|
|||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Executes [CreateMultipartUpload](https://docs.aws.amazon.com/AmazonS3/latest/API/API_CreateMultipartUpload.html) S3 API
|
||||||
pub async fn create_multipart_upload(
|
pub async fn create_multipart_upload(
|
||||||
&self,
|
&self,
|
||||||
args: &CreateMultipartUploadArgs<'_>,
|
args: &CreateMultipartUploadArgs<'_>,
|
||||||
@ -2434,6 +2459,7 @@ impl<'a> Client<'a> {
|
|||||||
))
|
))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Executes [ListObjects](https://docs.aws.amazon.com/AmazonS3/latest/API/API_ListObjects.html) S3 API
|
||||||
pub async fn list_objects_v1(
|
pub async fn list_objects_v1(
|
||||||
&self,
|
&self,
|
||||||
args: &ListObjectsV1Args<'_>,
|
args: &ListObjectsV1Args<'_>,
|
||||||
@ -2500,6 +2526,7 @@ impl<'a> Client<'a> {
|
|||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Executes [ListObjectsV2](https://docs.aws.amazon.com/AmazonS3/latest/API/API_ListObjectsV2.html) S3 API
|
||||||
pub async fn list_objects_v2(
|
pub async fn list_objects_v2(
|
||||||
&self,
|
&self,
|
||||||
args: &ListObjectsV2Args<'_>,
|
args: &ListObjectsV2Args<'_>,
|
||||||
@ -2584,6 +2611,7 @@ impl<'a> Client<'a> {
|
|||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Executes [ListObjectVersions](https://docs.aws.amazon.com/AmazonS3/latest/API/API_ListObjectVersions.html) S3 API
|
||||||
pub async fn list_object_versions(
|
pub async fn list_object_versions(
|
||||||
&self,
|
&self,
|
||||||
args: &ListObjectVersionsArgs<'_>,
|
args: &ListObjectVersionsArgs<'_>,
|
||||||
@ -2980,6 +3008,7 @@ impl<'a> Client<'a> {
|
|||||||
res
|
res
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Executes [PutObject](https://docs.aws.amazon.com/AmazonS3/latest/API/API_PutObject.html) S3 API
|
||||||
pub async fn put_object_api(
|
pub async fn put_object_api(
|
||||||
&self,
|
&self,
|
||||||
args: &PutObjectApiArgs<'_>,
|
args: &PutObjectApiArgs<'_>,
|
||||||
@ -3099,6 +3128,7 @@ impl<'a> Client<'a> {
|
|||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Executes [DeleteObjects](https://docs.aws.amazon.com/AmazonS3/latest/API/API_DeleteObjects.html) S3 API
|
||||||
pub async fn remove_objects_api(
|
pub async fn remove_objects_api(
|
||||||
&self,
|
&self,
|
||||||
args: &RemoveObjectsApiArgs<'_>,
|
args: &RemoveObjectsApiArgs<'_>,
|
||||||
@ -3779,6 +3809,7 @@ impl<'a> Client<'a> {
|
|||||||
.await
|
.await
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Executes [UploadPart](https://docs.aws.amazon.com/AmazonS3/latest/API/API_UploadPart.html) S3 API
|
||||||
pub async fn upload_part(
|
pub async fn upload_part(
|
||||||
&self,
|
&self,
|
||||||
args: &UploadPartArgs<'_>,
|
args: &UploadPartArgs<'_>,
|
||||||
@ -3803,6 +3834,7 @@ impl<'a> Client<'a> {
|
|||||||
self.put_object_api(&poa_args).await
|
self.put_object_api(&poa_args).await
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Executes [UploadPartCopy](https://docs.aws.amazon.com/AmazonS3/latest/API/API_UploadPartCopy.html) S3 API
|
||||||
pub async fn upload_part_copy(
|
pub async fn upload_part_copy(
|
||||||
&self,
|
&self,
|
||||||
args: &UploadPartCopyArgs<'_>,
|
args: &UploadPartCopyArgs<'_>,
|
||||||
|
|||||||
@ -13,23 +13,36 @@
|
|||||||
// See the License for the specific language governing permissions and
|
// See the License for the specific language governing permissions and
|
||||||
// limitations under the License.
|
// limitations under the License.
|
||||||
|
|
||||||
|
//! Credential providers
|
||||||
|
|
||||||
#[derive(Clone, Debug, Default)]
|
#[derive(Clone, Debug, Default)]
|
||||||
|
/// Credentials contain access key, secret key and session token optionally
|
||||||
pub struct Credentials {
|
pub struct Credentials {
|
||||||
pub access_key: String,
|
pub access_key: String,
|
||||||
pub secret_key: String,
|
pub secret_key: String,
|
||||||
pub session_token: Option<String>,
|
pub session_token: Option<String>,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Provider trait to fetch credentials
|
||||||
pub trait Provider: std::fmt::Debug {
|
pub trait Provider: std::fmt::Debug {
|
||||||
fn fetch(&self) -> Credentials;
|
fn fetch(&self) -> Credentials;
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
/// Static credential provider
|
||||||
pub struct StaticProvider {
|
pub struct StaticProvider {
|
||||||
creds: Credentials,
|
creds: Credentials,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl StaticProvider {
|
impl StaticProvider {
|
||||||
|
/// Returns a static provider with given access key, secret key and optional session token
|
||||||
|
///
|
||||||
|
/// # Examples
|
||||||
|
///
|
||||||
|
/// ```
|
||||||
|
/// use minio::s3::creds::StaticProvider;
|
||||||
|
/// let provider = StaticProvider::new("minioadmin", "minio123", None);
|
||||||
|
/// ```
|
||||||
pub fn new(access_key: &str, secret_key: &str, session_token: Option<&str>) -> StaticProvider {
|
pub fn new(access_key: &str, secret_key: &str, session_token: Option<&str>) -> StaticProvider {
|
||||||
StaticProvider {
|
StaticProvider {
|
||||||
creds: Credentials {
|
creds: Credentials {
|
||||||
|
|||||||
@ -13,6 +13,8 @@
|
|||||||
// See the License for the specific language governing permissions and
|
// See the License for the specific language governing permissions and
|
||||||
// limitations under the License.
|
// limitations under the License.
|
||||||
|
|
||||||
|
//! Error definitions for S3 operations
|
||||||
|
|
||||||
extern crate alloc;
|
extern crate alloc;
|
||||||
use crate::s3::utils::get_default_text;
|
use crate::s3::utils::get_default_text;
|
||||||
use bytes::{Buf, Bytes};
|
use bytes::{Buf, Bytes};
|
||||||
@ -20,6 +22,7 @@ use std::fmt;
|
|||||||
use xmltree::Element;
|
use xmltree::Element;
|
||||||
|
|
||||||
#[derive(Clone, Debug, Default)]
|
#[derive(Clone, Debug, Default)]
|
||||||
|
/// Error response for S3 operations
|
||||||
pub struct ErrorResponse {
|
pub struct ErrorResponse {
|
||||||
pub code: String,
|
pub code: String,
|
||||||
pub message: String,
|
pub message: String,
|
||||||
@ -50,6 +53,7 @@ impl ErrorResponse {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Debug)]
|
#[derive(Debug)]
|
||||||
|
/// Error definitions
|
||||||
pub enum Error {
|
pub enum Error {
|
||||||
TimeParseError(chrono::ParseError),
|
TimeParseError(chrono::ParseError),
|
||||||
InvalidUrl(http::uri::InvalidUri),
|
InvalidUrl(http::uri::InvalidUri),
|
||||||
@ -74,6 +78,7 @@ pub enum Error {
|
|||||||
InvalidPartNumber(String),
|
InvalidPartNumber(String),
|
||||||
EmptyParts(String),
|
EmptyParts(String),
|
||||||
InvalidRetentionMode(String),
|
InvalidRetentionMode(String),
|
||||||
|
InvalidRetentionConfig(String),
|
||||||
InvalidMinPartSize(usize),
|
InvalidMinPartSize(usize),
|
||||||
InvalidMaxPartSize(usize),
|
InvalidMaxPartSize(usize),
|
||||||
InvalidObjectSize(usize),
|
InvalidObjectSize(usize),
|
||||||
@ -128,6 +133,7 @@ impl fmt::Display for Error {
|
|||||||
Error::InvalidPartNumber(m) => write!(f, "{}", m),
|
Error::InvalidPartNumber(m) => write!(f, "{}", m),
|
||||||
Error::EmptyParts(m) => write!(f, "{}", m),
|
Error::EmptyParts(m) => write!(f, "{}", m),
|
||||||
Error::InvalidRetentionMode(m) => write!(f, "invalid retention mode {}", m),
|
Error::InvalidRetentionMode(m) => write!(f, "invalid retention mode {}", m),
|
||||||
|
Error::InvalidRetentionConfig(m) => write!(f, "invalid retention configuration; {}", m),
|
||||||
Error::InvalidMinPartSize(s) => write!(f, "part size {} is not supported; minimum allowed 5MiB", s),
|
Error::InvalidMinPartSize(s) => write!(f, "part size {} is not supported; minimum allowed 5MiB", s),
|
||||||
Error::InvalidMaxPartSize(s) => write!(f, "part size {} is not supported; maximum allowed 5GiB", s),
|
Error::InvalidMaxPartSize(s) => write!(f, "part size {} is not supported; maximum allowed 5GiB", s),
|
||||||
Error::InvalidObjectSize(s) => write!(f, "object size {} is not supported; maximum allowed 5TiB", s),
|
Error::InvalidObjectSize(s) => write!(f, "object size {} is not supported; maximum allowed 5TiB", s),
|
||||||
|
|||||||
@ -13,6 +13,8 @@
|
|||||||
// See the License for the specific language governing permissions and
|
// See the License for the specific language governing permissions and
|
||||||
// limitations under the License.
|
// limitations under the License.
|
||||||
|
|
||||||
|
//! HTTP URL definitions
|
||||||
|
|
||||||
use crate::s3::error::Error;
|
use crate::s3::error::Error;
|
||||||
use crate::s3::utils::{to_query_string, Multimap};
|
use crate::s3::utils::{to_query_string, Multimap};
|
||||||
use derivative::Derivative;
|
use derivative::Derivative;
|
||||||
@ -22,6 +24,7 @@ use std::fmt;
|
|||||||
|
|
||||||
#[derive(Derivative)]
|
#[derive(Derivative)]
|
||||||
#[derivative(Clone, Debug, Default)]
|
#[derivative(Clone, Debug, Default)]
|
||||||
|
/// Represents HTTP URL
|
||||||
pub struct Url {
|
pub struct Url {
|
||||||
#[derivative(Default(value = "true"))]
|
#[derivative(Default(value = "true"))]
|
||||||
pub https: bool,
|
pub https: bool,
|
||||||
@ -90,6 +93,7 @@ fn extract_region(host: &str) -> String {
|
|||||||
|
|
||||||
#[derive(Derivative)]
|
#[derive(Derivative)]
|
||||||
#[derivative(Clone, Debug, Default)]
|
#[derivative(Clone, Debug, Default)]
|
||||||
|
/// Represents Base URL of S3 endpoint
|
||||||
pub struct BaseUrl {
|
pub struct BaseUrl {
|
||||||
#[derivative(Default(value = "true"))]
|
#[derivative(Default(value = "true"))]
|
||||||
pub https: bool,
|
pub https: bool,
|
||||||
@ -103,6 +107,7 @@ pub struct BaseUrl {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl BaseUrl {
|
impl BaseUrl {
|
||||||
|
/// Builds URL from base URL for given parameters for S3 operation
|
||||||
pub fn build_url(
|
pub fn build_url(
|
||||||
&self,
|
&self,
|
||||||
method: &Method,
|
method: &Method,
|
||||||
@ -188,6 +193,21 @@ impl BaseUrl {
|
|||||||
Ok(url)
|
Ok(url)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Returns a base URL from given host string
|
||||||
|
///
|
||||||
|
/// # Examples
|
||||||
|
///
|
||||||
|
/// ```
|
||||||
|
/// use minio::s3::http::BaseUrl;
|
||||||
|
/// // Get base URL from host name
|
||||||
|
/// let base_url = BaseUrl::from_string("play.min.io".to_string()).unwrap();
|
||||||
|
/// // Get base URL from host:port
|
||||||
|
/// let base_url = BaseUrl::from_string("play.minio.io:9000".to_string()).unwrap();
|
||||||
|
/// // Get base URL from IPv4 address
|
||||||
|
/// let base_url = BaseUrl::from_string("http://192.168.124.63:9000".to_string()).unwrap();
|
||||||
|
/// // Get base URL from IPv6 address
|
||||||
|
/// let base_url = BaseUrl::from_string("[0:0:0:0:0:ffff:c0a8:7c3f]:9000".to_string()).unwrap();
|
||||||
|
/// ```
|
||||||
pub fn from_string(s: String) -> Result<BaseUrl, Error> {
|
pub fn from_string(s: String) -> Result<BaseUrl, Error> {
|
||||||
let url = s.parse::<Uri>()?;
|
let url = s.parse::<Uri>()?;
|
||||||
|
|
||||||
|
|||||||
@ -13,6 +13,8 @@
|
|||||||
// See the License for the specific language governing permissions and
|
// See the License for the specific language governing permissions and
|
||||||
// limitations under the License.
|
// limitations under the License.
|
||||||
|
|
||||||
|
//! Implementation of Simple Storage Service (aka S3) client
|
||||||
|
|
||||||
pub mod args;
|
pub mod args;
|
||||||
pub mod client;
|
pub mod client;
|
||||||
pub mod creds;
|
pub mod creds;
|
||||||
|
|||||||
@ -13,6 +13,8 @@
|
|||||||
// See the License for the specific language governing permissions and
|
// See the License for the specific language governing permissions and
|
||||||
// limitations under the License.
|
// limitations under the License.
|
||||||
|
|
||||||
|
//! Responses for [minio::s3::client::Client](crate::s3::client::Client) APIs
|
||||||
|
|
||||||
use crate::s3::error::Error;
|
use crate::s3::error::Error;
|
||||||
use crate::s3::types::{
|
use crate::s3::types::{
|
||||||
parse_legal_hold, Bucket, Item, LifecycleConfig, NotificationConfig, ObjectLockConfig,
|
parse_legal_hold, Bucket, Item, LifecycleConfig, NotificationConfig, ObjectLockConfig,
|
||||||
@ -28,23 +30,28 @@ use std::io::BufReader;
|
|||||||
use xmltree::Element;
|
use xmltree::Element;
|
||||||
|
|
||||||
#[derive(Debug)]
|
#[derive(Debug)]
|
||||||
|
/// Response of [list_buckets()](crate::s3::client::Client::list_buckets) API
|
||||||
pub struct ListBucketsResponse {
|
pub struct ListBucketsResponse {
|
||||||
pub headers: HeaderMap,
|
pub headers: HeaderMap,
|
||||||
pub buckets: Vec<Bucket>,
|
pub buckets: Vec<Bucket>,
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Debug)]
|
#[derive(Debug)]
|
||||||
|
/// Base response for bucket operation
|
||||||
pub struct BucketResponse {
|
pub struct BucketResponse {
|
||||||
pub headers: HeaderMap,
|
pub headers: HeaderMap,
|
||||||
pub region: String,
|
pub region: String,
|
||||||
pub bucket_name: String,
|
pub bucket_name: String,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Response of [make_bucket()](crate::s3::client::Client::make_bucket) API
|
||||||
pub type MakeBucketResponse = BucketResponse;
|
pub type MakeBucketResponse = BucketResponse;
|
||||||
|
|
||||||
|
/// Response of [remove_bucket()](crate::s3::client::Client::remove_bucket) API
|
||||||
pub type RemoveBucketResponse = BucketResponse;
|
pub type RemoveBucketResponse = BucketResponse;
|
||||||
|
|
||||||
#[derive(Debug)]
|
#[derive(Debug)]
|
||||||
|
/// Base response for object operation
|
||||||
pub struct ObjectResponse {
|
pub struct ObjectResponse {
|
||||||
pub headers: HeaderMap,
|
pub headers: HeaderMap,
|
||||||
pub region: String,
|
pub region: String,
|
||||||
@ -53,9 +60,11 @@ pub struct ObjectResponse {
|
|||||||
pub version_id: Option<String>,
|
pub version_id: Option<String>,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Response of [remove_object()](crate::s3::client::Client::remove_object) API
|
||||||
pub type RemoveObjectResponse = ObjectResponse;
|
pub type RemoveObjectResponse = ObjectResponse;
|
||||||
|
|
||||||
#[derive(Debug)]
|
#[derive(Debug)]
|
||||||
|
/// Base Upload ID response
|
||||||
pub struct UploadIdResponse {
|
pub struct UploadIdResponse {
|
||||||
pub headers: HeaderMap,
|
pub headers: HeaderMap,
|
||||||
pub region: String,
|
pub region: String,
|
||||||
@ -64,11 +73,14 @@ pub struct UploadIdResponse {
|
|||||||
pub upload_id: String,
|
pub upload_id: String,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Response of [abort_multipart_upload()](crate::s3::client::Client::abort_multipart_upload) API
|
||||||
pub type AbortMultipartUploadResponse = UploadIdResponse;
|
pub type AbortMultipartUploadResponse = UploadIdResponse;
|
||||||
|
|
||||||
|
/// Response of [create_multipart_upload()](crate::s3::client::Client::create_multipart_upload) API
|
||||||
pub type CreateMultipartUploadResponse = UploadIdResponse;
|
pub type CreateMultipartUploadResponse = UploadIdResponse;
|
||||||
|
|
||||||
#[derive(Debug)]
|
#[derive(Debug)]
|
||||||
|
/// Base response for put object
|
||||||
pub struct PutObjectBaseResponse {
|
pub struct PutObjectBaseResponse {
|
||||||
pub headers: HeaderMap,
|
pub headers: HeaderMap,
|
||||||
pub bucket_name: String,
|
pub bucket_name: String,
|
||||||
@ -78,23 +90,32 @@ pub struct PutObjectBaseResponse {
|
|||||||
pub version_id: Option<String>,
|
pub version_id: Option<String>,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Response of [complete_multipart_upload()](crate::s3::client::Client::complete_multipart_upload) API
|
||||||
pub type CompleteMultipartUploadResponse = PutObjectBaseResponse;
|
pub type CompleteMultipartUploadResponse = PutObjectBaseResponse;
|
||||||
|
|
||||||
|
/// Response of [put_object_api()](crate::s3::client::Client::put_object_api) S3 API
|
||||||
pub type PutObjectApiResponse = PutObjectBaseResponse;
|
pub type PutObjectApiResponse = PutObjectBaseResponse;
|
||||||
|
|
||||||
|
/// Response of [upload_part()](crate::s3::client::Client::upload_part) S3 API
|
||||||
pub type UploadPartResponse = PutObjectApiResponse;
|
pub type UploadPartResponse = PutObjectApiResponse;
|
||||||
|
|
||||||
|
/// Response of [put_object()](crate::s3::client::Client::put_object) API
|
||||||
pub type PutObjectResponse = PutObjectApiResponse;
|
pub type PutObjectResponse = PutObjectApiResponse;
|
||||||
|
|
||||||
|
/// Response of [upload_part_copy()](crate::s3::client::Client::upload_part_copy) S3 API
|
||||||
pub type UploadPartCopyResponse = PutObjectApiResponse;
|
pub type UploadPartCopyResponse = PutObjectApiResponse;
|
||||||
|
|
||||||
|
/// Response of [copy_object()](crate::s3::client::Client::copy_object) API
|
||||||
pub type CopyObjectResponse = PutObjectApiResponse;
|
pub type CopyObjectResponse = PutObjectApiResponse;
|
||||||
|
|
||||||
|
/// Response of [compose_object()](crate::s3::client::Client::compose_object) API
|
||||||
pub type ComposeObjectResponse = PutObjectApiResponse;
|
pub type ComposeObjectResponse = PutObjectApiResponse;
|
||||||
|
|
||||||
|
/// Response of [upload_object()](crate::s3::client::Client::upload_object) API
|
||||||
pub type UploadObjectResponse = PutObjectApiResponse;
|
pub type UploadObjectResponse = PutObjectApiResponse;
|
||||||
|
|
||||||
#[derive(Debug)]
|
#[derive(Debug)]
|
||||||
|
/// Response of [stat_object()](crate::s3::client::Client::stat_object) API
|
||||||
pub struct StatObjectResponse {
|
pub struct StatObjectResponse {
|
||||||
pub headers: HeaderMap,
|
pub headers: HeaderMap,
|
||||||
pub region: String,
|
pub region: String,
|
||||||
@ -184,6 +205,7 @@ impl StatObjectResponse {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
/// Error defintion of [remove_objects_api()](crate::s3::client::Client::remove_objects_api) S3 API
|
||||||
pub struct DeleteError {
|
pub struct DeleteError {
|
||||||
pub code: String,
|
pub code: String,
|
||||||
pub message: String,
|
pub message: String,
|
||||||
@ -192,6 +214,7 @@ pub struct DeleteError {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
/// Deleted object defintion of [remove_objects_api()](crate::s3::client::Client::remove_objects_api) S3 API
|
||||||
pub struct DeletedObject {
|
pub struct DeletedObject {
|
||||||
pub name: String,
|
pub name: String,
|
||||||
pub version_id: Option<String>,
|
pub version_id: Option<String>,
|
||||||
@ -200,6 +223,7 @@ pub struct DeletedObject {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
/// Response of [remove_objects_api()](crate::s3::client::Client::remove_objects_api) S3 API
|
||||||
pub struct RemoveObjectsApiResponse {
|
pub struct RemoveObjectsApiResponse {
|
||||||
pub headers: HeaderMap,
|
pub headers: HeaderMap,
|
||||||
pub region: String,
|
pub region: String,
|
||||||
@ -208,9 +232,11 @@ pub struct RemoveObjectsApiResponse {
|
|||||||
pub errors: Vec<DeleteError>,
|
pub errors: Vec<DeleteError>,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Response of [remove_objects()](crate::s3::client::Client::remove_objects) API
|
||||||
pub type RemoveObjectsResponse = RemoveObjectsApiResponse;
|
pub type RemoveObjectsResponse = RemoveObjectsApiResponse;
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
/// Response of [list_objects_v1()](crate::s3::client::Client::list_objects_v1) S3 API
|
||||||
pub struct ListObjectsV1Response {
|
pub struct ListObjectsV1Response {
|
||||||
pub headers: HeaderMap,
|
pub headers: HeaderMap,
|
||||||
pub name: String,
|
pub name: String,
|
||||||
@ -225,6 +251,7 @@ pub struct ListObjectsV1Response {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
/// Response of [list_objects_v2()](crate::s3::client::Client::list_objects_v2) S3 API
|
||||||
pub struct ListObjectsV2Response {
|
pub struct ListObjectsV2Response {
|
||||||
pub headers: HeaderMap,
|
pub headers: HeaderMap,
|
||||||
pub name: String,
|
pub name: String,
|
||||||
@ -241,6 +268,7 @@ pub struct ListObjectsV2Response {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
/// Response of [list_object_versions()](crate::s3::client::Client::list_object_versions) S3 API
|
||||||
pub struct ListObjectVersionsResponse {
|
pub struct ListObjectVersionsResponse {
|
||||||
pub headers: HeaderMap,
|
pub headers: HeaderMap,
|
||||||
pub name: String,
|
pub name: String,
|
||||||
@ -257,6 +285,7 @@ pub struct ListObjectVersionsResponse {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
/// Response of [list_objects()](crate::s3::client::Client::list_objects) API
|
||||||
pub struct ListObjectsResponse {
|
pub struct ListObjectsResponse {
|
||||||
pub headers: HeaderMap,
|
pub headers: HeaderMap,
|
||||||
pub name: String,
|
pub name: String,
|
||||||
@ -284,6 +313,7 @@ pub struct ListObjectsResponse {
|
|||||||
pub next_version_id_marker: String,
|
pub next_version_id_marker: String,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Response of [select_object_content()](crate::s3::client::Client::select_object_content) API
|
||||||
pub struct SelectObjectContentResponse {
|
pub struct SelectObjectContentResponse {
|
||||||
pub headers: HeaderMap,
|
pub headers: HeaderMap,
|
||||||
pub region: String,
|
pub region: String,
|
||||||
@ -607,6 +637,7 @@ impl SelectObjectContentResponse {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
/// Response of [listen_bucket_notification()](crate::s3::client::Client::listen_bucket_notification) API
|
||||||
pub struct ListenBucketNotificationResponse {
|
pub struct ListenBucketNotificationResponse {
|
||||||
pub headers: HeaderMap,
|
pub headers: HeaderMap,
|
||||||
pub region: String,
|
pub region: String,
|
||||||
@ -627,9 +658,11 @@ impl ListenBucketNotificationResponse {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Response of [delete_bucket_encryption()](crate::s3::client::Client::delete_bucket_encryption) API
|
||||||
pub type DeleteBucketEncryptionResponse = BucketResponse;
|
pub type DeleteBucketEncryptionResponse = BucketResponse;
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
/// Response of [get_bucket_encryption()](crate::s3::client::Client::get_bucket_encryption) API
|
||||||
pub struct GetBucketEncryptionResponse {
|
pub struct GetBucketEncryptionResponse {
|
||||||
pub headers: HeaderMap,
|
pub headers: HeaderMap,
|
||||||
pub region: String,
|
pub region: String,
|
||||||
@ -637,13 +670,17 @@ pub struct GetBucketEncryptionResponse {
|
|||||||
pub config: SseConfig,
|
pub config: SseConfig,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Response of [set_bucket_encryption()](crate::s3::client::Client::set_bucket_encryption) API
|
||||||
pub type SetBucketEncryptionResponse = BucketResponse;
|
pub type SetBucketEncryptionResponse = BucketResponse;
|
||||||
|
|
||||||
|
/// Response of [enable_object_legal_hold()](crate::s3::client::Client::enable_object_legal_hold) API
|
||||||
pub type EnableObjectLegalHoldResponse = ObjectResponse;
|
pub type EnableObjectLegalHoldResponse = ObjectResponse;
|
||||||
|
|
||||||
|
/// Response of [disable_object_legal_hold()](crate::s3::client::Client::disable_object_legal_hold) API
|
||||||
pub type DisableObjectLegalHoldResponse = ObjectResponse;
|
pub type DisableObjectLegalHoldResponse = ObjectResponse;
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
/// Response of [is_object_legal_hold_enabled()](crate::s3::client::Client::is_object_legal_hold_enabled) API
|
||||||
pub struct IsObjectLegalHoldEnabledResponse {
|
pub struct IsObjectLegalHoldEnabledResponse {
|
||||||
pub headers: HeaderMap,
|
pub headers: HeaderMap,
|
||||||
pub region: String,
|
pub region: String,
|
||||||
@ -653,9 +690,11 @@ pub struct IsObjectLegalHoldEnabledResponse {
|
|||||||
pub enabled: bool,
|
pub enabled: bool,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Response of [delete_bucket_lifecycle()](crate::s3::client::Client::delete_bucket_lifecycle) API
|
||||||
pub type DeleteBucketLifecycleResponse = BucketResponse;
|
pub type DeleteBucketLifecycleResponse = BucketResponse;
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
/// Response of [get_bucket_lifecycle()](crate::s3::client::Client::get_bucket_lifecycle) API
|
||||||
pub struct GetBucketLifecycleResponse {
|
pub struct GetBucketLifecycleResponse {
|
||||||
pub headers: HeaderMap,
|
pub headers: HeaderMap,
|
||||||
pub region: String,
|
pub region: String,
|
||||||
@ -663,11 +702,14 @@ pub struct GetBucketLifecycleResponse {
|
|||||||
pub config: LifecycleConfig,
|
pub config: LifecycleConfig,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Response of [set_bucket_lifecycle()](crate::s3::client::Client::set_bucket_lifecycle) API
|
||||||
pub type SetBucketLifecycleResponse = BucketResponse;
|
pub type SetBucketLifecycleResponse = BucketResponse;
|
||||||
|
|
||||||
|
/// Response of [delete_bucket_notification()](crate::s3::client::Client::delete_bucket_notification) API
|
||||||
pub type DeleteBucketNotificationResponse = BucketResponse;
|
pub type DeleteBucketNotificationResponse = BucketResponse;
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
/// Response of [get_bucket_notification()](crate::s3::client::Client::get_bucket_notification) API
|
||||||
pub struct GetBucketNotificationResponse {
|
pub struct GetBucketNotificationResponse {
|
||||||
pub headers: HeaderMap,
|
pub headers: HeaderMap,
|
||||||
pub region: String,
|
pub region: String,
|
||||||
@ -675,11 +717,14 @@ pub struct GetBucketNotificationResponse {
|
|||||||
pub config: NotificationConfig,
|
pub config: NotificationConfig,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Response of [set_bucket_notification()](crate::s3::client::Client::set_bucket_notification) API
|
||||||
pub type SetBucketNotificationResponse = BucketResponse;
|
pub type SetBucketNotificationResponse = BucketResponse;
|
||||||
|
|
||||||
|
/// Response of [delete_bucket_policy()](crate::s3::client::Client::delete_bucket_policy) API
|
||||||
pub type DeleteBucketPolicyResponse = BucketResponse;
|
pub type DeleteBucketPolicyResponse = BucketResponse;
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
/// Response of [get_bucket_policy()](crate::s3::client::Client::get_bucket_policy) API
|
||||||
pub struct GetBucketPolicyResponse {
|
pub struct GetBucketPolicyResponse {
|
||||||
pub headers: HeaderMap,
|
pub headers: HeaderMap,
|
||||||
pub region: String,
|
pub region: String,
|
||||||
@ -687,11 +732,14 @@ pub struct GetBucketPolicyResponse {
|
|||||||
pub config: String,
|
pub config: String,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Response of [set_bucket_policy()](crate::s3::client::Client::set_bucket_policy) API
|
||||||
pub type SetBucketPolicyResponse = BucketResponse;
|
pub type SetBucketPolicyResponse = BucketResponse;
|
||||||
|
|
||||||
|
/// Response of [delete_bucket_replication()](crate::s3::client::Client::delete_bucket_replication) API
|
||||||
pub type DeleteBucketReplicationResponse = BucketResponse;
|
pub type DeleteBucketReplicationResponse = BucketResponse;
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
/// Response of [get_bucket_replication()](crate::s3::client::Client::get_bucket_replication) API
|
||||||
pub struct GetBucketReplicationResponse {
|
pub struct GetBucketReplicationResponse {
|
||||||
pub headers: HeaderMap,
|
pub headers: HeaderMap,
|
||||||
pub region: String,
|
pub region: String,
|
||||||
@ -699,11 +747,14 @@ pub struct GetBucketReplicationResponse {
|
|||||||
pub config: ReplicationConfig,
|
pub config: ReplicationConfig,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Response of [set_bucket_replication()](crate::s3::client::Client::set_bucket_replication) API
|
||||||
pub type SetBucketReplicationResponse = BucketResponse;
|
pub type SetBucketReplicationResponse = BucketResponse;
|
||||||
|
|
||||||
|
/// Response of [delete_bucket_tags()](crate::s3::client::Client::delete_bucket_tags) API
|
||||||
pub type DeleteBucketTagsResponse = BucketResponse;
|
pub type DeleteBucketTagsResponse = BucketResponse;
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
/// Response of [get_bucket_tags()](crate::s3::client::Client::get_bucket_tags) API
|
||||||
pub struct GetBucketTagsResponse {
|
pub struct GetBucketTagsResponse {
|
||||||
pub headers: HeaderMap,
|
pub headers: HeaderMap,
|
||||||
pub region: String,
|
pub region: String,
|
||||||
@ -711,9 +762,11 @@ pub struct GetBucketTagsResponse {
|
|||||||
pub tags: std::collections::HashMap<String, String>,
|
pub tags: std::collections::HashMap<String, String>,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Response of [set_bucket_tags()](crate::s3::client::Client::set_bucket_tags) API
|
||||||
pub type SetBucketTagsResponse = BucketResponse;
|
pub type SetBucketTagsResponse = BucketResponse;
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
/// Response of [get_bucket_versioning()](crate::s3::client::Client::get_bucket_versioning) API
|
||||||
pub struct GetBucketVersioningResponse {
|
pub struct GetBucketVersioningResponse {
|
||||||
pub headers: HeaderMap,
|
pub headers: HeaderMap,
|
||||||
pub region: String,
|
pub region: String,
|
||||||
@ -722,11 +775,14 @@ pub struct GetBucketVersioningResponse {
|
|||||||
pub mfa_delete: Option<bool>,
|
pub mfa_delete: Option<bool>,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Response of [set_bucket_versioning()](crate::s3::client::Client::set_bucket_versioning) API
|
||||||
pub type SetBucketVersioningResponse = BucketResponse;
|
pub type SetBucketVersioningResponse = BucketResponse;
|
||||||
|
|
||||||
|
/// Response of [delete_object_lock_config()](crate::s3::client::Client::delete_object_lock_config) API
|
||||||
pub type DeleteObjectLockConfigResponse = BucketResponse;
|
pub type DeleteObjectLockConfigResponse = BucketResponse;
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
/// Response of [get_object_lock_config()](crate::s3::client::Client::get_object_lock_config) API
|
||||||
pub struct GetObjectLockConfigResponse {
|
pub struct GetObjectLockConfigResponse {
|
||||||
pub headers: HeaderMap,
|
pub headers: HeaderMap,
|
||||||
pub region: String,
|
pub region: String,
|
||||||
@ -734,9 +790,11 @@ pub struct GetObjectLockConfigResponse {
|
|||||||
pub config: ObjectLockConfig,
|
pub config: ObjectLockConfig,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Response of [set_object_lock_config()](crate::s3::client::Client::set_object_lock_config) API
|
||||||
pub type SetObjectLockConfigResponse = BucketResponse;
|
pub type SetObjectLockConfigResponse = BucketResponse;
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
/// Response of [get_object_retention()](crate::s3::client::Client::get_object_retention) API
|
||||||
pub struct GetObjectRetentionResponse {
|
pub struct GetObjectRetentionResponse {
|
||||||
pub headers: HeaderMap,
|
pub headers: HeaderMap,
|
||||||
pub region: String,
|
pub region: String,
|
||||||
@ -747,11 +805,14 @@ pub struct GetObjectRetentionResponse {
|
|||||||
pub retain_until_date: Option<UtcTime>,
|
pub retain_until_date: Option<UtcTime>,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Response of [set_object_retention()](crate::s3::client::Client::set_object_retention) API
|
||||||
pub type SetObjectRetentionResponse = ObjectResponse;
|
pub type SetObjectRetentionResponse = ObjectResponse;
|
||||||
|
|
||||||
|
/// Response of [delete_object_tags()](crate::s3::client::Client::delete_object_tags) API
|
||||||
pub type DeleteObjectTagsResponse = ObjectResponse;
|
pub type DeleteObjectTagsResponse = ObjectResponse;
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
/// Response of [get_object_tags()](crate::s3::client::Client::get_object_tags) API
|
||||||
pub struct GetObjectTagsResponse {
|
pub struct GetObjectTagsResponse {
|
||||||
pub headers: HeaderMap,
|
pub headers: HeaderMap,
|
||||||
pub region: String,
|
pub region: String,
|
||||||
@ -761,9 +822,11 @@ pub struct GetObjectTagsResponse {
|
|||||||
pub tags: std::collections::HashMap<String, String>,
|
pub tags: std::collections::HashMap<String, String>,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Response of [set_object_tags()](crate::s3::client::Client::set_object_tags) API
|
||||||
pub type SetObjectTagsResponse = ObjectResponse;
|
pub type SetObjectTagsResponse = ObjectResponse;
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
/// Response of [get_presigned_object_url()](crate::s3::client::Client::get_presigned_object_url) API
|
||||||
pub struct GetPresignedObjectUrlResponse {
|
pub struct GetPresignedObjectUrlResponse {
|
||||||
pub region: String,
|
pub region: String,
|
||||||
pub bucket_name: String,
|
pub bucket_name: String,
|
||||||
@ -773,6 +836,7 @@ pub struct GetPresignedObjectUrlResponse {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
/// Response of [download_object()](crate::s3::client::Client::download_object) API
|
||||||
pub struct DownloadObjectResponse {
|
pub struct DownloadObjectResponse {
|
||||||
pub headers: HeaderMap,
|
pub headers: HeaderMap,
|
||||||
pub region: String,
|
pub region: String,
|
||||||
|
|||||||
@ -13,6 +13,8 @@
|
|||||||
// See the License for the specific language governing permissions and
|
// See the License for the specific language governing permissions and
|
||||||
// limitations under the License.
|
// limitations under the License.
|
||||||
|
|
||||||
|
//! Signature V4 for S3 API
|
||||||
|
|
||||||
use crate::s3::utils::{
|
use crate::s3::utils::{
|
||||||
get_canonical_headers, get_canonical_query_string, sha256_hash, to_amz_date, to_signer_date,
|
get_canonical_headers, get_canonical_query_string, sha256_hash, to_amz_date, to_signer_date,
|
||||||
Multimap, UtcTime,
|
Multimap, UtcTime,
|
||||||
@ -22,16 +24,19 @@ use hmac::{Hmac, Mac};
|
|||||||
use hyper::http::Method;
|
use hyper::http::Method;
|
||||||
use sha2::Sha256;
|
use sha2::Sha256;
|
||||||
|
|
||||||
|
/// Returns HMAC hash for given key and data
|
||||||
pub fn hmac_hash(key: &[u8], data: &[u8]) -> Vec<u8> {
|
pub fn hmac_hash(key: &[u8], data: &[u8]) -> Vec<u8> {
|
||||||
let mut hasher = Hmac::<Sha256>::new_from_slice(key).expect("HMAC can take key of any size");
|
let mut hasher = Hmac::<Sha256>::new_from_slice(key).expect("HMAC can take key of any size");
|
||||||
hasher.update(data);
|
hasher.update(data);
|
||||||
hasher.finalize().into_bytes().to_vec()
|
hasher.finalize().into_bytes().to_vec()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Returns hex encoded HMAC hash for given key and data
|
||||||
pub fn hmac_hash_hex(key: &[u8], data: &[u8]) -> String {
|
pub fn hmac_hash_hex(key: &[u8], data: &[u8]) -> String {
|
||||||
hexencode(hmac_hash(key, data))
|
hexencode(hmac_hash(key, data))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Returns scope value of given date, region and service name
|
||||||
pub fn get_scope(date: UtcTime, region: &str, service_name: &str) -> String {
|
pub fn get_scope(date: UtcTime, region: &str, service_name: &str) -> String {
|
||||||
format!(
|
format!(
|
||||||
"{}/{}/{}/aws4_request",
|
"{}/{}/{}/aws4_request",
|
||||||
@ -41,6 +46,7 @@ pub fn get_scope(date: UtcTime, region: &str, service_name: &str) -> String {
|
|||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Returns hex encoded SHA256 hash of canonical request
|
||||||
pub fn get_canonical_request_hash(
|
pub fn get_canonical_request_hash(
|
||||||
method: &Method,
|
method: &Method,
|
||||||
uri: &str,
|
uri: &str,
|
||||||
@ -63,6 +69,7 @@ pub fn get_canonical_request_hash(
|
|||||||
return sha256_hash(canonical_request.as_bytes());
|
return sha256_hash(canonical_request.as_bytes());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Returns string-to-sign value of given date, scope and canonical request hash
|
||||||
pub fn get_string_to_sign(date: UtcTime, scope: &str, canonical_request_hash: &str) -> String {
|
pub fn get_string_to_sign(date: UtcTime, scope: &str, canonical_request_hash: &str) -> String {
|
||||||
format!(
|
format!(
|
||||||
"AWS4-HMAC-SHA256\n{}\n{}\n{}",
|
"AWS4-HMAC-SHA256\n{}\n{}\n{}",
|
||||||
@ -72,6 +79,7 @@ pub fn get_string_to_sign(date: UtcTime, scope: &str, canonical_request_hash: &s
|
|||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Returns signing key of given secret key, date, region and service name
|
||||||
pub fn get_signing_key(
|
pub fn get_signing_key(
|
||||||
secret_key: &str,
|
secret_key: &str,
|
||||||
date: UtcTime,
|
date: UtcTime,
|
||||||
@ -87,10 +95,12 @@ pub fn get_signing_key(
|
|||||||
return hmac_hash(date_region_service_key.as_slice(), b"aws4_request");
|
return hmac_hash(date_region_service_key.as_slice(), b"aws4_request");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Returns signature value for given signing key and string-to-sign
|
||||||
pub fn get_signature(signing_key: &[u8], string_to_sign: &[u8]) -> String {
|
pub fn get_signature(signing_key: &[u8], string_to_sign: &[u8]) -> String {
|
||||||
hmac_hash_hex(signing_key, string_to_sign)
|
hmac_hash_hex(signing_key, string_to_sign)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Returns authorization value for given access key, scope, signed headers and signature
|
||||||
pub fn get_authorization(
|
pub fn get_authorization(
|
||||||
access_key: &str,
|
access_key: &str,
|
||||||
scope: &str,
|
scope: &str,
|
||||||
@ -103,6 +113,7 @@ pub fn get_authorization(
|
|||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Signs and updates headers for given parameters
|
||||||
pub fn sign_v4(
|
pub fn sign_v4(
|
||||||
service_name: &str,
|
service_name: &str,
|
||||||
method: &Method,
|
method: &Method,
|
||||||
@ -134,6 +145,7 @@ pub fn sign_v4(
|
|||||||
headers.insert("Authorization".to_string(), authorization);
|
headers.insert("Authorization".to_string(), authorization);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Signs and updates headers for given parameters for S3 request
|
||||||
pub fn sign_v4_s3(
|
pub fn sign_v4_s3(
|
||||||
method: &Method,
|
method: &Method,
|
||||||
uri: &str,
|
uri: &str,
|
||||||
@ -159,6 +171,7 @@ pub fn sign_v4_s3(
|
|||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Signs and updates headers for given parameters for STS request
|
||||||
pub fn sign_v4_sts(
|
pub fn sign_v4_sts(
|
||||||
method: &Method,
|
method: &Method,
|
||||||
uri: &str,
|
uri: &str,
|
||||||
@ -184,6 +197,7 @@ pub fn sign_v4_sts(
|
|||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Signs and updates headers for given parameters for pre-sign request
|
||||||
pub fn presign_v4(
|
pub fn presign_v4(
|
||||||
method: &Method,
|
method: &Method,
|
||||||
host: &str,
|
host: &str,
|
||||||
@ -230,6 +244,7 @@ pub fn presign_v4(
|
|||||||
query_params.insert("X-Amz-Signature".to_string(), signature);
|
query_params.insert("X-Amz-Signature".to_string(), signature);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Signs and updates headers for given parameters for pre-sign POST request
|
||||||
pub fn post_presign_v4(
|
pub fn post_presign_v4(
|
||||||
string_to_sign: &str,
|
string_to_sign: &str,
|
||||||
secret_key: &str,
|
secret_key: &str,
|
||||||
|
|||||||
@ -13,9 +13,12 @@
|
|||||||
// See the License for the specific language governing permissions and
|
// See the License for the specific language governing permissions and
|
||||||
// limitations under the License.
|
// limitations under the License.
|
||||||
|
|
||||||
|
//! Server side encryption definitions
|
||||||
|
|
||||||
use crate::s3::utils;
|
use crate::s3::utils;
|
||||||
use std::any::Any;
|
use std::any::Any;
|
||||||
|
|
||||||
|
/// Base server side encryption
|
||||||
pub trait Sse: std::fmt::Debug {
|
pub trait Sse: std::fmt::Debug {
|
||||||
fn headers(&self) -> utils::Multimap;
|
fn headers(&self) -> utils::Multimap;
|
||||||
fn copy_headers(&self) -> utils::Multimap;
|
fn copy_headers(&self) -> utils::Multimap;
|
||||||
@ -24,6 +27,7 @@ pub trait Sse: std::fmt::Debug {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
/// Server side encryption customer key type
|
||||||
pub struct SseCustomerKey {
|
pub struct SseCustomerKey {
|
||||||
headers: utils::Multimap,
|
headers: utils::Multimap,
|
||||||
copy_headers: utils::Multimap,
|
copy_headers: utils::Multimap,
|
||||||
@ -88,6 +92,7 @@ impl Sse for SseCustomerKey {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
/// Server side encryption KMS type
|
||||||
pub struct SseKms {
|
pub struct SseKms {
|
||||||
headers: utils::Multimap,
|
headers: utils::Multimap,
|
||||||
}
|
}
|
||||||
@ -133,6 +138,7 @@ impl Sse for SseKms {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
/// Server side encryption S3 type
|
||||||
pub struct SseS3 {
|
pub struct SseS3 {
|
||||||
headers: utils::Multimap,
|
headers: utils::Multimap,
|
||||||
}
|
}
|
||||||
|
|||||||
@ -13,6 +13,8 @@
|
|||||||
// See the License for the specific language governing permissions and
|
// See the License for the specific language governing permissions and
|
||||||
// limitations under the License.
|
// limitations under the License.
|
||||||
|
|
||||||
|
//! Various types for S3 API requests and responses
|
||||||
|
|
||||||
use crate::s3::error::Error;
|
use crate::s3::error::Error;
|
||||||
use crate::s3::utils::{
|
use crate::s3::utils::{
|
||||||
from_iso8601utc, get_default_text, get_option_text, get_text, to_iso8601utc, UtcTime,
|
from_iso8601utc, get_default_text, get_option_text, get_text, to_iso8601utc, UtcTime,
|
||||||
@ -23,6 +25,7 @@ use std::fmt;
|
|||||||
use xmltree::Element;
|
use xmltree::Element;
|
||||||
|
|
||||||
#[derive(Clone, Debug, Default)]
|
#[derive(Clone, Debug, Default)]
|
||||||
|
/// Contains information of an item of [list_objects()](crate::s3::client::Client::list_objects) API
|
||||||
pub struct Item {
|
pub struct Item {
|
||||||
pub name: String,
|
pub name: String,
|
||||||
pub last_modified: Option<UtcTime>,
|
pub last_modified: Option<UtcTime>,
|
||||||
@ -40,18 +43,21 @@ pub struct Item {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
/// Contains bucket name and creation date
|
||||||
pub struct Bucket {
|
pub struct Bucket {
|
||||||
pub name: String,
|
pub name: String,
|
||||||
pub creation_date: UtcTime,
|
pub creation_date: UtcTime,
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
/// Contains part number and etag of multipart upload
|
||||||
pub struct Part {
|
pub struct Part {
|
||||||
pub number: u16,
|
pub number: u16,
|
||||||
pub etag: String,
|
pub etag: String,
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
/// Contains retention mode information
|
||||||
pub enum RetentionMode {
|
pub enum RetentionMode {
|
||||||
GOVERNANCE,
|
GOVERNANCE,
|
||||||
COMPLIANCE,
|
COMPLIANCE,
|
||||||
@ -77,11 +83,13 @@ impl fmt::Display for RetentionMode {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
/// Contains retention mode and retain until date
|
||||||
pub struct Retention {
|
pub struct Retention {
|
||||||
pub mode: RetentionMode,
|
pub mode: RetentionMode,
|
||||||
pub retain_until_date: UtcTime,
|
pub retain_until_date: UtcTime,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Parses legal hold string value
|
||||||
pub fn parse_legal_hold(s: &str) -> Result<bool, Error> {
|
pub fn parse_legal_hold(s: &str) -> Result<bool, Error> {
|
||||||
match s {
|
match s {
|
||||||
"ON" => Ok(true),
|
"ON" => Ok(true),
|
||||||
@ -91,12 +99,14 @@ pub fn parse_legal_hold(s: &str) -> Result<bool, Error> {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Debug, Copy)]
|
#[derive(Clone, Debug, Copy)]
|
||||||
|
/// Contains delete object name and optional version ID
|
||||||
pub struct DeleteObject<'a> {
|
pub struct DeleteObject<'a> {
|
||||||
pub name: &'a str,
|
pub name: &'a str,
|
||||||
pub version_id: Option<&'a str>,
|
pub version_id: Option<&'a str>,
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
/// Compression types
|
||||||
pub enum CompressionType {
|
pub enum CompressionType {
|
||||||
NONE,
|
NONE,
|
||||||
GZIP,
|
GZIP,
|
||||||
@ -114,6 +124,7 @@ impl fmt::Display for CompressionType {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
/// File header information types
|
||||||
pub enum FileHeaderInfo {
|
pub enum FileHeaderInfo {
|
||||||
USE,
|
USE,
|
||||||
IGNORE,
|
IGNORE,
|
||||||
@ -131,6 +142,7 @@ impl fmt::Display for FileHeaderInfo {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
/// JSON document types
|
||||||
pub enum JsonType {
|
pub enum JsonType {
|
||||||
DOCUMENT,
|
DOCUMENT,
|
||||||
LINES,
|
LINES,
|
||||||
@ -146,6 +158,7 @@ impl fmt::Display for JsonType {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
/// Quote fields types
|
||||||
pub enum QuoteFields {
|
pub enum QuoteFields {
|
||||||
ALWAYS,
|
ALWAYS,
|
||||||
ASNEEDED,
|
ASNEEDED,
|
||||||
@ -161,6 +174,7 @@ impl fmt::Display for QuoteFields {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Debug, Default)]
|
#[derive(Clone, Debug, Default)]
|
||||||
|
/// CSV input serialization definitions
|
||||||
pub struct CsvInputSerialization {
|
pub struct CsvInputSerialization {
|
||||||
pub compression_type: Option<CompressionType>,
|
pub compression_type: Option<CompressionType>,
|
||||||
pub allow_quoted_record_delimiter: bool,
|
pub allow_quoted_record_delimiter: bool,
|
||||||
@ -173,15 +187,18 @@ pub struct CsvInputSerialization {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Debug, Default)]
|
#[derive(Clone, Debug, Default)]
|
||||||
|
/// JSON input serialization definitions
|
||||||
pub struct JsonInputSerialization {
|
pub struct JsonInputSerialization {
|
||||||
pub compression_type: Option<CompressionType>,
|
pub compression_type: Option<CompressionType>,
|
||||||
pub json_type: Option<JsonType>,
|
pub json_type: Option<JsonType>,
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Debug, Default)]
|
#[derive(Clone, Debug, Default)]
|
||||||
|
/// Parque input serialization definitions
|
||||||
pub struct ParquetInputSerialization;
|
pub struct ParquetInputSerialization;
|
||||||
|
|
||||||
#[derive(Clone, Debug, Default)]
|
#[derive(Clone, Debug, Default)]
|
||||||
|
/// CSV output serialization definitions
|
||||||
pub struct CsvOutputSerialization {
|
pub struct CsvOutputSerialization {
|
||||||
pub field_delimiter: Option<char>,
|
pub field_delimiter: Option<char>,
|
||||||
pub quote_character: Option<char>,
|
pub quote_character: Option<char>,
|
||||||
@ -191,11 +208,13 @@ pub struct CsvOutputSerialization {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Debug, Default)]
|
#[derive(Clone, Debug, Default)]
|
||||||
|
/// JSON output serialization definitions
|
||||||
pub struct JsonOutputSerialization {
|
pub struct JsonOutputSerialization {
|
||||||
pub record_delimiter: Option<char>,
|
pub record_delimiter: Option<char>,
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Debug, Default)]
|
#[derive(Clone, Debug, Default)]
|
||||||
|
/// Select request for [select_object_content()](crate::s3::client::Client::select_object_content) API
|
||||||
pub struct SelectRequest<'a> {
|
pub struct SelectRequest<'a> {
|
||||||
pub expr: &'a str,
|
pub expr: &'a str,
|
||||||
pub csv_input: Option<CsvInputSerialization>,
|
pub csv_input: Option<CsvInputSerialization>,
|
||||||
@ -456,6 +475,7 @@ impl<'a> SelectRequest<'a> {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
/// Progress information of [select_object_content()](crate::s3::client::Client::select_object_content) API
|
||||||
pub struct SelectProgress {
|
pub struct SelectProgress {
|
||||||
pub bytes_scanned: usize,
|
pub bytes_scanned: usize,
|
||||||
pub bytes_progressed: usize,
|
pub bytes_progressed: usize,
|
||||||
@ -463,14 +483,17 @@ pub struct SelectProgress {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Debug, Deserialize, Serialize)]
|
#[derive(Debug, Deserialize, Serialize)]
|
||||||
|
/// User identity contains principal ID
|
||||||
pub struct UserIdentity {
|
pub struct UserIdentity {
|
||||||
#[serde(alias = "principalId")]
|
#[serde(alias = "principalId")]
|
||||||
pub principal_id: Option<String>,
|
pub principal_id: Option<String>,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Owner identity contains principal ID
|
||||||
pub type OwnerIdentity = UserIdentity;
|
pub type OwnerIdentity = UserIdentity;
|
||||||
|
|
||||||
#[derive(Debug, Deserialize, Serialize)]
|
#[derive(Debug, Deserialize, Serialize)]
|
||||||
|
/// Request parameters contain principal ID, region and source IP address
|
||||||
pub struct RequestParameters {
|
pub struct RequestParameters {
|
||||||
#[serde(alias = "principalId")]
|
#[serde(alias = "principalId")]
|
||||||
pub principal_id: Option<String>,
|
pub principal_id: Option<String>,
|
||||||
@ -481,6 +504,7 @@ pub struct RequestParameters {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Debug, Deserialize, Serialize)]
|
#[derive(Debug, Deserialize, Serialize)]
|
||||||
|
/// Response elements information
|
||||||
pub struct ResponseElements {
|
pub struct ResponseElements {
|
||||||
#[serde(alias = "content-length")]
|
#[serde(alias = "content-length")]
|
||||||
pub content_length: Option<String>,
|
pub content_length: Option<String>,
|
||||||
@ -493,6 +517,7 @@ pub struct ResponseElements {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Debug, Deserialize, Serialize)]
|
#[derive(Debug, Deserialize, Serialize)]
|
||||||
|
/// S3 bucket information
|
||||||
pub struct S3Bucket {
|
pub struct S3Bucket {
|
||||||
#[serde(alias = "name")]
|
#[serde(alias = "name")]
|
||||||
pub name: Option<String>,
|
pub name: Option<String>,
|
||||||
@ -503,6 +528,7 @@ pub struct S3Bucket {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Debug, Deserialize, Serialize)]
|
#[derive(Debug, Deserialize, Serialize)]
|
||||||
|
/// S3 object information
|
||||||
pub struct S3Object {
|
pub struct S3Object {
|
||||||
#[serde(alias = "key")]
|
#[serde(alias = "key")]
|
||||||
pub key: Option<String>,
|
pub key: Option<String>,
|
||||||
@ -519,6 +545,7 @@ pub struct S3Object {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Debug, Deserialize, Serialize)]
|
#[derive(Debug, Deserialize, Serialize)]
|
||||||
|
/// S3 definitions for NotificationRecord
|
||||||
pub struct S3 {
|
pub struct S3 {
|
||||||
#[serde(alias = "s3SchemaVersion")]
|
#[serde(alias = "s3SchemaVersion")]
|
||||||
pub s3_schema_version: Option<String>,
|
pub s3_schema_version: Option<String>,
|
||||||
@ -531,6 +558,7 @@ pub struct S3 {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Debug, Deserialize, Serialize)]
|
#[derive(Debug, Deserialize, Serialize)]
|
||||||
|
/// Source information
|
||||||
pub struct Source {
|
pub struct Source {
|
||||||
#[serde(alias = "host")]
|
#[serde(alias = "host")]
|
||||||
pub host: Option<String>,
|
pub host: Option<String>,
|
||||||
@ -541,6 +569,7 @@ pub struct Source {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Debug, Deserialize, Serialize)]
|
#[derive(Debug, Deserialize, Serialize)]
|
||||||
|
/// Notification record information
|
||||||
pub struct NotificationRecord {
|
pub struct NotificationRecord {
|
||||||
#[serde(alias = "eventVersion")]
|
#[serde(alias = "eventVersion")]
|
||||||
pub event_version: Option<String>,
|
pub event_version: Option<String>,
|
||||||
@ -565,12 +594,14 @@ pub struct NotificationRecord {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Debug, Deserialize, Serialize)]
|
#[derive(Debug, Deserialize, Serialize)]
|
||||||
|
/// Contains notification records
|
||||||
pub struct NotificationRecords {
|
pub struct NotificationRecords {
|
||||||
#[serde(alias = "Records")]
|
#[serde(alias = "Records")]
|
||||||
pub records: Vec<NotificationRecord>,
|
pub records: Vec<NotificationRecord>,
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
/// Directive types
|
||||||
pub enum Directive {
|
pub enum Directive {
|
||||||
Copy,
|
Copy,
|
||||||
Replace,
|
Replace,
|
||||||
@ -596,6 +627,7 @@ impl fmt::Display for Directive {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
/// Server-side information configuration
|
||||||
pub struct SseConfig {
|
pub struct SseConfig {
|
||||||
pub sse_algorithm: String,
|
pub sse_algorithm: String,
|
||||||
pub kms_master_key_id: Option<String>,
|
pub kms_master_key_id: Option<String>,
|
||||||
@ -636,18 +668,21 @@ impl SseConfig {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
/// Contains key and value
|
||||||
pub struct Tag {
|
pub struct Tag {
|
||||||
pub key: String,
|
pub key: String,
|
||||||
pub value: String,
|
pub value: String,
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
/// And operator contains prefix and tags
|
||||||
pub struct AndOperator {
|
pub struct AndOperator {
|
||||||
pub prefix: Option<String>,
|
pub prefix: Option<String>,
|
||||||
pub tags: Option<HashMap<String, String>>,
|
pub tags: Option<HashMap<String, String>>,
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
/// Filter information
|
||||||
pub struct Filter {
|
pub struct Filter {
|
||||||
pub and_operator: Option<AndOperator>,
|
pub and_operator: Option<AndOperator>,
|
||||||
pub prefix: Option<String>,
|
pub prefix: Option<String>,
|
||||||
@ -763,6 +798,7 @@ impl Filter {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
/// Lifecycle rule information
|
||||||
pub struct LifecycleRule {
|
pub struct LifecycleRule {
|
||||||
pub abort_incomplete_multipart_upload_days_after_initiation: Option<usize>,
|
pub abort_incomplete_multipart_upload_days_after_initiation: Option<usize>,
|
||||||
pub expiration_date: Option<UtcTime>,
|
pub expiration_date: Option<UtcTime>,
|
||||||
@ -900,6 +936,7 @@ impl LifecycleRule {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
/// Lifecycle configuration
|
||||||
pub struct LifecycleConfig {
|
pub struct LifecycleConfig {
|
||||||
pub rules: Vec<LifecycleRule>,
|
pub rules: Vec<LifecycleRule>,
|
||||||
}
|
}
|
||||||
@ -1155,6 +1192,7 @@ fn to_xml_common_notification_config(
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
/// Prefix filter rule
|
||||||
pub struct PrefixFilterRule {
|
pub struct PrefixFilterRule {
|
||||||
pub value: String,
|
pub value: String,
|
||||||
}
|
}
|
||||||
@ -1164,6 +1202,7 @@ impl PrefixFilterRule {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
/// Suffix filter rule
|
||||||
pub struct SuffixFilterRule {
|
pub struct SuffixFilterRule {
|
||||||
pub value: String,
|
pub value: String,
|
||||||
}
|
}
|
||||||
@ -1173,6 +1212,7 @@ impl SuffixFilterRule {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
/// Cloud function configuration information
|
||||||
pub struct CloudFuncConfig {
|
pub struct CloudFuncConfig {
|
||||||
pub events: Vec<String>,
|
pub events: Vec<String>,
|
||||||
pub id: Option<String>,
|
pub id: Option<String>,
|
||||||
@ -1223,6 +1263,7 @@ impl CloudFuncConfig {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
/// Queue configuration information
|
||||||
pub struct QueueConfig {
|
pub struct QueueConfig {
|
||||||
pub events: Vec<String>,
|
pub events: Vec<String>,
|
||||||
pub id: Option<String>,
|
pub id: Option<String>,
|
||||||
@ -1273,6 +1314,7 @@ impl QueueConfig {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
/// Topic configuration information
|
||||||
pub struct TopicConfig {
|
pub struct TopicConfig {
|
||||||
pub events: Vec<String>,
|
pub events: Vec<String>,
|
||||||
pub id: Option<String>,
|
pub id: Option<String>,
|
||||||
@ -1323,6 +1365,7 @@ impl TopicConfig {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
/// Notification configuration information
|
||||||
pub struct NotificationConfig {
|
pub struct NotificationConfig {
|
||||||
pub cloud_func_config_list: Option<Vec<CloudFuncConfig>>,
|
pub cloud_func_config_list: Option<Vec<CloudFuncConfig>>,
|
||||||
pub queue_config_list: Option<Vec<QueueConfig>>,
|
pub queue_config_list: Option<Vec<QueueConfig>>,
|
||||||
@ -1413,6 +1456,7 @@ impl NotificationConfig {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
/// Access control translation information
|
||||||
pub struct AccessControlTranslation {
|
pub struct AccessControlTranslation {
|
||||||
pub owner: String,
|
pub owner: String,
|
||||||
}
|
}
|
||||||
@ -1432,11 +1476,13 @@ impl Default for AccessControlTranslation {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
/// Encryption configuration information
|
||||||
pub struct EncryptionConfig {
|
pub struct EncryptionConfig {
|
||||||
pub replica_kms_key_id: Option<String>,
|
pub replica_kms_key_id: Option<String>,
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
/// Metrics information
|
||||||
pub struct Metrics {
|
pub struct Metrics {
|
||||||
pub event_threshold_minutes: Option<i32>,
|
pub event_threshold_minutes: Option<i32>,
|
||||||
pub status: bool,
|
pub status: bool,
|
||||||
@ -1452,6 +1498,7 @@ impl Metrics {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
/// Replication time information
|
||||||
pub struct ReplicationTime {
|
pub struct ReplicationTime {
|
||||||
pub time_minutes: Option<i32>,
|
pub time_minutes: Option<i32>,
|
||||||
pub status: bool,
|
pub status: bool,
|
||||||
@ -1467,6 +1514,7 @@ impl ReplicationTime {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
/// Destination information
|
||||||
pub struct Destination {
|
pub struct Destination {
|
||||||
pub bucket_arn: String,
|
pub bucket_arn: String,
|
||||||
pub access_control_translation: Option<AccessControlTranslation>,
|
pub access_control_translation: Option<AccessControlTranslation>,
|
||||||
@ -1601,11 +1649,13 @@ impl Destination {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
/// Source selection criteria information
|
||||||
pub struct SourceSelectionCriteria {
|
pub struct SourceSelectionCriteria {
|
||||||
pub sse_kms_encrypted_objects_status: Option<bool>,
|
pub sse_kms_encrypted_objects_status: Option<bool>,
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
/// Replication rule information
|
||||||
pub struct ReplicationRule {
|
pub struct ReplicationRule {
|
||||||
pub destination: Destination,
|
pub destination: Destination,
|
||||||
pub delete_marker_replication_status: Option<bool>,
|
pub delete_marker_replication_status: Option<bool>,
|
||||||
@ -1750,6 +1800,7 @@ impl ReplicationRule {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
/// Replication configuration information
|
||||||
pub struct ReplicationConfig {
|
pub struct ReplicationConfig {
|
||||||
pub role: Option<String>,
|
pub role: Option<String>,
|
||||||
pub rules: Vec<ReplicationRule>,
|
pub rules: Vec<ReplicationRule>,
|
||||||
@ -1794,6 +1845,7 @@ impl ReplicationConfig {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
|
/// Object lock configuration information
|
||||||
pub struct ObjectLockConfig {
|
pub struct ObjectLockConfig {
|
||||||
pub retention_mode: Option<RetentionMode>,
|
pub retention_mode: Option<RetentionMode>,
|
||||||
pub retention_duration_days: Option<i32>,
|
pub retention_duration_days: Option<i32>,
|
||||||
|
|||||||
@ -13,6 +13,8 @@
|
|||||||
// See the License for the specific language governing permissions and
|
// See the License for the specific language governing permissions and
|
||||||
// limitations under the License.
|
// limitations under the License.
|
||||||
|
|
||||||
|
//! Various utility and helper functions
|
||||||
|
|
||||||
use crate::s3::error::Error;
|
use crate::s3::error::Error;
|
||||||
use base64::engine::general_purpose::STANDARD as BASE64;
|
use base64::engine::general_purpose::STANDARD as BASE64;
|
||||||
use base64::engine::Engine as _;
|
use base64::engine::Engine as _;
|
||||||
@ -29,14 +31,18 @@ pub use urlencoding::decode as urldecode;
|
|||||||
pub use urlencoding::encode as urlencode;
|
pub use urlencoding::encode as urlencode;
|
||||||
use xmltree::Element;
|
use xmltree::Element;
|
||||||
|
|
||||||
|
/// Date and time with UTC timezone
|
||||||
pub type UtcTime = DateTime<Utc>;
|
pub type UtcTime = DateTime<Utc>;
|
||||||
|
|
||||||
|
/// Multimap for string key and string value
|
||||||
pub type Multimap = MultiMap<String, String>;
|
pub type Multimap = MultiMap<String, String>;
|
||||||
|
|
||||||
|
/// Encodes data using base64 algorithm
|
||||||
pub fn b64encode<T: AsRef<[u8]>>(input: T) -> String {
|
pub fn b64encode<T: AsRef<[u8]>>(input: T) -> String {
|
||||||
BASE64.encode(input)
|
BASE64.encode(input)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Merges two multimaps.
|
||||||
pub fn merge(m1: &mut Multimap, m2: &Multimap) {
|
pub fn merge(m1: &mut Multimap, m2: &Multimap) {
|
||||||
for (key, values) in m2.iter_all() {
|
for (key, values) in m2.iter_all() {
|
||||||
for value in values {
|
for value in values {
|
||||||
@ -45,36 +51,44 @@ pub fn merge(m1: &mut Multimap, m2: &Multimap) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Computes CRC32 of given data.
|
||||||
pub fn crc32(data: &[u8]) -> u32 {
|
pub fn crc32(data: &[u8]) -> u32 {
|
||||||
Crc::<u32>::new(&CRC_32_ISO_HDLC).checksum(data)
|
Crc::<u32>::new(&CRC_32_ISO_HDLC).checksum(data)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Converts data array into 32 bit unsigned int
|
||||||
pub fn uint32(mut data: &[u8]) -> Result<u32, std::io::Error> {
|
pub fn uint32(mut data: &[u8]) -> Result<u32, std::io::Error> {
|
||||||
data.read_u32::<BigEndian>()
|
data.read_u32::<BigEndian>()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Gets hex encoded SHA256 hash of given data
|
||||||
pub fn sha256_hash(data: &[u8]) -> String {
|
pub fn sha256_hash(data: &[u8]) -> String {
|
||||||
let mut hasher = Sha256::new();
|
let mut hasher = Sha256::new();
|
||||||
hasher.update(data);
|
hasher.update(data);
|
||||||
format!("{:x}", hasher.finalize())
|
format!("{:x}", hasher.finalize())
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Gets bas64 encoded MD5 hash of given data
|
||||||
pub fn md5sum_hash(data: &[u8]) -> String {
|
pub fn md5sum_hash(data: &[u8]) -> String {
|
||||||
b64encode(md5compute(data).as_slice())
|
b64encode(md5compute(data).as_slice())
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Gets current UTC time
|
||||||
pub fn utc_now() -> UtcTime {
|
pub fn utc_now() -> UtcTime {
|
||||||
chrono::offset::Utc::now()
|
chrono::offset::Utc::now()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Gets signer date value of given time
|
||||||
pub fn to_signer_date(time: UtcTime) -> String {
|
pub fn to_signer_date(time: UtcTime) -> String {
|
||||||
time.format("%Y%m%d").to_string()
|
time.format("%Y%m%d").to_string()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Gets AMZ date value of given time
|
||||||
pub fn to_amz_date(time: UtcTime) -> String {
|
pub fn to_amz_date(time: UtcTime) -> String {
|
||||||
time.format("%Y%m%dT%H%M%SZ").to_string()
|
time.format("%Y%m%dT%H%M%SZ").to_string()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Gets HTTP header value of given time
|
||||||
pub fn to_http_header_value(time: UtcTime) -> String {
|
pub fn to_http_header_value(time: UtcTime) -> String {
|
||||||
format!(
|
format!(
|
||||||
"{}, {} {} {} GMT",
|
"{}, {} {} {} GMT",
|
||||||
@ -99,10 +113,12 @@ pub fn to_http_header_value(time: UtcTime) -> String {
|
|||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Gets ISO8601 UTC formatted value of given time
|
||||||
pub fn to_iso8601utc(time: UtcTime) -> String {
|
pub fn to_iso8601utc(time: UtcTime) -> String {
|
||||||
time.format("%Y-%m-%dT%H:%M:%S.%3fZ").to_string()
|
time.format("%Y-%m-%dT%H:%M:%S.%3fZ").to_string()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Parses ISO8601 UTC formatted value to time
|
||||||
pub fn from_iso8601utc(s: &str) -> Result<UtcTime, ParseError> {
|
pub fn from_iso8601utc(s: &str) -> Result<UtcTime, ParseError> {
|
||||||
Ok(DateTime::<Utc>::from_naive_utc_and_offset(
|
Ok(DateTime::<Utc>::from_naive_utc_and_offset(
|
||||||
match NaiveDateTime::parse_from_str(s, "%Y-%m-%dT%H:%M:%S.%3fZ") {
|
match NaiveDateTime::parse_from_str(s, "%Y-%m-%dT%H:%M:%S.%3fZ") {
|
||||||
@ -113,6 +129,7 @@ pub fn from_iso8601utc(s: &str) -> Result<UtcTime, ParseError> {
|
|||||||
))
|
))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Parses HTTP header value to time
|
||||||
pub fn from_http_header_value(s: &str) -> Result<UtcTime, ParseError> {
|
pub fn from_http_header_value(s: &str) -> Result<UtcTime, ParseError> {
|
||||||
Ok(DateTime::<Utc>::from_naive_utc_and_offset(
|
Ok(DateTime::<Utc>::from_naive_utc_and_offset(
|
||||||
NaiveDateTime::parse_from_str(s, "%a, %d %b %Y %H:%M:%S GMT")?,
|
NaiveDateTime::parse_from_str(s, "%a, %d %b %Y %H:%M:%S GMT")?,
|
||||||
@ -120,6 +137,7 @@ pub fn from_http_header_value(s: &str) -> Result<UtcTime, ParseError> {
|
|||||||
))
|
))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Converts multimap to HTTP headers
|
||||||
pub fn to_http_headers(map: &Multimap) -> Vec<String> {
|
pub fn to_http_headers(map: &Multimap) -> Vec<String> {
|
||||||
let mut headers: Vec<String> = Vec::new();
|
let mut headers: Vec<String> = Vec::new();
|
||||||
for (key, values) in map.iter_all() {
|
for (key, values) in map.iter_all() {
|
||||||
@ -134,6 +152,7 @@ pub fn to_http_headers(map: &Multimap) -> Vec<String> {
|
|||||||
headers
|
headers
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Converts multimap to HTTP query string
|
||||||
pub fn to_query_string(map: &Multimap) -> String {
|
pub fn to_query_string(map: &Multimap) -> String {
|
||||||
let mut query = String::new();
|
let mut query = String::new();
|
||||||
for (key, values) in map.iter_all() {
|
for (key, values) in map.iter_all() {
|
||||||
@ -149,6 +168,7 @@ pub fn to_query_string(map: &Multimap) -> String {
|
|||||||
query
|
query
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Converts multimap to canonical query string
|
||||||
pub fn get_canonical_query_string(map: &Multimap) -> String {
|
pub fn get_canonical_query_string(map: &Multimap) -> String {
|
||||||
let mut keys: Vec<String> = Vec::new();
|
let mut keys: Vec<String> = Vec::new();
|
||||||
for (key, _) in map.iter() {
|
for (key, _) in map.iter() {
|
||||||
@ -176,6 +196,7 @@ pub fn get_canonical_query_string(map: &Multimap) -> String {
|
|||||||
query
|
query
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Converts multimap to signed headers and canonical headers
|
||||||
pub fn get_canonical_headers(map: &Multimap) -> (String, String) {
|
pub fn get_canonical_headers(map: &Multimap) -> (String, String) {
|
||||||
lazy_static! {
|
lazy_static! {
|
||||||
static ref MULTI_SPACE_REGEX: Regex = Regex::new("( +)").unwrap();
|
static ref MULTI_SPACE_REGEX: Regex = Regex::new("( +)").unwrap();
|
||||||
@ -223,6 +244,7 @@ pub fn get_canonical_headers(map: &Multimap) -> (String, String) {
|
|||||||
(signed_headers, canonical_headers)
|
(signed_headers, canonical_headers)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Validates given bucket name
|
||||||
pub fn check_bucket_name(bucket_name: &str, strict: bool) -> Result<(), Error> {
|
pub fn check_bucket_name(bucket_name: &str, strict: bool) -> Result<(), Error> {
|
||||||
if bucket_name.trim().is_empty() {
|
if bucket_name.trim().is_empty() {
|
||||||
return Err(Error::InvalidBucketName(String::from(
|
return Err(Error::InvalidBucketName(String::from(
|
||||||
@ -277,6 +299,7 @@ pub fn check_bucket_name(bucket_name: &str, strict: bool) -> Result<(), Error> {
|
|||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Gets text value of given XML element for given tag.
|
||||||
pub fn get_text(element: &Element, tag: &str) -> Result<String, Error> {
|
pub fn get_text(element: &Element, tag: &str) -> Result<String, Error> {
|
||||||
Ok(element
|
Ok(element
|
||||||
.get_child(tag)
|
.get_child(tag)
|
||||||
@ -286,6 +309,7 @@ pub fn get_text(element: &Element, tag: &str) -> Result<String, Error> {
|
|||||||
.to_string())
|
.to_string())
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Gets optional text value of given XML element for given tag.
|
||||||
pub fn get_option_text(element: &Element, tag: &str) -> Option<String> {
|
pub fn get_option_text(element: &Element, tag: &str) -> Option<String> {
|
||||||
if let Some(v) = element.get_child(tag) {
|
if let Some(v) = element.get_child(tag) {
|
||||||
return Some(v.get_text().unwrap_or_default().to_string());
|
return Some(v.get_text().unwrap_or_default().to_string());
|
||||||
@ -294,12 +318,14 @@ pub fn get_option_text(element: &Element, tag: &str) -> Option<String> {
|
|||||||
None
|
None
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Gets default text value of given XML element for given tag.
|
||||||
pub fn get_default_text(element: &Element, tag: &str) -> String {
|
pub fn get_default_text(element: &Element, tag: &str) -> String {
|
||||||
element.get_child(tag).map_or(String::new(), |v| {
|
element.get_child(tag).map_or(String::new(), |v| {
|
||||||
v.get_text().unwrap_or_default().to_string()
|
v.get_text().unwrap_or_default().to_string()
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Copies source byte slice into destination byte slice
|
||||||
pub fn copy_slice(dst: &mut [u8], src: &[u8]) -> usize {
|
pub fn copy_slice(dst: &mut [u8], src: &[u8]) -> usize {
|
||||||
let mut c = 0;
|
let mut c = 0;
|
||||||
for (d, s) in dst.iter_mut().zip(src.iter()) {
|
for (d, s) in dst.iter_mut().zip(src.iter()) {
|
||||||
|
|||||||
@ -567,7 +567,7 @@ impl<'a> ClientTest<'_> {
|
|||||||
};
|
};
|
||||||
|
|
||||||
let spawned_task = task::spawn(listen_task());
|
let spawned_task = task::spawn(listen_task());
|
||||||
task::sleep(std::time::Duration::from_millis(100)).await;
|
task::sleep(std::time::Duration::from_millis(200)).await;
|
||||||
|
|
||||||
let size = 16_usize;
|
let size = 16_usize;
|
||||||
self.client
|
self.client
|
||||||
@ -1059,10 +1059,14 @@ impl<'a> ClientTest<'_> {
|
|||||||
.await
|
.await
|
||||||
.unwrap();
|
.unwrap();
|
||||||
|
|
||||||
let mut args = SetObjectRetentionArgs::new(&bucket_name, &object_name).unwrap();
|
|
||||||
args.retention_mode = Some(RetentionMode::GOVERNANCE);
|
|
||||||
let retain_until_date = utc_now() + Duration::days(1);
|
let retain_until_date = utc_now() + Duration::days(1);
|
||||||
args.retain_until_date = Some(retain_until_date);
|
let args = SetObjectRetentionArgs::new(
|
||||||
|
&bucket_name,
|
||||||
|
&object_name,
|
||||||
|
Some(RetentionMode::GOVERNANCE),
|
||||||
|
Some(retain_until_date),
|
||||||
|
)
|
||||||
|
.unwrap();
|
||||||
|
|
||||||
self.client.set_object_retention(&args).await.unwrap();
|
self.client.set_object_retention(&args).await.unwrap();
|
||||||
|
|
||||||
@ -1080,7 +1084,7 @@ impl<'a> ClientTest<'_> {
|
|||||||
_ => false,
|
_ => false,
|
||||||
},);
|
},);
|
||||||
|
|
||||||
let mut args = SetObjectRetentionArgs::new(&bucket_name, &object_name).unwrap();
|
let mut args = SetObjectRetentionArgs::new(&bucket_name, &object_name, None, None).unwrap();
|
||||||
args.bypass_governance_mode = true;
|
args.bypass_governance_mode = true;
|
||||||
self.client.set_object_retention(&args).await.unwrap();
|
self.client.set_object_retention(&args).await.unwrap();
|
||||||
|
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user