diff --git a/sdk/storage/azure_storage_blob/assets.json b/sdk/storage/azure_storage_blob/assets.json index 8443d02da4..fde4bc2893 100644 --- a/sdk/storage/azure_storage_blob/assets.json +++ b/sdk/storage/azure_storage_blob/assets.json @@ -1,6 +1,6 @@ { "AssetsRepo": "Azure/azure-sdk-assets", "AssetsRepoPrefixPath": "rust", - "Tag": "rust/azure_storage_blob_873d66a4ea", + "Tag": "rust/azure_storage_blob_84d344d028", "TagPrefix": "rust/azure_storage_blob" } \ No newline at end of file diff --git a/sdk/storage/azure_storage_blob/src/clients/blob_client.rs b/sdk/storage/azure_storage_blob/src/clients/blob_client.rs index d8546facb5..6792aa2810 100644 --- a/sdk/storage/azure_storage_blob/src/clients/blob_client.rs +++ b/sdk/storage/azure_storage_blob/src/clients/blob_client.rs @@ -24,7 +24,7 @@ use azure_core::{ credentials::TokenCredential, http::{ policies::{BearerTokenCredentialPolicy, Policy}, - NoFormat, RequestContent, Response, Url, XmlFormat, + NoFormat, RequestContent, Response, StatusCode, Url, XmlFormat, }, Bytes, Result, }; diff --git a/sdk/storage/azure_storage_blob/src/clients/blob_container_client.rs b/sdk/storage/azure_storage_blob/src/clients/blob_container_client.rs index 312a85c08a..42199e8922 100644 --- a/sdk/storage/azure_storage_blob/src/clients/blob_container_client.rs +++ b/sdk/storage/azure_storage_blob/src/clients/blob_container_client.rs @@ -27,7 +27,7 @@ use azure_core::{ }, Result, }; -use std::sync::Arc; +use std::{collections::HashMap, sync::Arc}; /// A client to interact with a specified Azure storage container. pub struct BlobContainerClient { @@ -111,12 +111,14 @@ impl BlobContainerClient { /// /// # Arguments /// + /// * `metadata` - A HashMap containing the name-value pairs to associate with the container as metadata. /// * `options` - Optional configuration for the request. pub async fn set_metadata( &self, + metadata: HashMap, options: Option>, ) -> Result> { - self.client.set_metadata(options).await + self.client.set_metadata(metadata, options).await } /// Marks the specified container for deletion. The container and any blobs contained within are later deleted during garbage collection. diff --git a/sdk/storage/azure_storage_blob/src/clients/blob_service_client.rs b/sdk/storage/azure_storage_blob/src/clients/blob_service_client.rs index 3ce4326ac4..b898185cc5 100644 --- a/sdk/storage/azure_storage_blob/src/clients/blob_service_client.rs +++ b/sdk/storage/azure_storage_blob/src/clients/blob_service_client.rs @@ -5,7 +5,7 @@ use crate::{ generated::clients::BlobServiceClient as GeneratedBlobServiceClient, models::{ BlobServiceClientGetPropertiesOptions, BlobServiceClientListContainersSegmentOptions, - ListContainersSegmentResponse, StorageServiceProperties, + BlobServiceProperties, ListContainersSegmentResponse, }, pipeline::StorageHeadersPolicy, BlobContainerClient, BlobServiceClientOptions, @@ -80,7 +80,7 @@ impl BlobServiceClient { pub async fn get_properties( &self, options: Option>, - ) -> Result> { + ) -> Result> { self.client.get_properties(options).await } diff --git a/sdk/storage/azure_storage_blob/src/clients/block_blob_client.rs b/sdk/storage/azure_storage_blob/src/clients/block_blob_client.rs index 5436ab67ad..49fe05ed7e 100644 --- a/sdk/storage/azure_storage_blob/src/clients/block_blob_client.rs +++ b/sdk/storage/azure_storage_blob/src/clients/block_blob_client.rs @@ -9,11 +9,9 @@ use crate::{ BlockBlobClientUploadResult, }, models::{ - BlobClientDeleteOptions, BlobClientDownloadOptions, BlobClientGetPropertiesOptions, - BlobClientSetMetadataOptions, BlobClientSetPropertiesOptions, BlobClientSetTierOptions, BlockBlobClientCommitBlockListOptions, BlockBlobClientGetBlockListOptions, BlockBlobClientStageBlockOptions, BlockBlobClientUploadOptions, BlockList, BlockListType, - BlockLookupList, StorageServiceProperties, + BlockLookupList, }, pipeline::StorageHeadersPolicy, BlobClientOptions, BlockBlobClientOptions, diff --git a/sdk/storage/azure_storage_blob/src/generated/clients/blob_container_client.rs b/sdk/storage/azure_storage_blob/src/generated/clients/blob_container_client.rs index 0871c272cd..baef9259e1 100644 --- a/sdk/storage/azure_storage_blob/src/generated/clients/blob_container_client.rs +++ b/sdk/storage/azure_storage_blob/src/generated/clients/blob_container_client.rs @@ -36,7 +36,7 @@ use azure_core::{ time::to_rfc7231, tracing, xml, Error, Result, }; -use std::sync::Arc; +use std::{collections::HashMap, sync::Arc}; #[tracing::client] pub struct BlobContainerClient { @@ -1043,10 +1043,12 @@ impl BlobContainerClient { /// /// # Arguments /// + /// * `metadata` - The metadata headers. /// * `options` - Optional parameters for the request. #[tracing::function("Storage.Blob.Container.setMetadata")] pub async fn set_metadata( &self, + metadata: HashMap, options: Option>, ) -> Result> { let options = options.unwrap_or_default(); @@ -1072,10 +1074,8 @@ impl BlobContainerClient { if let Some(lease_id) = options.lease_id { request.insert_header("x-ms-lease-id", lease_id); } - if let Some(metadata) = options.metadata { - for (k, v) in &metadata { - request.insert_header(format!("x-ms-meta-{k}"), v); - } + for (k, v) in &metadata { + request.insert_header(format!("x-ms-meta-{k}"), v); } request.insert_header("x-ms-version", &self.version); let rsp = self.pipeline.send(&ctx, &mut request).await?; diff --git a/sdk/storage/azure_storage_blob/src/generated/clients/blob_service_client.rs b/sdk/storage/azure_storage_blob/src/generated/clients/blob_service_client.rs index 1cfd4fc4d1..6d16e35c91 100644 --- a/sdk/storage/azure_storage_blob/src/generated/clients/blob_service_client.rs +++ b/sdk/storage/azure_storage_blob/src/generated/clients/blob_service_client.rs @@ -10,7 +10,7 @@ use crate::generated::{ BlobServiceClientGetAccountInfoResult, BlobServiceClientGetPropertiesOptions, BlobServiceClientGetStatisticsOptions, BlobServiceClientGetUserDelegationKeyOptions, BlobServiceClientListContainersSegmentOptions, BlobServiceClientSetPropertiesOptions, - FilterBlobSegment, KeyInfo, ListContainersSegmentResponse, StorageServiceProperties, + BlobServiceProperties, FilterBlobSegment, KeyInfo, ListContainersSegmentResponse, StorageServiceStats, UserDelegationKey, }, }; @@ -212,7 +212,7 @@ impl BlobServiceClient { pub async fn get_properties( &self, options: Option>, - ) -> Result> { + ) -> Result> { let options = options.unwrap_or_default(); let ctx = Context::with_context(&options.method_options.context); let mut url = self.endpoint.clone(); @@ -423,12 +423,12 @@ impl BlobServiceClient { /// /// # Arguments /// - /// * `storage_service_properties` - The storage service properties to set. + /// * `blob_service_properties` - The storage service properties to set. /// * `options` - Optional parameters for the request. #[tracing::function("Storage.Blob.setProperties")] pub async fn set_properties( &self, - storage_service_properties: RequestContent, + blob_service_properties: RequestContent, options: Option>, ) -> Result> { let options = options.unwrap_or_default(); @@ -448,7 +448,7 @@ impl BlobServiceClient { request.insert_header("x-ms-client-request-id", client_request_id); } request.insert_header("x-ms-version", &self.version); - request.set_body(storage_service_properties); + request.set_body(blob_service_properties); let rsp = self.pipeline.send(&ctx, &mut request).await?; if !rsp.status().is_success() { let status = rsp.status(); diff --git a/sdk/storage/azure_storage_blob/src/generated/models/method_options.rs b/sdk/storage/azure_storage_blob/src/generated/models/method_options.rs index ab4a82a118..8ece63fced 100644 --- a/sdk/storage/azure_storage_blob/src/generated/models/method_options.rs +++ b/sdk/storage/azure_storage_blob/src/generated/models/method_options.rs @@ -1519,9 +1519,6 @@ pub struct BlobContainerClientSetMetadataOptions<'a> { /// If specified, the operation only succeeds if the resource's lease is active and matches this ID. pub lease_id: Option, - /// The metadata headers. - pub metadata: Option>, - /// Allows customization of the method call. pub method_options: ClientMethodOptions<'a>, diff --git a/sdk/storage/azure_storage_blob/src/generated/models/models_impl.rs b/sdk/storage/azure_storage_blob/src/generated/models/models_impl.rs index 3621ba90d9..d8f349ac0b 100644 --- a/sdk/storage/azure_storage_blob/src/generated/models/models_impl.rs +++ b/sdk/storage/azure_storage_blob/src/generated/models/models_impl.rs @@ -3,13 +3,20 @@ // Licensed under the MIT License. See License.txt in the project root for license information. // Code generated by Microsoft (R) Rust Code Generator. DO NOT EDIT. -use super::{BlobTags, BlockLookupList, KeyInfo, QueryRequest, StorageServiceProperties}; +use super::{BlobServiceProperties, BlobTags, BlockLookupList, KeyInfo, QueryRequest}; use azure_core::{ http::{RequestContent, XmlFormat}, xml::to_xml, Result, }; +impl TryFrom for RequestContent { + type Error = azure_core::Error; + fn try_from(value: BlobServiceProperties) -> Result { + RequestContent::try_from(to_xml(&value)?) + } +} + impl TryFrom for RequestContent { type Error = azure_core::Error; fn try_from(value: BlobTags) -> Result { @@ -37,10 +44,3 @@ impl TryFrom for RequestContent { RequestContent::try_from(to_xml(&value)?) } } - -impl TryFrom for RequestContent { - type Error = azure_core::Error; - fn try_from(value: StorageServiceProperties) -> Result { - RequestContent::try_from(to_xml(&value)?) - } -} diff --git a/sdk/storage/azure_storage_blob/src/generated/models/pub_models.rs b/sdk/storage/azure_storage_blob/src/generated/models/pub_models.rs index ba2065a4e3..5cfc5da9f5 100644 --- a/sdk/storage/azure_storage_blob/src/generated/models/pub_models.rs +++ b/sdk/storage/azure_storage_blob/src/generated/models/pub_models.rs @@ -549,6 +549,50 @@ pub struct BlobPropertiesInternal { #[derive(SafeDebug)] pub struct BlobServiceClientGetAccountInfoResult; +/// The service properties. +#[derive(Clone, Default, Deserialize, SafeDebug, Serialize)] +pub struct BlobServiceProperties { + /// The CORS properties. + #[serde( + default, + deserialize_with = "CorsCorsRule::unwrap", + rename = "Cors", + serialize_with = "CorsCorsRule::wrap", + skip_serializing_if = "Option::is_none" + )] + pub cors: Option>, + + /// The default service version. + #[serde( + rename = "DefaultServiceVersion", + skip_serializing_if = "Option::is_none" + )] + pub default_service_version: Option, + + /// The delete retention policy. + #[serde( + rename = "DeleteRetentionPolicy", + skip_serializing_if = "Option::is_none" + )] + pub delete_retention_policy: Option, + + /// The hour metrics properties. + #[serde(rename = "HourMetrics", skip_serializing_if = "Option::is_none")] + pub hour_metrics: Option, + + /// The logging properties. + #[serde(rename = "Logging", skip_serializing_if = "Option::is_none")] + pub logging: Option, + + /// The minute metrics properties. + #[serde(rename = "MinuteMetrics", skip_serializing_if = "Option::is_none")] + pub minute_metrics: Option, + + /// The static website properties. + #[serde(rename = "StaticWebsite", skip_serializing_if = "Option::is_none")] + pub static_website: Option, +} + /// The blob tags. #[derive(Clone, Default, Deserialize, SafeDebug, Serialize)] #[serde(rename = "Tag")] @@ -1282,50 +1326,6 @@ pub struct StaticWebsite { pub index_document: Option, } -/// The service properties. -#[derive(Clone, Default, Deserialize, SafeDebug, Serialize)] -pub struct StorageServiceProperties { - /// The CORS properties. - #[serde( - default, - deserialize_with = "CorsCorsRule::unwrap", - rename = "Cors", - serialize_with = "CorsCorsRule::wrap", - skip_serializing_if = "Option::is_none" - )] - pub cors: Option>, - - /// The default service version. - #[serde( - rename = "DefaultServiceVersion", - skip_serializing_if = "Option::is_none" - )] - pub default_service_version: Option, - - /// The delete retention policy. - #[serde( - rename = "DeleteRetentionPolicy", - skip_serializing_if = "Option::is_none" - )] - pub delete_retention_policy: Option, - - /// The hour metrics properties. - #[serde(rename = "HourMetrics", skip_serializing_if = "Option::is_none")] - pub hour_metrics: Option, - - /// The logging properties. - #[serde(rename = "Logging", skip_serializing_if = "Option::is_none")] - pub logging: Option, - - /// The minute metrics properties. - #[serde(rename = "MinuteMetrics", skip_serializing_if = "Option::is_none")] - pub minute_metrics: Option, - - /// The static website properties. - #[serde(rename = "StaticWebsite", skip_serializing_if = "Option::is_none")] - pub static_website: Option, -} - /// Stats for the storage service. #[derive(Clone, Default, Deserialize, SafeDebug, Serialize)] #[non_exhaustive] diff --git a/sdk/storage/azure_storage_blob/src/models/mod.rs b/sdk/storage/azure_storage_blob/src/models/mod.rs index 84795abc1e..77772ca381 100644 --- a/sdk/storage/azure_storage_blob/src/models/mod.rs +++ b/sdk/storage/azure_storage_blob/src/models/mod.rs @@ -32,16 +32,17 @@ pub use crate::generated::models::{ BlobContainerClientRenewLeaseOptions, BlobContainerClientRenewLeaseResult, BlobContainerClientSetMetadataOptions, BlobFlatListSegment, BlobImmutabilityPolicyMode, BlobItemInternal, BlobMetadata, BlobName, BlobPropertiesInternal, - BlobServiceClientGetPropertiesOptions, BlobServiceClientListContainersSegmentOptions, BlobTag, - BlobTags, BlobType, Block, BlockBlobClientCommitBlockListOptions, - BlockBlobClientCommitBlockListResult, BlockBlobClientCommitBlockListResultHeaders, - BlockBlobClientGetBlockListOptions, BlockBlobClientStageBlockOptions, - BlockBlobClientStageBlockResult, BlockBlobClientStageBlockResultHeaders, - BlockBlobClientUploadOptions, BlockBlobClientUploadResult, BlockBlobClientUploadResultHeaders, - BlockList, BlockListType, BlockLookupList, ContainerItem, CopyStatus, CorsRule, LeaseDuration, - LeaseState, LeaseStatus, ListBlobsFlatSegmentResponse, ListBlobsIncludeItem, - ListContainersIncludeType, ListContainersSegmentResponse, Logging, Metrics, - ObjectReplicationMetadata, PageBlobClientClearPagesOptions, PageBlobClientClearPagesResult, + BlobServiceClientGetPropertiesOptions, BlobServiceClientListContainersSegmentOptions, + BlobServiceProperties, BlobTag, BlobTags, BlobType, Block, + BlockBlobClientCommitBlockListOptions, BlockBlobClientCommitBlockListResult, + BlockBlobClientCommitBlockListResultHeaders, BlockBlobClientGetBlockListOptions, + BlockBlobClientStageBlockOptions, BlockBlobClientStageBlockResult, + BlockBlobClientStageBlockResultHeaders, BlockBlobClientUploadOptions, + BlockBlobClientUploadResult, BlockBlobClientUploadResultHeaders, BlockList, BlockListType, + BlockLookupList, ContainerItem, CopyStatus, CorsRule, LeaseDuration, LeaseState, LeaseStatus, + ListBlobsFlatSegmentResponse, ListBlobsIncludeItem, ListContainersIncludeType, + ListContainersSegmentResponse, Logging, Metrics, ObjectReplicationMetadata, + PageBlobClientClearPagesOptions, PageBlobClientClearPagesResult, PageBlobClientClearPagesResultHeaders, PageBlobClientCreateOptions, PageBlobClientCreateResult, PageBlobClientCreateResultHeaders, PageBlobClientGetPageRangesOptions, PageBlobClientResizeOptions, PageBlobClientResizeResult, PageBlobClientResizeResultHeaders, @@ -50,6 +51,6 @@ pub use crate::generated::models::{ PageBlobClientUploadPagesFromUrlResult, PageBlobClientUploadPagesOptions, PageBlobClientUploadPagesResult, PageBlobClientUploadPagesResultHeaders, PageList, PremiumPageBlobAccessTier, PublicAccessType, RehydratePriority, RetentionPolicy, - SequenceNumberActionType, StaticWebsite, StorageServiceProperties, + SequenceNumberActionType, StaticWebsite, }; pub use extensions::*; diff --git a/sdk/storage/azure_storage_blob/tests/blob_client.rs b/sdk/storage/azure_storage_blob/tests/blob_client.rs index 5d5818b2f9..f156f89a97 100644 --- a/sdk/storage/azure_storage_blob/tests/blob_client.rs +++ b/sdk/storage/azure_storage_blob/tests/blob_client.rs @@ -17,6 +17,27 @@ use azure_storage_blob_test::{create_test_blob, get_blob_name, get_container_cli use std::{collections::HashMap, error::Error, time::Duration}; use tokio::time; +#[recorded::test] +async fn test_blob_exists(ctx: TestContext) -> Result<(), Box> { + // Recording Setup + let recording = ctx.recording(); + let container_client = get_container_client(recording, false).await?; + let blob_client = container_client.blob_client(get_blob_name(recording)); + container_client.create_container(None).await?; + + // Blob Does Not Exists Scenario + let response = blob_client.exists().await?; + assert!(!response); + + // Blob Exists Scenario + create_test_blob(&blob_client).await?; + let response = blob_client.exists().await?; + assert!(response); + + container_client.delete_container(None).await?; + Ok(()) +} + #[recorded::test] async fn test_get_blob_properties(ctx: TestContext) -> Result<(), Box> { // Recording Setup diff --git a/sdk/storage/azure_storage_blob/tests/blob_container_client.rs b/sdk/storage/azure_storage_blob/tests/blob_container_client.rs index 79ebc320f9..65a169a88e 100644 --- a/sdk/storage/azure_storage_blob/tests/blob_container_client.rs +++ b/sdk/storage/azure_storage_blob/tests/blob_container_client.rs @@ -63,12 +63,8 @@ async fn test_set_container_metadata(ctx: TestContext) -> Result<(), Box Result<(), Box Result<(), Box Result<(), Box