mirror of
https://github.com/rustfs/rustfs.git
synced 2026-08-08 22:33:22 +00:00
60f14cb0f1
* fix(bucket-encryption): populate default KMS key for SSE-KMS without key ID When PutBucketEncryption receives SSE-KMS configuration without a specific KMS key ID, query the KMS service for the default key and populate KMSMasterKeyID before storing. This ensures GetBucketEncryption responses include the key ID, which S3 clients like mc rely on to distinguish SSE-KMS from SSE-S3 in their display logic. Fixes #3039 * test(kms): cover empty bucket encryption key ID * fix(bucket-encryption): require default KMS key
595 lines
22 KiB
Rust
595 lines
22 KiB
Rust
// Copyright 2024 RustFS Team
|
|
//
|
|
// Licensed under the Apache License, Version 2.0 (the "License");
|
|
// you may not use this file except in compliance with the License.
|
|
// You may obtain a copy of the License at
|
|
//
|
|
// http://www.apache.org/licenses/LICENSE-2.0
|
|
//
|
|
// Unless required by applicable law or agreed to in writing, software
|
|
// distributed under the License is distributed on an "AS IS" BASIS,
|
|
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
// See the License for the specific language governing permissions and
|
|
// limitations under the License.
|
|
|
|
//! Bucket Default Encryption Configuration Integration Tests
|
|
//!
|
|
//! This test suite verifies that bucket-level default encryption configuration is properly integrated with:
|
|
//! 1. put_object operations
|
|
//! 2. create_multipart_upload operations
|
|
//! 3. KMS service integration
|
|
|
|
use super::common::LocalKMSTestEnvironment;
|
|
use crate::common::{TEST_BUCKET, init_logging};
|
|
use aws_sdk_s3::types::{
|
|
ServerSideEncryption, ServerSideEncryptionByDefault, ServerSideEncryptionConfiguration, ServerSideEncryptionRule,
|
|
};
|
|
use serial_test::serial;
|
|
use tracing::{debug, info, warn};
|
|
|
|
/// Test 1: When bucket is configured with default SSE-S3 encryption, put_object should automatically apply encryption
|
|
#[tokio::test]
|
|
#[serial]
|
|
async fn test_bucket_default_sse_s3_put_object() -> Result<(), Box<dyn std::error::Error + Send + Sync>> {
|
|
init_logging();
|
|
info!("Testing bucket default SSE-S3 encryption impact on put_object");
|
|
|
|
let mut kms_env = LocalKMSTestEnvironment::new().await?;
|
|
let _default_key_id = kms_env.start_rustfs_for_local_kms().await?;
|
|
tokio::time::sleep(tokio::time::Duration::from_secs(3)).await;
|
|
|
|
let s3_client = kms_env.base_env.create_s3_client();
|
|
kms_env.base_env.create_test_bucket(TEST_BUCKET).await?;
|
|
|
|
// Step 1: Set bucket default encryption to SSE-S3
|
|
info!("Setting bucket default encryption configuration");
|
|
let encryption_config = ServerSideEncryptionConfiguration::builder()
|
|
.rules(
|
|
ServerSideEncryptionRule::builder()
|
|
.apply_server_side_encryption_by_default(
|
|
ServerSideEncryptionByDefault::builder()
|
|
.sse_algorithm(ServerSideEncryption::Aes256)
|
|
.build()
|
|
.unwrap(),
|
|
)
|
|
.build(),
|
|
)
|
|
.build()
|
|
.unwrap();
|
|
|
|
s3_client
|
|
.put_bucket_encryption()
|
|
.bucket(TEST_BUCKET)
|
|
.server_side_encryption_configuration(encryption_config)
|
|
.send()
|
|
.await
|
|
.expect("Failed to set bucket encryption");
|
|
|
|
info!("Bucket default encryption configuration set successfully");
|
|
|
|
// Verify bucket encryption configuration
|
|
let get_encryption_response = s3_client
|
|
.get_bucket_encryption()
|
|
.bucket(TEST_BUCKET)
|
|
.send()
|
|
.await
|
|
.expect("Failed to get bucket encryption");
|
|
|
|
debug!(
|
|
"Bucket encryption configuration: {:?}",
|
|
get_encryption_response.server_side_encryption_configuration()
|
|
);
|
|
|
|
// Step 2: put_object without specifying encryption parameters should automatically use bucket default encryption
|
|
info!("Uploading file (without specifying encryption parameters, should use bucket default encryption)");
|
|
let test_data = b"test-bucket-default-sse-s3-data";
|
|
let test_key = "test-bucket-default-sse-s3.txt";
|
|
|
|
let put_response = s3_client
|
|
.put_object()
|
|
.bucket(TEST_BUCKET)
|
|
.key(test_key)
|
|
.body(test_data.to_vec().into())
|
|
// Note: No server_side_encryption specified here, should use bucket default
|
|
.send()
|
|
.await
|
|
.expect("Failed to put object");
|
|
|
|
debug!(
|
|
"PUT response: ETag={:?}, SSE={:?}",
|
|
put_response.e_tag(),
|
|
put_response.server_side_encryption()
|
|
);
|
|
|
|
// Verify: Response should contain SSE-S3 encryption information
|
|
assert_eq!(
|
|
put_response.server_side_encryption(),
|
|
Some(&ServerSideEncryption::Aes256),
|
|
"put_object response should contain bucket default SSE-S3 encryption information"
|
|
);
|
|
|
|
// Step 3: Download file and verify encryption status
|
|
info!("Downloading file and verifying encryption status");
|
|
let get_response = s3_client
|
|
.get_object()
|
|
.bucket(TEST_BUCKET)
|
|
.key(test_key)
|
|
.send()
|
|
.await
|
|
.expect("Failed to get object");
|
|
|
|
debug!("GET response: SSE={:?}", get_response.server_side_encryption());
|
|
|
|
// Verify: GET response should contain encryption information
|
|
assert_eq!(
|
|
get_response.server_side_encryption(),
|
|
Some(&ServerSideEncryption::Aes256),
|
|
"get_object response should contain SSE-S3 encryption information"
|
|
);
|
|
|
|
// Verify data integrity
|
|
let downloaded_data = get_response
|
|
.body
|
|
.collect()
|
|
.await
|
|
.expect("Failed to collect body")
|
|
.into_bytes();
|
|
assert_eq!(&downloaded_data[..], test_data, "Downloaded data should match original data");
|
|
|
|
// Step 4: Explicitly specifying encryption parameters should override bucket default
|
|
info!("Uploading file (explicitly specifying no encryption, should override bucket default)");
|
|
let _test_key_2 = "test-explicit-override.txt";
|
|
// Note: This test might temporarily fail because current implementation might not support explicit override
|
|
// But this is the target behavior we want to implement
|
|
warn!("Test for explicitly overriding bucket default encryption is temporarily skipped, this is a feature to be implemented");
|
|
|
|
// TODO: Add test for explicit override when implemented
|
|
|
|
info!("Test passed: bucket default SSE-S3 encryption correctly applied to put_object");
|
|
|
|
Ok(())
|
|
}
|
|
|
|
/// Test 2: When bucket is configured with default SSE-KMS encryption, put_object should automatically apply encryption and use the specified KMS key
|
|
#[tokio::test]
|
|
#[serial]
|
|
async fn test_bucket_default_sse_kms_put_object() -> Result<(), Box<dyn std::error::Error + Send + Sync>> {
|
|
init_logging();
|
|
info!("Testing bucket default SSE-KMS encryption impact on put_object");
|
|
|
|
let mut kms_env = LocalKMSTestEnvironment::new().await?;
|
|
let default_key_id = kms_env.start_rustfs_for_local_kms().await?;
|
|
tokio::time::sleep(tokio::time::Duration::from_secs(3)).await;
|
|
|
|
let s3_client = kms_env.base_env.create_s3_client();
|
|
kms_env.base_env.create_test_bucket(TEST_BUCKET).await?;
|
|
|
|
// Step 1: Set bucket default encryption to SSE-KMS with specified KMS key
|
|
info!("Setting bucket default encryption configuration to SSE-KMS");
|
|
let encryption_config = ServerSideEncryptionConfiguration::builder()
|
|
.rules(
|
|
ServerSideEncryptionRule::builder()
|
|
.apply_server_side_encryption_by_default(
|
|
ServerSideEncryptionByDefault::builder()
|
|
.sse_algorithm(ServerSideEncryption::AwsKms)
|
|
.kms_master_key_id(&default_key_id)
|
|
.build()
|
|
.unwrap(),
|
|
)
|
|
.build(),
|
|
)
|
|
.build()
|
|
.unwrap();
|
|
|
|
s3_client
|
|
.put_bucket_encryption()
|
|
.bucket(TEST_BUCKET)
|
|
.server_side_encryption_configuration(encryption_config)
|
|
.send()
|
|
.await
|
|
.expect("Failed to set bucket SSE-KMS encryption");
|
|
|
|
info!("Bucket default SSE-KMS encryption configuration set successfully");
|
|
|
|
// Step 2: put_object without specifying encryption parameters should automatically use bucket default SSE-KMS
|
|
info!("Uploading file (without specifying encryption parameters, should use bucket default SSE-KMS)");
|
|
let test_data = b"test-bucket-default-sse-kms-data";
|
|
let test_key = "test-bucket-default-sse-kms.txt";
|
|
|
|
let put_response = s3_client
|
|
.put_object()
|
|
.bucket(TEST_BUCKET)
|
|
.key(test_key)
|
|
.body(test_data.to_vec().into())
|
|
// Note: No encryption parameters specified here, should use bucket default SSE-KMS
|
|
.send()
|
|
.await
|
|
.expect("Failed to put object with bucket default SSE-KMS");
|
|
|
|
debug!(
|
|
"PUT response: ETag={:?}, SSE={:?}, KMS_Key={:?}",
|
|
put_response.e_tag(),
|
|
put_response.server_side_encryption(),
|
|
put_response.ssekms_key_id()
|
|
);
|
|
|
|
// Verify: Response should contain SSE-KMS encryption information
|
|
assert_eq!(
|
|
put_response.server_side_encryption(),
|
|
Some(&ServerSideEncryption::AwsKms),
|
|
"put_object response should contain bucket default SSE-KMS encryption information"
|
|
);
|
|
|
|
assert_eq!(
|
|
put_response.ssekms_key_id().unwrap(),
|
|
&default_key_id,
|
|
"put_object response should contain correct KMS key ID"
|
|
);
|
|
|
|
// Step 3: Download file and verify encryption status
|
|
info!("Downloading file and verifying encryption status");
|
|
let get_response = s3_client
|
|
.get_object()
|
|
.bucket(TEST_BUCKET)
|
|
.key(test_key)
|
|
.send()
|
|
.await
|
|
.expect("Failed to get object");
|
|
|
|
debug!(
|
|
"GET response: SSE={:?}, KMS_Key={:?}",
|
|
get_response.server_side_encryption(),
|
|
get_response.ssekms_key_id()
|
|
);
|
|
|
|
// Verify: GET response should contain encryption information
|
|
assert_eq!(
|
|
get_response.server_side_encryption(),
|
|
Some(&ServerSideEncryption::AwsKms),
|
|
"get_object response should contain SSE-KMS encryption information"
|
|
);
|
|
|
|
assert_eq!(
|
|
get_response.ssekms_key_id().unwrap(),
|
|
&default_key_id,
|
|
"get_object response should contain correct KMS key ID"
|
|
);
|
|
|
|
// Verify data integrity
|
|
let downloaded_data = get_response
|
|
.body
|
|
.collect()
|
|
.await
|
|
.expect("Failed to collect body")
|
|
.into_bytes();
|
|
assert_eq!(&downloaded_data[..], test_data, "Downloaded data should match original data");
|
|
|
|
// Cleanup is handled automatically when the test environment is dropped
|
|
info!("Test passed: bucket default SSE-KMS encryption correctly applied to put_object");
|
|
|
|
Ok(())
|
|
}
|
|
|
|
/// Test 3: When bucket is configured with default encryption, create_multipart_upload should inherit the configuration
|
|
#[tokio::test]
|
|
#[serial]
|
|
async fn test_bucket_default_encryption_multipart_upload() -> Result<(), Box<dyn std::error::Error + Send + Sync>> {
|
|
init_logging();
|
|
info!("Testing bucket default encryption impact on create_multipart_upload");
|
|
|
|
let mut kms_env = LocalKMSTestEnvironment::new().await?;
|
|
let default_key_id = kms_env.start_rustfs_for_local_kms().await?;
|
|
tokio::time::sleep(tokio::time::Duration::from_secs(3)).await;
|
|
|
|
let s3_client = kms_env.base_env.create_s3_client();
|
|
kms_env.base_env.create_test_bucket(TEST_BUCKET).await?;
|
|
|
|
// Step 1: Set bucket default encryption to SSE-KMS
|
|
info!("Setting bucket default encryption configuration to SSE-KMS");
|
|
let encryption_config = ServerSideEncryptionConfiguration::builder()
|
|
.rules(
|
|
ServerSideEncryptionRule::builder()
|
|
.apply_server_side_encryption_by_default(
|
|
ServerSideEncryptionByDefault::builder()
|
|
.sse_algorithm(ServerSideEncryption::AwsKms)
|
|
.kms_master_key_id(&default_key_id)
|
|
.build()
|
|
.unwrap(),
|
|
)
|
|
.build(),
|
|
)
|
|
.build()
|
|
.unwrap();
|
|
|
|
s3_client
|
|
.put_bucket_encryption()
|
|
.bucket(TEST_BUCKET)
|
|
.server_side_encryption_configuration(encryption_config)
|
|
.send()
|
|
.await
|
|
.expect("Failed to set bucket encryption");
|
|
|
|
// Step 2: Create multipart upload (without specifying encryption parameters)
|
|
info!("Creating multipart upload (without specifying encryption parameters, should use bucket default configuration)");
|
|
let test_key = "test-multipart-bucket-default.txt";
|
|
|
|
let create_multipart_response = s3_client
|
|
.create_multipart_upload()
|
|
.bucket(TEST_BUCKET)
|
|
.key(test_key)
|
|
// Note: No encryption parameters specified here, should use bucket default configuration
|
|
.send()
|
|
.await
|
|
.expect("Failed to create multipart upload");
|
|
|
|
let upload_id = create_multipart_response.upload_id().unwrap();
|
|
debug!(
|
|
"CreateMultipartUpload response: UploadId={}, SSE={:?}, KMS_Key={:?}",
|
|
upload_id,
|
|
create_multipart_response.server_side_encryption(),
|
|
create_multipart_response.ssekms_key_id()
|
|
);
|
|
|
|
// Verify: create_multipart_upload response should contain bucket default encryption configuration
|
|
assert_eq!(
|
|
create_multipart_response.server_side_encryption(),
|
|
Some(&ServerSideEncryption::AwsKms),
|
|
"create_multipart_upload response should contain bucket default SSE-KMS encryption information"
|
|
);
|
|
|
|
assert_eq!(
|
|
create_multipart_response.ssekms_key_id().unwrap(),
|
|
&default_key_id,
|
|
"create_multipart_upload response should contain correct KMS key ID"
|
|
);
|
|
|
|
// Step 3: Upload a part and complete multipart upload
|
|
info!("Uploading part and completing multipart upload");
|
|
let test_data = b"test-multipart-bucket-default-encryption-data";
|
|
|
|
// Upload part 1
|
|
let upload_part_response = s3_client
|
|
.upload_part()
|
|
.bucket(TEST_BUCKET)
|
|
.key(test_key)
|
|
.upload_id(upload_id)
|
|
.part_number(1)
|
|
.body(test_data.to_vec().into())
|
|
.send()
|
|
.await
|
|
.expect("Failed to upload part");
|
|
|
|
let etag = upload_part_response.e_tag().unwrap().to_string();
|
|
|
|
// Complete multipart upload
|
|
let completed_part = aws_sdk_s3::types::CompletedPart::builder()
|
|
.part_number(1)
|
|
.e_tag(&etag)
|
|
.build();
|
|
|
|
let complete_multipart_response = s3_client
|
|
.complete_multipart_upload()
|
|
.bucket(TEST_BUCKET)
|
|
.key(test_key)
|
|
.upload_id(upload_id)
|
|
.multipart_upload(
|
|
aws_sdk_s3::types::CompletedMultipartUpload::builder()
|
|
.parts(completed_part)
|
|
.build(),
|
|
)
|
|
.send()
|
|
.await
|
|
.expect("Failed to complete multipart upload");
|
|
|
|
debug!(
|
|
"CompleteMultipartUpload response: ETag={:?}, SSE={:?}, KMS_Key={:?}",
|
|
complete_multipart_response.e_tag(),
|
|
complete_multipart_response.server_side_encryption(),
|
|
complete_multipart_response.ssekms_key_id()
|
|
);
|
|
|
|
assert_eq!(
|
|
complete_multipart_response.server_side_encryption(),
|
|
Some(&ServerSideEncryption::AwsKms),
|
|
"complete_multipart_upload response should contain SSE-KMS encryption information"
|
|
);
|
|
|
|
// Step 4: Download file and verify encryption status
|
|
info!("Downloading file and verifying encryption status");
|
|
let get_response = s3_client
|
|
.get_object()
|
|
.bucket(TEST_BUCKET)
|
|
.key(test_key)
|
|
.send()
|
|
.await
|
|
.expect("Failed to get object");
|
|
|
|
// Verify: Final object should be properly encrypted
|
|
assert_eq!(
|
|
get_response.server_side_encryption(),
|
|
Some(&ServerSideEncryption::AwsKms),
|
|
"Final object should contain SSE-KMS encryption information"
|
|
);
|
|
|
|
// Verify data integrity
|
|
let downloaded_data = get_response
|
|
.body
|
|
.collect()
|
|
.await
|
|
.expect("Failed to collect body")
|
|
.into_bytes();
|
|
assert_eq!(&downloaded_data[..], test_data, "Downloaded data should match original data");
|
|
|
|
// Cleanup is handled automatically when the test environment is dropped
|
|
info!("Test passed: bucket default encryption correctly applied to multipart upload");
|
|
|
|
Ok(())
|
|
}
|
|
|
|
/// Test 4: Explicitly specified encryption parameters in requests should override bucket default configuration
|
|
#[tokio::test]
|
|
#[serial]
|
|
async fn test_explicit_encryption_overrides_bucket_default() -> Result<(), Box<dyn std::error::Error + Send + Sync>> {
|
|
init_logging();
|
|
info!("Testing explicitly specified encryption parameters override bucket default configuration");
|
|
|
|
let mut kms_env = LocalKMSTestEnvironment::new().await?;
|
|
let default_key_id = kms_env.start_rustfs_for_local_kms().await?;
|
|
tokio::time::sleep(tokio::time::Duration::from_secs(3)).await;
|
|
|
|
let s3_client = kms_env.base_env.create_s3_client();
|
|
kms_env.base_env.create_test_bucket(TEST_BUCKET).await?;
|
|
|
|
// Step 1: Set bucket default encryption to SSE-S3
|
|
info!("Setting bucket default encryption configuration to SSE-S3");
|
|
let encryption_config = ServerSideEncryptionConfiguration::builder()
|
|
.rules(
|
|
ServerSideEncryptionRule::builder()
|
|
.apply_server_side_encryption_by_default(
|
|
ServerSideEncryptionByDefault::builder()
|
|
.sse_algorithm(ServerSideEncryption::Aes256)
|
|
.build()
|
|
.unwrap(),
|
|
)
|
|
.build(),
|
|
)
|
|
.build()
|
|
.unwrap();
|
|
|
|
s3_client
|
|
.put_bucket_encryption()
|
|
.bucket(TEST_BUCKET)
|
|
.server_side_encryption_configuration(encryption_config)
|
|
.send()
|
|
.await
|
|
.expect("Failed to set bucket encryption");
|
|
|
|
// Step 2: Explicitly specify SSE-KMS encryption (should override bucket default SSE-S3)
|
|
info!("Uploading file (explicitly specifying SSE-KMS, should override bucket default SSE-S3)");
|
|
let test_data = b"test-explicit-override-data";
|
|
let test_key = "test-explicit-override.txt";
|
|
|
|
let put_response = s3_client
|
|
.put_object()
|
|
.bucket(TEST_BUCKET)
|
|
.key(test_key)
|
|
.body(test_data.to_vec().into())
|
|
// Explicitly specify SSE-KMS, should override bucket default SSE-S3
|
|
.server_side_encryption(ServerSideEncryption::AwsKms)
|
|
.ssekms_key_id(&default_key_id)
|
|
.send()
|
|
.await
|
|
.expect("Failed to put object with explicit SSE-KMS");
|
|
|
|
debug!(
|
|
"PUT response: SSE={:?}, KMS_Key={:?}",
|
|
put_response.server_side_encryption(),
|
|
put_response.ssekms_key_id()
|
|
);
|
|
|
|
// Verify: Should use explicitly specified SSE-KMS, not bucket default SSE-S3
|
|
assert_eq!(
|
|
put_response.server_side_encryption(),
|
|
Some(&ServerSideEncryption::AwsKms),
|
|
"Explicitly specified SSE-KMS should override bucket default SSE-S3"
|
|
);
|
|
|
|
assert_eq!(
|
|
put_response.ssekms_key_id().unwrap(),
|
|
&default_key_id,
|
|
"Should use explicitly specified KMS key ID"
|
|
);
|
|
|
|
// Verify GET response
|
|
let get_response = s3_client
|
|
.get_object()
|
|
.bucket(TEST_BUCKET)
|
|
.key(test_key)
|
|
.send()
|
|
.await
|
|
.expect("Failed to get object");
|
|
|
|
assert_eq!(
|
|
get_response.server_side_encryption(),
|
|
Some(&ServerSideEncryption::AwsKms),
|
|
"GET response should reflect the actually used SSE-KMS encryption"
|
|
);
|
|
|
|
// Cleanup is handled automatically when the test environment is dropped
|
|
info!("Test passed: explicitly specified encryption parameters correctly override bucket default configuration");
|
|
|
|
Ok(())
|
|
}
|
|
|
|
/// Test 5: Setting SSE-KMS without a specific key ID should auto-populate the
|
|
/// default KMS key ID so that GetBucketEncryption returns it (issue #3039).
|
|
#[tokio::test]
|
|
#[serial]
|
|
async fn test_sse_kms_without_key_id_populates_default() -> Result<(), Box<dyn std::error::Error + Send + Sync>> {
|
|
init_logging();
|
|
info!("Testing SSE-KMS without explicit key ID populates default key");
|
|
|
|
let mut kms_env = LocalKMSTestEnvironment::new().await?;
|
|
let default_key_id = kms_env.start_rustfs_for_local_kms().await?;
|
|
tokio::time::sleep(tokio::time::Duration::from_secs(3)).await;
|
|
|
|
let s3_client = kms_env.base_env.create_s3_client();
|
|
kms_env.base_env.create_test_bucket(TEST_BUCKET).await?;
|
|
|
|
// Set bucket encryption to SSE-KMS WITHOUT specifying a key ID
|
|
info!("Setting bucket default encryption to SSE-KMS without key ID");
|
|
let encryption_config = ServerSideEncryptionConfiguration::builder()
|
|
.rules(
|
|
ServerSideEncryptionRule::builder()
|
|
.apply_server_side_encryption_by_default(
|
|
ServerSideEncryptionByDefault::builder()
|
|
.sse_algorithm(ServerSideEncryption::AwsKms)
|
|
.kms_master_key_id("")
|
|
.build()
|
|
.unwrap(),
|
|
)
|
|
.build(),
|
|
)
|
|
.build()
|
|
.unwrap();
|
|
|
|
s3_client
|
|
.put_bucket_encryption()
|
|
.bucket(TEST_BUCKET)
|
|
.server_side_encryption_configuration(encryption_config)
|
|
.send()
|
|
.await
|
|
.expect("Failed to set bucket SSE-KMS encryption without key ID");
|
|
|
|
// GetBucketEncryption should return the default KMS key ID
|
|
info!("Verifying GetBucketEncryption returns default KMS key ID");
|
|
let get_response = s3_client
|
|
.get_bucket_encryption()
|
|
.bucket(TEST_BUCKET)
|
|
.send()
|
|
.await
|
|
.expect("Failed to get bucket encryption");
|
|
|
|
let config = get_response.server_side_encryption_configuration();
|
|
let rule = config
|
|
.and_then(|c| c.rules().first())
|
|
.expect("Should have at least one encryption rule");
|
|
let by_default = rule
|
|
.apply_server_side_encryption_by_default()
|
|
.expect("Should have ApplyServerSideEncryptionByDefault");
|
|
|
|
assert_eq!(by_default.sse_algorithm(), &ServerSideEncryption::AwsKms, "Algorithm should be aws:kms");
|
|
assert!(
|
|
by_default.kms_master_key_id().is_some(),
|
|
"KMS key ID should be populated with the default key (was None)"
|
|
);
|
|
assert_eq!(
|
|
by_default.kms_master_key_id().unwrap(),
|
|
&default_key_id,
|
|
"KMS key ID should match the configured default key"
|
|
);
|
|
|
|
info!("Test passed: SSE-KMS without key ID correctly populates default key '{}'", default_key_id);
|
|
Ok(())
|
|
}
|