Skip to main content

Client

Struct Client 

Source
pub struct Client { /* private fields */ }

Implementations§

Source§

impl Client

Source

pub fn create_aws_kms_keyring(&self) -> CreateAwsKmsKeyringFluentBuilder

Examples found in repository?
examples/keyring/aws_kms_keyring_example.rs (line 69)
30pub async fn encrypt_and_decrypt_with_keyring(
31    example_data: &str,
32    kms_key_id: &str,
33) -> Result<(), crate::BoxError> {
34    // 1. Instantiate the encryption SDK client.
35    // This builds the default client with the RequireEncryptRequireDecrypt commitment policy,
36    // which enforces that this client only encrypts using committing algorithm suites and enforces
37    // that this client will only decrypt encrypted messages that were created with a committing
38    // algorithm suite.
39    let esdk_config = AwsEncryptionSdkConfig::builder().build()?;
40    let esdk_client = esdk_client::Client::from_conf(esdk_config)?;
41
42    // 2. Create a KMS client.
43    let sdk_config = aws_config::load_defaults(aws_config::BehaviorVersion::latest()).await;
44    let kms_client = aws_sdk_kms::Client::new(&sdk_config);
45
46    // 3. Create encryption context.
47    // Remember that your encryption context is NOT SECRET.
48    // For more information, see
49    // https://docs.aws.amazon.com/encryption-sdk/latest/developer-guide/concepts.html#encryption-context
50    let encryption_context = HashMap::from([
51        ("encryption".to_string(), "context".to_string()),
52        ("is not".to_string(), "secret".to_string()),
53        ("but adds".to_string(), "useful metadata".to_string()),
54        (
55            "that can help you".to_string(),
56            "be confident that".to_string(),
57        ),
58        (
59            "the data you are handling".to_string(),
60            "is what you think it is".to_string(),
61        ),
62    ]);
63
64    // 4. Create a KMS keyring
65    let mpl_config = MaterialProvidersConfig::builder().build()?;
66    let mpl = mpl_client::Client::from_conf(mpl_config)?;
67
68    let kms_keyring = mpl
69        .create_aws_kms_keyring()
70        .kms_key_id(kms_key_id)
71        .kms_client(kms_client)
72        .send()
73        .await?;
74
75    // 5. Encrypt the data with the encryption_context
76    let plaintext = example_data.as_bytes();
77
78    let encryption_response = esdk_client
79        .encrypt()
80        .plaintext(plaintext)
81        .keyring(kms_keyring.clone())
82        .encryption_context(encryption_context.clone())
83        .send()
84        .await?;
85
86    let ciphertext = encryption_response
87        .ciphertext
88        .expect("Unable to unwrap ciphertext from encryption response");
89
90    // 6. Demonstrate that the ciphertext and plaintext are different.
91    // (This is an example for demonstration; you do not need to do this in your own code.)
92    assert_ne!(
93        ciphertext,
94        aws_smithy_types::Blob::new(plaintext),
95        "Ciphertext and plaintext data are the same. Invalid encryption"
96    );
97
98    // 7. Decrypt your encrypted data using the same keyring you used on encrypt.
99    let decryption_response = esdk_client
100        .decrypt()
101        .ciphertext(ciphertext)
102        .keyring(kms_keyring)
103        // Provide the encryption context that was supplied to the encrypt method
104        .encryption_context(encryption_context)
105        .send()
106        .await?;
107
108    let decrypted_plaintext = decryption_response
109        .plaintext
110        .expect("Unable to unwrap plaintext from decryption response");
111
112    // 8. Demonstrate that the decrypted plaintext is identical to the original plaintext.
113    // (This is an example for demonstration; you do not need to do this in your own code.)
114    assert_eq!(
115        decrypted_plaintext,
116        aws_smithy_types::Blob::new(plaintext),
117        "Decrypted plaintext should be identical to the original plaintext. Invalid decryption"
118    );
119
120    println!("KMS Keyring Example Completed Successfully");
121
122    Ok(())
123}
More examples
Hide additional examples
examples/set_commitment_policy_example.rs (line 78)
34pub async fn encrypt_and_decrypt_with_keyring(
35    example_data: &str,
36    kms_key_id: &str,
37) -> Result<(), crate::BoxError> {
38    // 1. Instantiate the encryption SDK client.
39    // This example builds the client with the ForbidEncryptAllowDecrypt commitment policy,
40    // which enforces that this client cannot encrypt with key commitment
41    // and it can decrypt ciphertexts encrypted with or without key commitment.
42    // The default commitment policy if you were to build the client like in
43    // the `keyring/aws_kms_keyring_example.rs` is RequireEncryptRequireDecrypt.
44    // We recommend that AWS Encryption SDK users use the default commitment policy
45    // (RequireEncryptRequireDecrypt) whenever possible.
46    let esdk_config = AwsEncryptionSdkConfig::builder()
47        .commitment_policy(ForbidEncryptAllowDecrypt)
48        .build()?;
49    let esdk_client = esdk_client::Client::from_conf(esdk_config)?;
50
51    // 2. Create a KMS client.
52    let sdk_config = aws_config::load_defaults(aws_config::BehaviorVersion::latest()).await;
53    let kms_client = aws_sdk_kms::Client::new(&sdk_config);
54
55    // 3. Create encryption context.
56    // Remember that your encryption context is NOT SECRET.
57    // For more information, see
58    // https://docs.aws.amazon.com/encryption-sdk/latest/developer-guide/concepts.html#encryption-context
59    let encryption_context = HashMap::from([
60        ("encryption".to_string(), "context".to_string()),
61        ("is not".to_string(), "secret".to_string()),
62        ("but adds".to_string(), "useful metadata".to_string()),
63        (
64            "that can help you".to_string(),
65            "be confident that".to_string(),
66        ),
67        (
68            "the data you are handling".to_string(),
69            "is what you think it is".to_string(),
70        ),
71    ]);
72
73    // 4. Create a KMS keyring
74    let mpl_config = MaterialProvidersConfig::builder().build()?;
75    let mpl = mpl_client::Client::from_conf(mpl_config)?;
76
77    let kms_keyring = mpl
78        .create_aws_kms_keyring()
79        .kms_key_id(kms_key_id)
80        .kms_client(kms_client)
81        .send()
82        .await?;
83
84    // 5. Encrypt the data with the encryption_context. Make sure you use a non-committing algorithm
85    // with the commitment policy ForbidEncryptAllowDecrypt. Otherwise esdk_client.encrypt() will throw
86    // Error: AwsCryptographicMaterialProvidersError
87    //   {
88    //     error: InvalidAlgorithmSuiteInfoOnEncrypt
89    //     {
90    //       message: "Configuration conflict. Commitment policy requires only non-committing algorithm suites"
91    //     }
92    //   }
93    // By default for ForbidEncryptAllowDecrypt, the algorithm used is
94    // AlgAes256GcmIv12Tag16HkdfSha384EcdsaP384 which is a non-committing algorithm.
95    let plaintext = example_data.as_bytes();
96
97    let encryption_response = esdk_client
98        .encrypt()
99        .plaintext(plaintext)
100        .keyring(kms_keyring.clone())
101        .encryption_context(encryption_context.clone())
102        .send()
103        .await?;
104
105    let ciphertext = encryption_response
106        .ciphertext
107        .expect("Unable to unwrap ciphertext from encryption response");
108
109    // 6. Demonstrate that the ciphertext and plaintext are different.
110    // (This is an example for demonstration; you do not need to do this in your own code.)
111    assert_ne!(
112        ciphertext,
113        aws_smithy_types::Blob::new(plaintext),
114        "Ciphertext and plaintext data are the same. Invalid encryption"
115    );
116
117    // 7. Decrypt your encrypted data using the same keyring you used on encrypt.
118    let decryption_response = esdk_client
119        .decrypt()
120        .ciphertext(ciphertext)
121        .keyring(kms_keyring)
122        // Provide the encryption context that was supplied to the encrypt method
123        .encryption_context(encryption_context)
124        .send()
125        .await?;
126
127    let decrypted_plaintext = decryption_response
128        .plaintext
129        .expect("Unable to unwrap plaintext from decryption response");
130
131    // 8. Demonstrate that the decrypted plaintext is identical to the original plaintext.
132    // (This is an example for demonstration; you do not need to do this in your own code.)
133    assert_eq!(
134        decrypted_plaintext,
135        aws_smithy_types::Blob::new(plaintext),
136        "Decrypted plaintext should be identical to the original plaintext. Invalid decryption"
137    );
138
139    println!("Set Commitment Policy Example Completed Successfully");
140
141    Ok(())
142}
examples/cryptographic_materials_manager/restrict_algorithm_suite/signing_only_example.rs (line 58)
19pub async fn encrypt_and_decrypt_with_cmm(
20    example_data: &str,
21    kms_key_id: &str,
22) -> Result<(), crate::BoxError> {
23    // 1. Instantiate the encryption SDK client.
24    // This builds the default client with the RequireEncryptRequireDecrypt commitment policy,
25    // which enforces that this client only encrypts using committing algorithm suites and enforces
26    // that this client will only decrypt encrypted messages that were created with a committing
27    // algorithm suite.
28    let esdk_config = AwsEncryptionSdkConfig::builder().build()?;
29    let esdk_client = esdk_client::Client::from_conf(esdk_config)?;
30
31    // 2. Create a KMS client.
32    let sdk_config = aws_config::load_defaults(aws_config::BehaviorVersion::latest()).await;
33    let kms_client = aws_sdk_kms::Client::new(&sdk_config);
34
35    // 3. Create encryption context.
36    // Remember that your encryption context is NOT SECRET.
37    // For more information, see
38    // https://docs.aws.amazon.com/encryption-sdk/latest/developer-guide/concepts.html#encryption-context
39    let encryption_context = HashMap::from([
40        ("encryption".to_string(), "context".to_string()),
41        ("is not".to_string(), "secret".to_string()),
42        ("but adds".to_string(), "useful metadata".to_string()),
43        (
44            "that can help you".to_string(),
45            "be confident that".to_string(),
46        ),
47        (
48            "the data you are handling".to_string(),
49            "is what you think it is".to_string(),
50        ),
51    ]);
52
53    // 4. Create a custom SigningSuiteOnlyCMM
54    let mpl_config = MaterialProvidersConfig::builder().build()?;
55    let mpl = mpl_client::Client::from_conf(mpl_config)?;
56
57    let kms_keyring = mpl
58        .create_aws_kms_keyring()
59        .kms_key_id(kms_key_id)
60        .kms_client(kms_client)
61        .send()
62        .await?;
63
64    let signing_suite_only_cmm = SigningSuiteOnlyCMM::new(kms_keyring);
65
66    let signing_suite_only_cmm_ref: CryptographicMaterialsManagerRef =
67        CryptographicMaterialsManagerRef {
68            inner: ::std::sync::Arc::new(std::sync::Mutex::new(signing_suite_only_cmm)),
69        };
70
71    // 5. Encrypt the data with the encryption_context
72    let plaintext = example_data.as_bytes();
73
74    let encryption_response = esdk_client
75        .encrypt()
76        .plaintext(plaintext)
77        .materials_manager(signing_suite_only_cmm_ref.clone())
78        .encryption_context(encryption_context.clone())
79        .algorithm_suite_id(EsdkAlgorithmSuiteId::AlgAes256GcmHkdfSha512CommitKeyEcdsaP384)
80        .send()
81        .await?;
82
83    let ciphertext = encryption_response
84        .ciphertext
85        .expect("Unable to unwrap ciphertext from encryption response");
86
87    // 6. Demonstrate that the ciphertext and plaintext are different.
88    // (This is an example for demonstration; you do not need to do this in your own code.)
89    assert_ne!(
90        ciphertext,
91        aws_smithy_types::Blob::new(plaintext),
92        "Ciphertext and plaintext data are the same. Invalid encryption"
93    );
94
95    // 7. Decrypt your encrypted data using the same keyring you used on encrypt.
96    let decryption_response = esdk_client
97        .decrypt()
98        .ciphertext(ciphertext)
99        .materials_manager(signing_suite_only_cmm_ref.clone())
100        // Provide the encryption context that was supplied to the encrypt method
101        .encryption_context(encryption_context.clone())
102        .send()
103        .await?;
104
105    let decrypted_plaintext = decryption_response
106        .plaintext
107        .expect("Unable to unwrap plaintext from decryption response");
108
109    // 8. Demonstrate that the decrypted plaintext is identical to the original plaintext.
110    // (This is an example for demonstration; you do not need to do this in your own code.)
111    assert_eq!(
112        decrypted_plaintext,
113        aws_smithy_types::Blob::new(plaintext),
114        "Decrypted plaintext should be identical to the original plaintext. Invalid decryption"
115    );
116
117    // 9. Demonstrate that a Non Signing Algorithm Suite will be rejected
118    // by the CMM.
119    let encryption_response_non_signing = esdk_client
120        .encrypt()
121        .plaintext(plaintext)
122        .materials_manager(signing_suite_only_cmm_ref)
123        .encryption_context(encryption_context.clone())
124        .algorithm_suite_id(EsdkAlgorithmSuiteId::AlgAes256GcmHkdfSha512CommitKey)
125        .send()
126        .await;
127
128    match encryption_response_non_signing {
129        Ok(_) => panic!(
130            "Encrypt using non signing algorithm suite MUST \
131                            raise AwsCryptographicMaterialProvidersError"
132        ),
133        Err(AwsCryptographicMaterialProvidersError { error: _e }) => (),
134        _ => panic!("Unexpected error type"),
135    }
136
137    println!("SigningSuiteOnlyCMM Example Completed Successfully");
138
139    Ok(())
140}
examples/keyring/aws_kms_discovery_multi_keyring_example.rs (line 87)
44pub async fn encrypt_and_decrypt_with_keyring(
45    example_data: &str,
46    kms_key_id: &str,
47    aws_account_id: &str,
48    aws_regions: Vec<String>,
49) -> Result<(), crate::BoxError> {
50    // 1. Instantiate the encryption SDK client.
51    // This builds the default client with the RequireEncryptRequireDecrypt commitment policy,
52    // which enforces that this client only encrypts using committing algorithm suites and enforces
53    // that this client will only decrypt encrypted messages that were created with a committing
54    // algorithm suite.
55    let esdk_config = AwsEncryptionSdkConfig::builder().build()?;
56    let esdk_client = esdk_client::Client::from_conf(esdk_config)?;
57
58    // 2. Create a KMS client.
59    let sdk_config = aws_config::load_defaults(aws_config::BehaviorVersion::latest()).await;
60    let kms_client = aws_sdk_kms::Client::new(&sdk_config);
61
62    // 3. Create encryption context.
63    // Remember that your encryption context is NOT SECRET.
64    // For more information, see
65    // https://docs.aws.amazon.com/encryption-sdk/latest/developer-guide/concepts.html#encryption-context
66    let encryption_context = HashMap::from([
67        ("encryption".to_string(), "context".to_string()),
68        ("is not".to_string(), "secret".to_string()),
69        ("but adds".to_string(), "useful metadata".to_string()),
70        (
71            "that can help you".to_string(),
72            "be confident that".to_string(),
73        ),
74        (
75            "the data you are handling".to_string(),
76            "is what you think it is".to_string(),
77        ),
78    ]);
79
80    // 4. Create the keyring that determines how your data keys are protected.
81    //    Although this example highlights Discovery keyrings, Discovery keyrings cannot
82    //    be used to encrypt, so for encryption we create a KMS keyring without discovery mode.
83    let mpl_config = MaterialProvidersConfig::builder().build()?;
84    let mpl = mpl_client::Client::from_conf(mpl_config)?;
85
86    let encrypt_kms_keyring = mpl
87        .create_aws_kms_keyring()
88        .kms_key_id(kms_key_id)
89        .kms_client(kms_client.clone())
90        .send()
91        .await?;
92
93    // 5. Encrypt the data with the encryption_context
94    let plaintext = example_data.as_bytes();
95
96    let encryption_response = esdk_client
97        .encrypt()
98        .plaintext(plaintext)
99        .keyring(encrypt_kms_keyring)
100        .encryption_context(encryption_context.clone())
101        .send()
102        .await?;
103
104    let ciphertext = encryption_response
105        .ciphertext
106        .expect("Unable to unwrap ciphertext from encryption response");
107
108    // 6. Demonstrate that the ciphertext and plaintext are different.
109    // (This is an example for demonstration; you do not need to do this in your own code.)
110    assert_ne!(
111        ciphertext,
112        aws_smithy_types::Blob::new(plaintext),
113        "Ciphertext and plaintext data are the same. Invalid encryption"
114    );
115
116    // 7. Now create a Discovery Multi keyring to use for decryption. We'll add a discovery filter
117    //    so that we limit the set of ciphertexts we are willing to decrypt to only ones
118    //    created by KMS keys in our account and partition.
119    let discovery_filter = DiscoveryFilter::builder()
120        .account_ids(vec![aws_account_id.to_string()])
121        .partition("aws".to_string())
122        .build()?;
123
124    // This is a Multi Keyring composed of Discovery Keyrings.
125    // There is a keyring for every region in `regions`.
126    // All the keyrings have the same Discovery Filter.
127    // Each keyring has its own KMS Client, which is created for the keyring's region.
128    let discovery_multi_keyring = mpl
129        .create_aws_kms_discovery_multi_keyring()
130        .regions(aws_regions)
131        .discovery_filter(discovery_filter)
132        .send()
133        .await?;
134
135    // 8. On Decrypt, the header of the encrypted message (ciphertext) will be parsed.
136    // The header contains the Encrypted Data Keys (EDKs), which, if the EDK
137    // was encrypted by a KMS Keyring, includes the KMS Key ARN.
138    // For each member of the Multi Keyring, every EDK will try to be decrypted until a decryption
139    // is successful.
140    // Since every member of the Multi Keyring is a Discovery Keyring:
141    //   Each Keyring will filter the EDKs by the Discovery Filter
142    //       For the filtered EDKs, the keyring will try to decrypt it with the keyring's client.
143    // All of this is done serially, until a success occurs or all keyrings have
144    // failed all (filtered) EDKs.
145    // KMS Discovery Keyrings will attempt to decrypt Multi Region Keys (MRKs) and regular KMS Keys.
146    let decryption_response = esdk_client
147        .decrypt()
148        .ciphertext(ciphertext)
149        .keyring(discovery_multi_keyring)
150        // Provide the encryption context that was supplied to the encrypt method
151        .encryption_context(encryption_context)
152        .send()
153        .await?;
154
155    let decrypted_plaintext = decryption_response
156        .plaintext
157        .expect("Unable to unwrap plaintext from decryption response");
158
159    // 9. Demonstrate that the decrypted plaintext is identical to the original plaintext.
160    // (This is an example for demonstration; you do not need to do this in your own code.)
161    assert_eq!(
162        decrypted_plaintext,
163        aws_smithy_types::Blob::new(plaintext),
164        "Decrypted plaintext should be identical to the original plaintext. Invalid decryption"
165    );
166
167    println!("KMS Discovery Multi Keyring Example Completed Successfully");
168
169    Ok(())
170}
examples/keyring/aws_kms_discovery_keyring_example.rs (line 89)
47pub async fn encrypt_and_decrypt_with_keyring(
48    example_data: &str,
49    kms_key_id: &str,
50    aws_account_id: &str,
51) -> Result<(), crate::BoxError> {
52    // 1. Instantiate the encryption SDK client.
53    // This builds the default client with the RequireEncryptRequireDecrypt commitment policy,
54    // which enforces that this client only encrypts using committing algorithm suites and enforces
55    // that this client will only decrypt encrypted messages that were created with a committing
56    // algorithm suite.
57    let esdk_config = AwsEncryptionSdkConfig::builder().build()?;
58    let esdk_client = esdk_client::Client::from_conf(esdk_config)?;
59
60    // 2. Create a KMS client.
61    let sdk_config = aws_config::load_defaults(aws_config::BehaviorVersion::latest()).await;
62    let kms_client = aws_sdk_kms::Client::new(&sdk_config);
63
64    // 3. Create encryption context.
65    // Remember that your encryption context is NOT SECRET.
66    // For more information, see
67    // https://docs.aws.amazon.com/encryption-sdk/latest/developer-guide/concepts.html#encryption-context
68    let encryption_context = HashMap::from([
69        ("encryption".to_string(), "context".to_string()),
70        ("is not".to_string(), "secret".to_string()),
71        ("but adds".to_string(), "useful metadata".to_string()),
72        (
73            "that can help you".to_string(),
74            "be confident that".to_string(),
75        ),
76        (
77            "the data you are handling".to_string(),
78            "is what you think it is".to_string(),
79        ),
80    ]);
81
82    // 4. Create the keyring that determines how your data keys are protected.
83    //    Although this example highlights Discovery keyrings, Discovery keyrings cannot
84    //    be used to encrypt, so for encryption we create a KMS keyring without discovery mode.
85    let mpl_config = MaterialProvidersConfig::builder().build()?;
86    let mpl = mpl_client::Client::from_conf(mpl_config)?;
87
88    let encrypt_kms_keyring = mpl
89        .create_aws_kms_keyring()
90        .kms_key_id(kms_key_id)
91        .kms_client(kms_client.clone())
92        .send()
93        .await?;
94
95    // 5. Encrypt the data with the encryption_context
96    let plaintext = example_data.as_bytes();
97
98    let encryption_response = esdk_client
99        .encrypt()
100        .plaintext(plaintext)
101        .keyring(encrypt_kms_keyring)
102        .encryption_context(encryption_context.clone())
103        .send()
104        .await?;
105
106    let ciphertext = encryption_response
107        .ciphertext
108        .expect("Unable to unwrap ciphertext from encryption response");
109
110    // 6. Demonstrate that the ciphertext and plaintext are different.
111    // (This is an example for demonstration; you do not need to do this in your own code.)
112    assert_ne!(
113        ciphertext,
114        aws_smithy_types::Blob::new(plaintext),
115        "Ciphertext and plaintext data are the same. Invalid encryption"
116    );
117
118    // 7. Now create a Discovery keyring to use for decryption. We'll add a discovery filter
119    //    so that we limit the set of ciphertexts we are willing to decrypt to only ones
120    //    created by KMS keys in our account and partition.
121    let discovery_filter = DiscoveryFilter::builder()
122        .account_ids(vec![aws_account_id.to_string()])
123        .partition("aws".to_string())
124        .build()?;
125
126    let discovery_keyring = mpl
127        .create_aws_kms_discovery_keyring()
128        .kms_client(kms_client.clone())
129        .discovery_filter(discovery_filter)
130        .send()
131        .await?;
132
133    // 8. Decrypt your encrypted data using the discovery keyring.
134    //    On Decrypt, the header of the encrypted message (ciphertext) will be parsed.
135    //    The header contains the Encrypted Data Keys (EDKs), which, if the EDK
136    //    was encrypted by a KMS Keyring, includes the KMS Key ARN.
137    //    The Discovery Keyring filters these EDKs for
138    //    EDKs encrypted by Single Region OR Multi Region KMS Keys.
139    //    If a Discovery Filter is present, these KMS Keys must belong
140    //    to an AWS Account ID in the discovery filter's AccountIds and
141    //    must be from the discovery filter's partition.
142    //    Finally, KMS is called to decrypt each filtered EDK until an EDK is
143    //    successfully decrypted. The resulting data key is used to decrypt the
144    //    ciphertext's message.
145    //    If all calls to KMS fail, the decryption fails.
146    let decryption_response = esdk_client
147        .decrypt()
148        .ciphertext(ciphertext.clone())
149        .keyring(discovery_keyring)
150        // Provide the encryption context that was supplied to the encrypt method
151        .encryption_context(encryption_context.clone())
152        .send()
153        .await?;
154
155    let decrypted_plaintext = decryption_response
156        .plaintext
157        .expect("Unable to unwrap plaintext from decryption response");
158
159    // 9. Demonstrate that the decrypted plaintext is identical to the original plaintext.
160    // (This is an example for demonstration; you do not need to do this in your own code.)
161    assert_eq!(
162        decrypted_plaintext,
163        aws_smithy_types::Blob::new(plaintext),
164        "Decrypted plaintext should be identical to the original plaintext. Invalid decryption"
165    );
166
167    // 10. Demonstrate that if a different discovery keyring (Bob's) doesn't have the correct
168    //     AWS Account ID's, the decrypt will fail with an error message
169    //     Note that this assumes Account ID used here ('888888888888') is different than the one used
170    //     during encryption
171    let discovery_filter_bob = DiscoveryFilter::builder()
172        .account_ids(vec!["888888888888".to_string()])
173        .partition("aws".to_string())
174        .build()?;
175
176    let discovery_keyring_bob = mpl
177        .create_aws_kms_discovery_keyring()
178        .kms_client(kms_client)
179        .discovery_filter(discovery_filter_bob)
180        .send()
181        .await?;
182
183    // Decrypt the ciphertext using Bob's discovery keyring which doesn't contain the required
184    // Account ID's for the KMS keyring used for encryption.
185    // This should throw an AwsCryptographicMaterialProvidersError exception
186    let decryption_response_bob = esdk_client
187        .decrypt()
188        .ciphertext(ciphertext)
189        .keyring(discovery_keyring_bob)
190        // Provide the encryption context that was supplied to the encrypt method
191        .encryption_context(encryption_context)
192        .send()
193        .await;
194
195    match decryption_response_bob {
196        Ok(_) => panic!(
197            "Decrypt using discovery keyring with wrong AWS Account ID MUST \
198                            raise AwsCryptographicMaterialProvidersError"
199        ),
200        Err(AwsCryptographicMaterialProvidersError { error: _e }) => (),
201        _ => panic!("Unexpected error type"),
202    }
203
204    println!("KMS Discovery Keyring Example Completed Successfully");
205
206    Ok(())
207}
examples/keyring/multi_keyring_example.rs (line 91)
52pub async fn encrypt_and_decrypt_with_keyring(
53    example_data: &str,
54    kms_key_id: &str,
55) -> Result<(), crate::BoxError> {
56    // 1. Instantiate the encryption SDK client.
57    // This builds the default client with the RequireEncryptRequireDecrypt commitment policy,
58    // which enforces that this client only encrypts using committing algorithm suites and enforces
59    // that this client will only decrypt encrypted messages that were created with a committing
60    // algorithm suite.
61    let esdk_config = AwsEncryptionSdkConfig::builder().build()?;
62    let esdk_client = esdk_client::Client::from_conf(esdk_config)?;
63
64    // 2. Create a KMS client.
65    let sdk_config = aws_config::load_defaults(aws_config::BehaviorVersion::latest()).await;
66    let kms_client = aws_sdk_kms::Client::new(&sdk_config);
67
68    // 3. Create encryption context.
69    // Remember that your encryption context is NOT SECRET.
70    // For more information, see
71    // https://docs.aws.amazon.com/encryption-sdk/latest/developer-guide/concepts.html#encryption-context
72    let encryption_context = HashMap::from([
73        ("encryption".to_string(), "context".to_string()),
74        ("is not".to_string(), "secret".to_string()),
75        ("but adds".to_string(), "useful metadata".to_string()),
76        (
77            "that can help you".to_string(),
78            "be confident that".to_string(),
79        ),
80        (
81            "the data you are handling".to_string(),
82            "is what you think it is".to_string(),
83        ),
84    ]);
85
86    // 4. Create a KMS keyring
87    let mpl_config = MaterialProvidersConfig::builder().build()?;
88    let mpl = mpl_client::Client::from_conf(mpl_config)?;
89
90    let kms_keyring = mpl
91        .create_aws_kms_keyring()
92        .kms_key_id(kms_key_id)
93        .kms_client(kms_client)
94        .send()
95        .await?;
96
97    // 5. Create a raw AES keyring to additionally encrypt under as child_keyring
98
99    // The key namespace and key name are defined by you.
100    // and are used by the Raw AES keyring to determine
101    // whether it should attempt to decrypt an encrypted data key.
102    // For more information, see
103    // https://docs.aws.amazon.com/encryption-sdk/latest/developer-guide/use-raw-aes-keyring.html
104    let key_namespace: &str = "my-key-namespace";
105    let key_name: &str = "my-aes-key-name";
106
107    // Generate a 256-bit AES key to use with your raw AES keyring.
108    // In practice, you should get this key from a secure key management system such as an HSM.
109    let aes_key_bytes = generate_aes_key_bytes();
110
111    let raw_aes_keyring = mpl
112        .create_raw_aes_keyring()
113        .key_name(key_name)
114        .key_namespace(key_namespace)
115        .wrapping_key(aes_key_bytes)
116        .wrapping_alg(AesWrappingAlg::AlgAes256GcmIv12Tag16)
117        .send()
118        .await?;
119
120    // 6. Create a multi_keyring that consists of the previously created keyrings.
121    // When using this multi_keyring to encrypt data, either `kms_keyring` or
122    // `raw_aes_keyring` (or a multi_keyring containing either) may be used to decrypt the data.
123    let multi_keyring = mpl
124        .create_multi_keyring()
125        .generator(kms_keyring.clone())
126        .child_keyrings(vec![raw_aes_keyring.clone()])
127        .send()
128        .await?;
129
130    // 7. Encrypt the data with the encryption_context
131    let plaintext = example_data.as_bytes();
132
133    let encryption_response = esdk_client
134        .encrypt()
135        .plaintext(plaintext)
136        .keyring(multi_keyring.clone())
137        .encryption_context(encryption_context.clone())
138        .send()
139        .await?;
140
141    let ciphertext = encryption_response
142        .ciphertext
143        .expect("Unable to unwrap ciphertext from encryption response");
144
145    // 8. Demonstrate that the ciphertext and plaintext are different.
146    // (This is an example for demonstration; you do not need to do this in your own code.)
147    assert_ne!(
148        ciphertext,
149        aws_smithy_types::Blob::new(plaintext),
150        "Ciphertext and plaintext data are the same. Invalid encryption"
151    );
152
153    // 9a. Decrypt your encrypted data using the same multi_keyring you used on encrypt.
154    let decryption_response_multi_keyring = esdk_client
155        .decrypt()
156        .ciphertext(ciphertext.clone())
157        .keyring(multi_keyring)
158        // Provide the encryption context that was supplied to the encrypt method
159        .encryption_context(encryption_context.clone())
160        .send()
161        .await?;
162
163    let decrypted_plaintext_multi_keyring = decryption_response_multi_keyring
164        .plaintext
165        .expect("Unable to unwrap plaintext from decryption response");
166
167    // 9b. Demonstrate that the decrypted plaintext is identical to the original plaintext.
168    // (This is an example for demonstration; you do not need to do this in your own code.)
169    assert_eq!(
170        decrypted_plaintext_multi_keyring,
171        aws_smithy_types::Blob::new(plaintext),
172        "Decrypted plaintext should be identical to the original plaintext. Invalid decryption"
173    );
174
175    // Because you used a multi_keyring on Encrypt, you can use either the
176    // `kms_keyring` or `raw_aes_keyring` individually to decrypt the data.
177
178    // 10. Demonstrate that you can successfully decrypt data using just the `kms_keyring`
179    // directly.
180    // (This is an example for demonstration; you do not need to do this in your own code.)
181
182    // 10a. Decrypt your encrypted data using the kms_keyring.
183    let decryption_response_kms_keyring = esdk_client
184        .decrypt()
185        .ciphertext(ciphertext.clone())
186        .keyring(kms_keyring)
187        // Provide the encryption context that was supplied to the encrypt method
188        .encryption_context(encryption_context.clone())
189        .send()
190        .await?;
191
192    let decrypted_plaintext_kms_keyring = decryption_response_kms_keyring
193        .plaintext
194        .expect("Unable to unwrap plaintext from decryption response");
195
196    // 10b. Demonstrate that the decrypted plaintext is identical to the original plaintext.
197    // (This is an example for demonstration; you do not need to do this in your own code.)
198    assert_eq!(
199        decrypted_plaintext_kms_keyring,
200        aws_smithy_types::Blob::new(plaintext),
201        "Decrypted plaintext should be identical to the original plaintext. Invalid decryption"
202    );
203
204    // 11. Demonstrate that you can also successfully decrypt data using the `raw_aes_keyring`
205    // directly.
206    // (This is an example for demonstration; you do not need to do this in your own code.)
207
208    // 11a. Decrypt your encrypted data using the raw_aes_keyring.
209    let decryption_response_raw_aes_keyring = esdk_client
210        .decrypt()
211        .ciphertext(ciphertext)
212        .keyring(raw_aes_keyring)
213        // Provide the encryption context that was supplied to the encrypt method
214        .encryption_context(encryption_context)
215        .send()
216        .await?;
217
218    let decrypted_plaintext_raw_aes_keyring = decryption_response_raw_aes_keyring
219        .plaintext
220        .expect("Unable to unwrap plaintext from decryption response");
221
222    // 11b. Demonstrate that the decrypted plaintext is identical to the original plaintext.
223    // (This is an example for demonstration; you do not need to do this in your own code.)
224    assert_eq!(
225        decrypted_plaintext_raw_aes_keyring,
226        aws_smithy_types::Blob::new(plaintext),
227        "Decrypted plaintext should be identical to the original plaintext. Invalid decryption"
228    );
229
230    println!("Multi Keyring Example Completed Successfully");
231
232    Ok(())
233}
Source§

impl Client

Source

pub fn create_aws_kms_discovery_keyring( &self, ) -> CreateAwsKmsDiscoveryKeyringFluentBuilder

Examples found in repository?
examples/keyring/aws_kms_discovery_keyring_example.rs (line 127)
47pub async fn encrypt_and_decrypt_with_keyring(
48    example_data: &str,
49    kms_key_id: &str,
50    aws_account_id: &str,
51) -> Result<(), crate::BoxError> {
52    // 1. Instantiate the encryption SDK client.
53    // This builds the default client with the RequireEncryptRequireDecrypt commitment policy,
54    // which enforces that this client only encrypts using committing algorithm suites and enforces
55    // that this client will only decrypt encrypted messages that were created with a committing
56    // algorithm suite.
57    let esdk_config = AwsEncryptionSdkConfig::builder().build()?;
58    let esdk_client = esdk_client::Client::from_conf(esdk_config)?;
59
60    // 2. Create a KMS client.
61    let sdk_config = aws_config::load_defaults(aws_config::BehaviorVersion::latest()).await;
62    let kms_client = aws_sdk_kms::Client::new(&sdk_config);
63
64    // 3. Create encryption context.
65    // Remember that your encryption context is NOT SECRET.
66    // For more information, see
67    // https://docs.aws.amazon.com/encryption-sdk/latest/developer-guide/concepts.html#encryption-context
68    let encryption_context = HashMap::from([
69        ("encryption".to_string(), "context".to_string()),
70        ("is not".to_string(), "secret".to_string()),
71        ("but adds".to_string(), "useful metadata".to_string()),
72        (
73            "that can help you".to_string(),
74            "be confident that".to_string(),
75        ),
76        (
77            "the data you are handling".to_string(),
78            "is what you think it is".to_string(),
79        ),
80    ]);
81
82    // 4. Create the keyring that determines how your data keys are protected.
83    //    Although this example highlights Discovery keyrings, Discovery keyrings cannot
84    //    be used to encrypt, so for encryption we create a KMS keyring without discovery mode.
85    let mpl_config = MaterialProvidersConfig::builder().build()?;
86    let mpl = mpl_client::Client::from_conf(mpl_config)?;
87
88    let encrypt_kms_keyring = mpl
89        .create_aws_kms_keyring()
90        .kms_key_id(kms_key_id)
91        .kms_client(kms_client.clone())
92        .send()
93        .await?;
94
95    // 5. Encrypt the data with the encryption_context
96    let plaintext = example_data.as_bytes();
97
98    let encryption_response = esdk_client
99        .encrypt()
100        .plaintext(plaintext)
101        .keyring(encrypt_kms_keyring)
102        .encryption_context(encryption_context.clone())
103        .send()
104        .await?;
105
106    let ciphertext = encryption_response
107        .ciphertext
108        .expect("Unable to unwrap ciphertext from encryption response");
109
110    // 6. Demonstrate that the ciphertext and plaintext are different.
111    // (This is an example for demonstration; you do not need to do this in your own code.)
112    assert_ne!(
113        ciphertext,
114        aws_smithy_types::Blob::new(plaintext),
115        "Ciphertext and plaintext data are the same. Invalid encryption"
116    );
117
118    // 7. Now create a Discovery keyring to use for decryption. We'll add a discovery filter
119    //    so that we limit the set of ciphertexts we are willing to decrypt to only ones
120    //    created by KMS keys in our account and partition.
121    let discovery_filter = DiscoveryFilter::builder()
122        .account_ids(vec![aws_account_id.to_string()])
123        .partition("aws".to_string())
124        .build()?;
125
126    let discovery_keyring = mpl
127        .create_aws_kms_discovery_keyring()
128        .kms_client(kms_client.clone())
129        .discovery_filter(discovery_filter)
130        .send()
131        .await?;
132
133    // 8. Decrypt your encrypted data using the discovery keyring.
134    //    On Decrypt, the header of the encrypted message (ciphertext) will be parsed.
135    //    The header contains the Encrypted Data Keys (EDKs), which, if the EDK
136    //    was encrypted by a KMS Keyring, includes the KMS Key ARN.
137    //    The Discovery Keyring filters these EDKs for
138    //    EDKs encrypted by Single Region OR Multi Region KMS Keys.
139    //    If a Discovery Filter is present, these KMS Keys must belong
140    //    to an AWS Account ID in the discovery filter's AccountIds and
141    //    must be from the discovery filter's partition.
142    //    Finally, KMS is called to decrypt each filtered EDK until an EDK is
143    //    successfully decrypted. The resulting data key is used to decrypt the
144    //    ciphertext's message.
145    //    If all calls to KMS fail, the decryption fails.
146    let decryption_response = esdk_client
147        .decrypt()
148        .ciphertext(ciphertext.clone())
149        .keyring(discovery_keyring)
150        // Provide the encryption context that was supplied to the encrypt method
151        .encryption_context(encryption_context.clone())
152        .send()
153        .await?;
154
155    let decrypted_plaintext = decryption_response
156        .plaintext
157        .expect("Unable to unwrap plaintext from decryption response");
158
159    // 9. Demonstrate that the decrypted plaintext is identical to the original plaintext.
160    // (This is an example for demonstration; you do not need to do this in your own code.)
161    assert_eq!(
162        decrypted_plaintext,
163        aws_smithy_types::Blob::new(plaintext),
164        "Decrypted plaintext should be identical to the original plaintext. Invalid decryption"
165    );
166
167    // 10. Demonstrate that if a different discovery keyring (Bob's) doesn't have the correct
168    //     AWS Account ID's, the decrypt will fail with an error message
169    //     Note that this assumes Account ID used here ('888888888888') is different than the one used
170    //     during encryption
171    let discovery_filter_bob = DiscoveryFilter::builder()
172        .account_ids(vec!["888888888888".to_string()])
173        .partition("aws".to_string())
174        .build()?;
175
176    let discovery_keyring_bob = mpl
177        .create_aws_kms_discovery_keyring()
178        .kms_client(kms_client)
179        .discovery_filter(discovery_filter_bob)
180        .send()
181        .await?;
182
183    // Decrypt the ciphertext using Bob's discovery keyring which doesn't contain the required
184    // Account ID's for the KMS keyring used for encryption.
185    // This should throw an AwsCryptographicMaterialProvidersError exception
186    let decryption_response_bob = esdk_client
187        .decrypt()
188        .ciphertext(ciphertext)
189        .keyring(discovery_keyring_bob)
190        // Provide the encryption context that was supplied to the encrypt method
191        .encryption_context(encryption_context)
192        .send()
193        .await;
194
195    match decryption_response_bob {
196        Ok(_) => panic!(
197            "Decrypt using discovery keyring with wrong AWS Account ID MUST \
198                            raise AwsCryptographicMaterialProvidersError"
199        ),
200        Err(AwsCryptographicMaterialProvidersError { error: _e }) => (),
201        _ => panic!("Unexpected error type"),
202    }
203
204    println!("KMS Discovery Keyring Example Completed Successfully");
205
206    Ok(())
207}
Source§

impl Client

Source

pub fn create_aws_kms_multi_keyring( &self, ) -> CreateAwsKmsMultiKeyringFluentBuilder

Examples found in repository?
examples/keyring/aws_kms_multi_keyring_example.rs (line 90)
51pub async fn encrypt_and_decrypt_with_keyring(
52    example_data: &str,
53    default_region_kms_key_id: &str,
54    second_region_kms_key_id: &str,
55    default_region: String,
56    second_region: String,
57) -> Result<(), crate::BoxError> {
58    // 1. Instantiate the encryption SDK client.
59    // This builds the default client with the RequireEncryptRequireDecrypt commitment policy,
60    // which enforces that this client only encrypts using committing algorithm suites and enforces
61    // that this client will only decrypt encrypted messages that were created with a committing
62    // algorithm suite.
63    let esdk_config = AwsEncryptionSdkConfig::builder().build()?;
64    let esdk_client = esdk_client::Client::from_conf(esdk_config)?;
65
66    // 2. Create encryption context.
67    // Remember that your encryption context is NOT SECRET.
68    // For more information, see
69    // https://docs.aws.amazon.com/encryption-sdk/latest/developer-guide/concepts.html#encryption-context
70    let encryption_context = HashMap::from([
71        ("encryption".to_string(), "context".to_string()),
72        ("is not".to_string(), "secret".to_string()),
73        ("but adds".to_string(), "useful metadata".to_string()),
74        (
75            "that can help you".to_string(),
76            "be confident that".to_string(),
77        ),
78        (
79            "the data you are handling".to_string(),
80            "is what you think it is".to_string(),
81        ),
82    ]);
83
84    // 3. Create an AwsKmsMultiKeyring that protects your data under two different KMS Keys.
85    // Either KMS Key individually is capable of decrypting data encrypted under this Multi Keyring.
86    let mpl_config = MaterialProvidersConfig::builder().build()?;
87    let mpl = mpl_client::Client::from_conf(mpl_config)?;
88
89    let kms_multi_keyring = mpl
90        .create_aws_kms_multi_keyring()
91        .generator(default_region_kms_key_id)
92        .kms_key_ids(vec![second_region_kms_key_id.to_string()])
93        .send()
94        .await?;
95
96    // 4. Encrypt the data with the encryption_context
97    let plaintext = example_data.as_bytes();
98
99    let encryption_response = esdk_client
100        .encrypt()
101        .plaintext(plaintext)
102        .keyring(kms_multi_keyring.clone())
103        .encryption_context(encryption_context.clone())
104        .send()
105        .await?;
106
107    let ciphertext = encryption_response
108        .ciphertext
109        .expect("Unable to unwrap ciphertext from encryption response");
110
111    // 5. Demonstrate that the ciphertext and plaintext are different.
112    // (This is an example for demonstration; you do not need to do this in your own code.)
113    assert_ne!(
114        ciphertext,
115        aws_smithy_types::Blob::new(plaintext),
116        "Ciphertext and plaintext data are the same. Invalid encryption"
117    );
118
119    // 6a. Decrypt your encrypted data using the same multi_keyring you used on encrypt.
120    let decryption_response_multi_keyring = esdk_client
121        .decrypt()
122        .ciphertext(ciphertext.clone())
123        .keyring(kms_multi_keyring)
124        // Provide the encryption context that was supplied to the encrypt method
125        .encryption_context(encryption_context.clone())
126        .send()
127        .await?;
128
129    let decrypted_plaintext_multi_keyring = decryption_response_multi_keyring
130        .plaintext
131        .expect("Unable to unwrap plaintext from decryption response");
132
133    // 6b. Demonstrate that the decrypted plaintext is identical to the original plaintext.
134    // (This is an example for demonstration; you do not need to do this in your own code.)
135    assert_eq!(
136        decrypted_plaintext_multi_keyring,
137        aws_smithy_types::Blob::new(plaintext),
138        "Decrypted plaintext should be identical to the original plaintext. Invalid decryption"
139    );
140
141    // Because you used a multi_keyring on Encrypt, you can use either of the two
142    // kms keyrings individually to decrypt the data.
143
144    // 7. Demonstrate that you can successfully decrypt data using a KMS keyring with just the
145    // `default_region_kms_key_id` directly.
146    // (This is an example for demonstration; you do not need to do this in your own code.)
147
148    // 7a. Create a client for KMS for the default region.
149    let sdk_config = aws_config::load_defaults(aws_config::BehaviorVersion::latest()).await;
150    let default_region_kms_config = aws_sdk_kms::config::Builder::from(&sdk_config)
151        .region(Region::new(default_region))
152        .build();
153    let default_region_kms_client = aws_sdk_kms::Client::from_conf(default_region_kms_config);
154
155    // 7b. Create KMS keyring
156    let default_region_kms_keyring = mpl
157        .create_aws_kms_keyring()
158        .kms_key_id(default_region_kms_key_id)
159        .kms_client(default_region_kms_client)
160        .send()
161        .await?;
162
163    // 7c. Decrypt your encrypted data using the default_region_kms_keyring.
164    let decryption_response_default_region_kms_keyring = esdk_client
165        .decrypt()
166        .ciphertext(ciphertext.clone())
167        .keyring(default_region_kms_keyring)
168        // Provide the encryption context that was supplied to the encrypt method
169        .encryption_context(encryption_context.clone())
170        .send()
171        .await?;
172
173    let decrypted_plaintext_default_region_kms_keyring =
174        decryption_response_default_region_kms_keyring
175            .plaintext
176            .expect("Unable to unwrap plaintext from decryption response");
177
178    // 7d. Demonstrate that the decrypted plaintext is identical to the original plaintext.
179    // (This is an example for demonstration; you do not need to do this in your own code.)
180    assert_eq!(
181        decrypted_plaintext_default_region_kms_keyring,
182        aws_smithy_types::Blob::new(plaintext),
183        "Decrypted plaintext should be identical to the original plaintext. Invalid decryption"
184    );
185
186    // 8. Demonstrate that you can also successfully decrypt data using a KMS keyring with just the
187    // `second_region_kms_key_id` directly.
188    // (This is an example for demonstration; you do not need to do this in your own code.)
189
190    // 8a. Create a client for KMS for the second region.
191    let second_region_kms_config = aws_sdk_kms::config::Builder::from(&sdk_config)
192        .region(Region::new(second_region))
193        .build();
194    let second_region_kms_client = aws_sdk_kms::Client::from_conf(second_region_kms_config);
195
196    // 8b. Create KMS keyring
197    let second_region_kms_keyring = mpl
198        .create_aws_kms_keyring()
199        .kms_key_id(second_region_kms_key_id)
200        .kms_client(second_region_kms_client)
201        .send()
202        .await?;
203
204    // 8c. Decrypt your encrypted data using the second_region_kms_keyring.
205    let decryption_response_second_region_kms_keyring = esdk_client
206        .decrypt()
207        .ciphertext(ciphertext)
208        .keyring(second_region_kms_keyring)
209        // Provide the encryption context that was supplied to the encrypt method
210        .encryption_context(encryption_context)
211        .send()
212        .await?;
213
214    let decrypted_plaintext_second_region_kms_keyring =
215        decryption_response_second_region_kms_keyring
216            .plaintext
217            .expect("Unable to unwrap plaintext from decryption response");
218
219    // 8d. Demonstrate that the decrypted plaintext is identical to the original plaintext.
220    // (This is an example for demonstration; you do not need to do this in your own code.)
221    assert_eq!(
222        decrypted_plaintext_second_region_kms_keyring,
223        aws_smithy_types::Blob::new(plaintext),
224        "Decrypted plaintext should be identical to the original plaintext. Invalid decryption"
225    );
226
227    println!("KMS Multi Keyring Example Completed Successfully");
228
229    Ok(())
230}
Source§

impl Client

Source

pub fn create_aws_kms_discovery_multi_keyring( &self, ) -> CreateAwsKmsDiscoveryMultiKeyringFluentBuilder

Examples found in repository?
examples/keyring/aws_kms_discovery_multi_keyring_example.rs (line 129)
44pub async fn encrypt_and_decrypt_with_keyring(
45    example_data: &str,
46    kms_key_id: &str,
47    aws_account_id: &str,
48    aws_regions: Vec<String>,
49) -> Result<(), crate::BoxError> {
50    // 1. Instantiate the encryption SDK client.
51    // This builds the default client with the RequireEncryptRequireDecrypt commitment policy,
52    // which enforces that this client only encrypts using committing algorithm suites and enforces
53    // that this client will only decrypt encrypted messages that were created with a committing
54    // algorithm suite.
55    let esdk_config = AwsEncryptionSdkConfig::builder().build()?;
56    let esdk_client = esdk_client::Client::from_conf(esdk_config)?;
57
58    // 2. Create a KMS client.
59    let sdk_config = aws_config::load_defaults(aws_config::BehaviorVersion::latest()).await;
60    let kms_client = aws_sdk_kms::Client::new(&sdk_config);
61
62    // 3. Create encryption context.
63    // Remember that your encryption context is NOT SECRET.
64    // For more information, see
65    // https://docs.aws.amazon.com/encryption-sdk/latest/developer-guide/concepts.html#encryption-context
66    let encryption_context = HashMap::from([
67        ("encryption".to_string(), "context".to_string()),
68        ("is not".to_string(), "secret".to_string()),
69        ("but adds".to_string(), "useful metadata".to_string()),
70        (
71            "that can help you".to_string(),
72            "be confident that".to_string(),
73        ),
74        (
75            "the data you are handling".to_string(),
76            "is what you think it is".to_string(),
77        ),
78    ]);
79
80    // 4. Create the keyring that determines how your data keys are protected.
81    //    Although this example highlights Discovery keyrings, Discovery keyrings cannot
82    //    be used to encrypt, so for encryption we create a KMS keyring without discovery mode.
83    let mpl_config = MaterialProvidersConfig::builder().build()?;
84    let mpl = mpl_client::Client::from_conf(mpl_config)?;
85
86    let encrypt_kms_keyring = mpl
87        .create_aws_kms_keyring()
88        .kms_key_id(kms_key_id)
89        .kms_client(kms_client.clone())
90        .send()
91        .await?;
92
93    // 5. Encrypt the data with the encryption_context
94    let plaintext = example_data.as_bytes();
95
96    let encryption_response = esdk_client
97        .encrypt()
98        .plaintext(plaintext)
99        .keyring(encrypt_kms_keyring)
100        .encryption_context(encryption_context.clone())
101        .send()
102        .await?;
103
104    let ciphertext = encryption_response
105        .ciphertext
106        .expect("Unable to unwrap ciphertext from encryption response");
107
108    // 6. Demonstrate that the ciphertext and plaintext are different.
109    // (This is an example for demonstration; you do not need to do this in your own code.)
110    assert_ne!(
111        ciphertext,
112        aws_smithy_types::Blob::new(plaintext),
113        "Ciphertext and plaintext data are the same. Invalid encryption"
114    );
115
116    // 7. Now create a Discovery Multi keyring to use for decryption. We'll add a discovery filter
117    //    so that we limit the set of ciphertexts we are willing to decrypt to only ones
118    //    created by KMS keys in our account and partition.
119    let discovery_filter = DiscoveryFilter::builder()
120        .account_ids(vec![aws_account_id.to_string()])
121        .partition("aws".to_string())
122        .build()?;
123
124    // This is a Multi Keyring composed of Discovery Keyrings.
125    // There is a keyring for every region in `regions`.
126    // All the keyrings have the same Discovery Filter.
127    // Each keyring has its own KMS Client, which is created for the keyring's region.
128    let discovery_multi_keyring = mpl
129        .create_aws_kms_discovery_multi_keyring()
130        .regions(aws_regions)
131        .discovery_filter(discovery_filter)
132        .send()
133        .await?;
134
135    // 8. On Decrypt, the header of the encrypted message (ciphertext) will be parsed.
136    // The header contains the Encrypted Data Keys (EDKs), which, if the EDK
137    // was encrypted by a KMS Keyring, includes the KMS Key ARN.
138    // For each member of the Multi Keyring, every EDK will try to be decrypted until a decryption
139    // is successful.
140    // Since every member of the Multi Keyring is a Discovery Keyring:
141    //   Each Keyring will filter the EDKs by the Discovery Filter
142    //       For the filtered EDKs, the keyring will try to decrypt it with the keyring's client.
143    // All of this is done serially, until a success occurs or all keyrings have
144    // failed all (filtered) EDKs.
145    // KMS Discovery Keyrings will attempt to decrypt Multi Region Keys (MRKs) and regular KMS Keys.
146    let decryption_response = esdk_client
147        .decrypt()
148        .ciphertext(ciphertext)
149        .keyring(discovery_multi_keyring)
150        // Provide the encryption context that was supplied to the encrypt method
151        .encryption_context(encryption_context)
152        .send()
153        .await?;
154
155    let decrypted_plaintext = decryption_response
156        .plaintext
157        .expect("Unable to unwrap plaintext from decryption response");
158
159    // 9. Demonstrate that the decrypted plaintext is identical to the original plaintext.
160    // (This is an example for demonstration; you do not need to do this in your own code.)
161    assert_eq!(
162        decrypted_plaintext,
163        aws_smithy_types::Blob::new(plaintext),
164        "Decrypted plaintext should be identical to the original plaintext. Invalid decryption"
165    );
166
167    println!("KMS Discovery Multi Keyring Example Completed Successfully");
168
169    Ok(())
170}
Source§

impl Client

Source

pub fn create_aws_kms_mrk_keyring(&self) -> CreateAwsKmsMrkKeyringFluentBuilder

Examples found in repository?
examples/keyring/aws_kms_mrk_keyring_example.rs (line 81)
35pub async fn encrypt_and_decrypt_with_keyring(
36    example_data: &str,
37    mrk_key_id_encrypt: &str,
38    mrk_replica_key_id_decrypt: &str,
39    mrk_encrypt_region: String,
40    mrk_replica_decrypt_region: String,
41) -> Result<(), crate::BoxError> {
42    // 1. Instantiate the encryption SDK client.
43    // This builds the default client with the RequireEncryptRequireDecrypt commitment policy,
44    // which enforces that this client only encrypts using committing algorithm suites and enforces
45    // that this client will only decrypt encrypted messages that were created with a committing
46    // algorithm suite.
47    let esdk_config = AwsEncryptionSdkConfig::builder().build()?;
48    let esdk_client = esdk_client::Client::from_conf(esdk_config)?;
49
50    // 2. Create encryption context.
51    // Remember that your encryption context is NOT SECRET.
52    // For more information, see
53    // https://docs.aws.amazon.com/encryption-sdk/latest/developer-guide/concepts.html#encryption-context
54    let encryption_context = HashMap::from([
55        ("encryption".to_string(), "context".to_string()),
56        ("is not".to_string(), "secret".to_string()),
57        ("but adds".to_string(), "useful metadata".to_string()),
58        (
59            "that can help you".to_string(),
60            "be confident that".to_string(),
61        ),
62        (
63            "the data you are handling".to_string(),
64            "is what you think it is".to_string(),
65        ),
66    ]);
67
68    // 3. Create a keyring that will encrypt your data, using a KMS MRK in the first region.
69    let mpl_config = MaterialProvidersConfig::builder().build()?;
70    let mpl = mpl_client::Client::from_conf(mpl_config)?;
71
72    // Create a KMS client in the first region
73    let sdk_config = aws_config::load_defaults(aws_config::BehaviorVersion::latest()).await;
74    let encrypt_kms_config = aws_sdk_kms::config::Builder::from(&sdk_config)
75        .region(Region::new(mrk_encrypt_region))
76        .build();
77    let encrypt_kms_client = aws_sdk_kms::Client::from_conf(encrypt_kms_config);
78
79    // Create the keyring that determines how your data keys are protected.
80    let encrypt_kms_keyring = mpl
81        .create_aws_kms_mrk_keyring()
82        .kms_key_id(mrk_key_id_encrypt)
83        .kms_client(encrypt_kms_client)
84        .send()
85        .await?;
86
87    // 4. Encrypt the data with the encryption_context using the encrypt_keyring.
88    let plaintext = example_data.as_bytes();
89
90    let encryption_response = esdk_client
91        .encrypt()
92        .plaintext(plaintext)
93        .keyring(encrypt_kms_keyring)
94        .encryption_context(encryption_context.clone())
95        .send()
96        .await?;
97
98    let ciphertext = encryption_response
99        .ciphertext
100        .expect("Unable to unwrap ciphertext from encryption response");
101
102    // 5. Demonstrate that the ciphertext and plaintext are different.
103    // (This is an example for demonstration; you do not need to do this in your own code.)
104    assert_ne!(
105        ciphertext,
106        aws_smithy_types::Blob::new(plaintext),
107        "Ciphertext and plaintext data are the same. Invalid encryption"
108    );
109
110    // 6. Create a keyring that will decrypt your data, using the same KMS MRK replicated
111    // to the second region. This example assumes you have already replicated your key
112
113    // Create a KMS Client in the second region.
114    let decrypt_kms_config = aws_sdk_kms::config::Builder::from(&sdk_config)
115        .region(Region::new(mrk_replica_decrypt_region))
116        .build();
117    let decrypt_kms_client = aws_sdk_kms::Client::from_conf(decrypt_kms_config);
118
119    let decrypt_kms_keyring = mpl
120        .create_aws_kms_mrk_keyring()
121        .kms_key_id(mrk_replica_key_id_decrypt)
122        .kms_client(decrypt_kms_client)
123        .send()
124        .await?;
125
126    // 7. Decrypt your encrypted data using the decrypt keyring.
127    let decryption_response = esdk_client
128        .decrypt()
129        .ciphertext(ciphertext)
130        .keyring(decrypt_kms_keyring)
131        // Provide the encryption context that was supplied to the encrypt method
132        .encryption_context(encryption_context)
133        .send()
134        .await?;
135
136    let decrypted_plaintext = decryption_response
137        .plaintext
138        .expect("Unable to unwrap plaintext from decryption response");
139
140    // 8. Demonstrate that the decrypted plaintext is identical to the original plaintext.
141    // (This is an example for demonstration; you do not need to do this in your own code.)
142    assert_eq!(
143        decrypted_plaintext,
144        aws_smithy_types::Blob::new(plaintext),
145        "Decrypted plaintext should be identical to the original plaintext. Invalid decryption"
146    );
147
148    println!("KMS MRK Keyring Example Completed Successfully");
149
150    Ok(())
151}
More examples
Hide additional examples
examples/keyring/aws_kms_mrk_discovery_keyring_example.rs (line 97)
49pub async fn encrypt_and_decrypt_with_keyring(
50    example_data: &str,
51    mrk_key_id_encrypt: &str,
52    aws_account_id: &str,
53    mrk_encrypt_region: String,
54    mrk_replica_decrypt_region: String,
55) -> Result<(), crate::BoxError> {
56    // 1. Instantiate the encryption SDK client.
57    // This builds the default client with the RequireEncryptRequireDecrypt commitment policy,
58    // which enforces that this client only encrypts using committing algorithm suites and enforces
59    // that this client will only decrypt encrypted messages that were created with a committing
60    // algorithm suite.
61    let esdk_config = AwsEncryptionSdkConfig::builder().build()?;
62    let esdk_client = esdk_client::Client::from_conf(esdk_config)?;
63
64    // 2. Create encryption context.
65    // Remember that your encryption context is NOT SECRET.
66    // For more information, see
67    // https://docs.aws.amazon.com/encryption-sdk/latest/developer-guide/concepts.html#encryption-context
68    let encryption_context = HashMap::from([
69        ("encryption".to_string(), "context".to_string()),
70        ("is not".to_string(), "secret".to_string()),
71        ("but adds".to_string(), "useful metadata".to_string()),
72        (
73            "that can help you".to_string(),
74            "be confident that".to_string(),
75        ),
76        (
77            "the data you are handling".to_string(),
78            "is what you think it is".to_string(),
79        ),
80    ]);
81
82    // 3. Create the keyring that determines how your data keys are protected.
83    // Although this example highlights Discovery keyrings, Discovery keyrings cannot
84    // be used to encrypt, so for encryption we create an MRK keyring without discovery mode.
85    let mpl_config = MaterialProvidersConfig::builder().build()?;
86    let mpl = mpl_client::Client::from_conf(mpl_config)?;
87
88    // Create a KMS client in the first region
89    let sdk_config = aws_config::load_defaults(aws_config::BehaviorVersion::latest()).await;
90    let encrypt_kms_config = aws_sdk_kms::config::Builder::from(&sdk_config)
91        .region(Region::new(mrk_encrypt_region))
92        .build();
93    let encrypt_kms_client = aws_sdk_kms::Client::from_conf(encrypt_kms_config);
94
95    // Create a keyring that will encrypt your data, using a KMS MRK in the first region.
96    let encrypt_kms_keyring = mpl
97        .create_aws_kms_mrk_keyring()
98        .kms_key_id(mrk_key_id_encrypt)
99        .kms_client(encrypt_kms_client)
100        .send()
101        .await?;
102
103    // 4. Encrypt the data with the encryption_context using the encrypt_keyring.
104    let plaintext = example_data.as_bytes();
105
106    let encryption_response = esdk_client
107        .encrypt()
108        .plaintext(plaintext)
109        .keyring(encrypt_kms_keyring)
110        .encryption_context(encryption_context.clone())
111        .send()
112        .await?;
113
114    let ciphertext = encryption_response
115        .ciphertext
116        .expect("Unable to unwrap ciphertext from encryption response");
117
118    // 5. Demonstrate that the ciphertext and plaintext are different.
119    // (This is an example for demonstration; you do not need to do this in your own code.)
120    assert_ne!(
121        ciphertext,
122        aws_smithy_types::Blob::new(plaintext),
123        "Ciphertext and plaintext data are the same. Invalid encryption"
124    );
125
126    // 6. Now create a Discovery keyring to use for decryption.
127    // In order to illustrate the MRK behavior of this keyring, we configure
128    // the keyring to use the second KMS region where the MRK (mrk_key_id_encrypt) is replicated to.
129    // This example assumes you have already replicated your key, but since we
130    // are using a discovery keyring, we don't need to provide the mrk replica key id
131
132    // Create a KMS Client in the second region.
133    let decrypt_kms_config = aws_sdk_kms::config::Builder::from(&sdk_config)
134        .region(Region::new(mrk_replica_decrypt_region.clone()))
135        .build();
136    let decrypt_kms_client = aws_sdk_kms::Client::from_conf(decrypt_kms_config);
137
138    let discovery_filter = DiscoveryFilter::builder()
139        .account_ids(vec![aws_account_id.to_string()])
140        .partition("aws".to_string())
141        .build()?;
142
143    let discovery_keyring = mpl
144        .create_aws_kms_mrk_discovery_keyring()
145        .kms_client(decrypt_kms_client)
146        .region(mrk_replica_decrypt_region)
147        .discovery_filter(discovery_filter)
148        .send()
149        .await?;
150
151    // 7. Decrypt your encrypted data using the discovery keyring.
152    let decryption_response = esdk_client
153        .decrypt()
154        .ciphertext(ciphertext)
155        .keyring(discovery_keyring)
156        // Provide the encryption context that was supplied to the encrypt method
157        .encryption_context(encryption_context)
158        .send()
159        .await?;
160
161    let decrypted_plaintext = decryption_response
162        .plaintext
163        .expect("Unable to unwrap plaintext from decryption response");
164
165    // 8. Demonstrate that the decrypted plaintext is identical to the original plaintext.
166    // (This is an example for demonstration; you do not need to do this in your own code.)
167    assert_eq!(
168        decrypted_plaintext,
169        aws_smithy_types::Blob::new(plaintext),
170        "Decrypted plaintext should be identical to the original plaintext. Invalid decryption"
171    );
172
173    println!("KMS MRK Discovery Keyring Example Completed Successfully");
174
175    Ok(())
176}
examples/keyring/aws_kms_mrk_discovery_multi_keyring_example.rs (line 99)
51pub async fn encrypt_and_decrypt_with_keyring(
52    example_data: &str,
53    mrk_key_id_encrypt: &str,
54    mrk_encrypt_region: String,
55    aws_account_id: &str,
56    aws_regions: Vec<String>,
57) -> Result<(), crate::BoxError> {
58    // 1. Instantiate the encryption SDK client.
59    // This builds the default client with the RequireEncryptRequireDecrypt commitment policy,
60    // which enforces that this client only encrypts using committing algorithm suites and enforces
61    // that this client will only decrypt encrypted messages that were created with a committing
62    // algorithm suite.
63    let esdk_config = AwsEncryptionSdkConfig::builder().build()?;
64    let esdk_client = esdk_client::Client::from_conf(esdk_config)?;
65
66    // 2. Create encryption context.
67    // Remember that your encryption context is NOT SECRET.
68    // For more information, see
69    // https://docs.aws.amazon.com/encryption-sdk/latest/developer-guide/concepts.html#encryption-context
70    let encryption_context = HashMap::from([
71        ("encryption".to_string(), "context".to_string()),
72        ("is not".to_string(), "secret".to_string()),
73        ("but adds".to_string(), "useful metadata".to_string()),
74        (
75            "that can help you".to_string(),
76            "be confident that".to_string(),
77        ),
78        (
79            "the data you are handling".to_string(),
80            "is what you think it is".to_string(),
81        ),
82    ]);
83
84    // 3. Create the keyring that determines how your data keys are protected.
85    // Although this example highlights Discovery keyrings, Discovery keyrings cannot
86    // be used to encrypt, so for encryption we create an MRK keyring without discovery mode.
87    let mpl_config = MaterialProvidersConfig::builder().build()?;
88    let mpl = mpl_client::Client::from_conf(mpl_config)?;
89
90    // Create a KMS client in the first region
91    let sdk_config = aws_config::load_defaults(aws_config::BehaviorVersion::latest()).await;
92    let encrypt_kms_config = aws_sdk_kms::config::Builder::from(&sdk_config)
93        .region(Region::new(mrk_encrypt_region))
94        .build();
95    let encrypt_kms_client = aws_sdk_kms::Client::from_conf(encrypt_kms_config);
96
97    // Create a keyring that will encrypt your data, using a KMS MRK in the first region.
98    let encrypt_kms_keyring = mpl
99        .create_aws_kms_mrk_keyring()
100        .kms_key_id(mrk_key_id_encrypt)
101        .kms_client(encrypt_kms_client)
102        .send()
103        .await?;
104
105    // 4. Encrypt the data with the encryption_context using the encrypt_keyring.
106    let plaintext = example_data.as_bytes();
107
108    let encryption_response = esdk_client
109        .encrypt()
110        .plaintext(plaintext)
111        .keyring(encrypt_kms_keyring)
112        .encryption_context(encryption_context.clone())
113        .send()
114        .await?;
115
116    let ciphertext = encryption_response
117        .ciphertext
118        .expect("Unable to unwrap ciphertext from encryption response");
119
120    // 5. Demonstrate that the ciphertext and plaintext are different.
121    // (This is an example for demonstration; you do not need to do this in your own code.)
122    assert_ne!(
123        ciphertext,
124        aws_smithy_types::Blob::new(plaintext),
125        "Ciphertext and plaintext data are the same. Invalid encryption"
126    );
127
128    // 6. Now create a MRK Discovery Multi Keyring to use for decryption.
129    // We'll add a discovery filter to limit the set of encrypted data keys
130    // we are willing to decrypt to only ones created by KMS keys in select
131    // accounts and the partition `aws`.
132    // MRK Discovery keyrings also filter encrypted data keys by the region
133    // the keyring is created with.
134    let discovery_filter = DiscoveryFilter::builder()
135        .account_ids(vec![aws_account_id.to_string()])
136        .partition("aws".to_string())
137        .build()?;
138
139    // This is a Multi Keyring composed of Discovery Keyrings.
140    // There is a keyring for every region in `regions`.
141    // All the keyrings have the same Discovery Filter.
142    // Each keyring has its own KMS Client, which is created for the keyring's region.
143    let discovery_multi_keyring = mpl
144        .create_aws_kms_mrk_discovery_multi_keyring()
145        .regions(aws_regions)
146        .discovery_filter(discovery_filter)
147        .send()
148        .await?;
149
150    // 7. Decrypt your encrypted data using the discovery multi keyring.
151    // On Decrypt, the header of the encrypted message (ciphertext) will be parsed.
152    // The header contains the Encrypted Data Keys (EDKs), which, if the EDK
153    // was encrypted by a KMS Keyring, includes the KMS Key ARN.
154    // For each member of the Multi Keyring, every EDK will try to be decrypted until a decryption
155    // is successful.
156    // Since every member of the Multi Keyring is a Discovery Keyring:
157    //   Each Keyring will filter the EDKs by the Discovery Filter and the Keyring's region.
158    //      For each filtered EDK, the keyring will attempt decryption with the keyring's client.
159    // All of this is done serially, until a success occurs or all keyrings have failed
160    // all (filtered) EDKs. KMS MRK Discovery Keyrings will attempt to decrypt
161    // Multi Region Keys (MRKs) and regular KMS Keys.
162    let decryption_response = esdk_client
163        .decrypt()
164        .ciphertext(ciphertext)
165        .keyring(discovery_multi_keyring)
166        // Provide the encryption context that was supplied to the encrypt method
167        .encryption_context(encryption_context)
168        .send()
169        .await?;
170
171    let decrypted_plaintext = decryption_response
172        .plaintext
173        .expect("Unable to unwrap plaintext from decryption response");
174
175    // 8. Demonstrate that the decrypted plaintext is identical to the original plaintext.
176    // (This is an example for demonstration; you do not need to do this in your own code.)
177    assert_eq!(
178        decrypted_plaintext,
179        aws_smithy_types::Blob::new(plaintext),
180        "Decrypted plaintext should be identical to the original plaintext. Invalid decryption"
181    );
182
183    println!("KMS MRK Discovery Multi Keyring Example Completed Successfully");
184
185    Ok(())
186}
examples/keyring/aws_kms_mrk_multi_keyring_example.rs (line 148)
41pub async fn encrypt_and_decrypt_with_keyring(
42    example_data: &str,
43    mrk_key_id: &str,
44    kms_key_id: &str,
45    mrk_replica_key_id: &str,
46    mrk_replica_decrypt_region: String,
47) -> Result<(), crate::BoxError> {
48    // 1. Instantiate the encryption SDK client.
49    // This builds the default client with the RequireEncryptRequireDecrypt commitment policy,
50    // which enforces that this client only encrypts using committing algorithm suites and enforces
51    // that this client will only decrypt encrypted messages that were created with a committing
52    // algorithm suite.
53    let esdk_config = AwsEncryptionSdkConfig::builder().build()?;
54    let esdk_client = esdk_client::Client::from_conf(esdk_config)?;
55
56    // 2. Create encryption context.
57    // Remember that your encryption context is NOT SECRET.
58    // For more information, see
59    // https://docs.aws.amazon.com/encryption-sdk/latest/developer-guide/concepts.html#encryption-context
60    let encryption_context = HashMap::from([
61        ("encryption".to_string(), "context".to_string()),
62        ("is not".to_string(), "secret".to_string()),
63        ("but adds".to_string(), "useful metadata".to_string()),
64        (
65            "that can help you".to_string(),
66            "be confident that".to_string(),
67        ),
68        (
69            "the data you are handling".to_string(),
70            "is what you think it is".to_string(),
71        ),
72    ]);
73
74    // 3. Create an AwsKmsMrkMultiKeyring that protects your data under two different KMS Keys.
75    // The Keys can either be regular KMS keys or MRKs.
76    // Either KMS Key individually is capable of decrypting data encrypted under this keyring.
77    let mpl_config = MaterialProvidersConfig::builder().build()?;
78    let mpl = mpl_client::Client::from_conf(mpl_config)?;
79
80    let kms_mrk_multi_keyring = mpl
81        .create_aws_kms_mrk_multi_keyring()
82        .generator(mrk_key_id)
83        .kms_key_ids(vec![kms_key_id.to_string()])
84        .send()
85        .await?;
86
87    // 4. Encrypt the data with the encryption_context using the kms_mrk_multi_keyring.
88    let plaintext = example_data.as_bytes();
89
90    let encryption_response = esdk_client
91        .encrypt()
92        .plaintext(plaintext)
93        .keyring(kms_mrk_multi_keyring.clone())
94        .encryption_context(encryption_context.clone())
95        .send()
96        .await?;
97
98    let ciphertext = encryption_response
99        .ciphertext
100        .expect("Unable to unwrap ciphertext from encryption response");
101
102    // 5. Demonstrate that the ciphertext and plaintext are different.
103    // (This is an example for demonstration; you do not need to do this in your own code.)
104    assert_ne!(
105        ciphertext,
106        aws_smithy_types::Blob::new(plaintext),
107        "Ciphertext and plaintext data are the same. Invalid encryption"
108    );
109
110    // 6. Decrypt your encrypted data using the same AwsKmsMrkMultiKeyring you used on encrypt.
111    // It will decrypt the data using the generator key (in this case, the MRK), since that is
112    // the first available KMS key on the keyring that is capable of decrypting the data.
113    let decryption_response = esdk_client
114        .decrypt()
115        .ciphertext(ciphertext.clone())
116        .keyring(kms_mrk_multi_keyring)
117        // Provide the encryption context that was supplied to the encrypt method
118        .encryption_context(encryption_context.clone())
119        .send()
120        .await?;
121
122    let decrypted_plaintext = decryption_response
123        .plaintext
124        .expect("Unable to unwrap plaintext from decryption response");
125
126    // 7. Demonstrate that the decrypted plaintext is identical to the original plaintext.
127    // (This is an example for demonstration; you do not need to do this in your own code.)
128    assert_eq!(
129        decrypted_plaintext,
130        aws_smithy_types::Blob::new(plaintext),
131        "Decrypted plaintext should be identical to the original plaintext. Invalid decryption"
132    );
133
134    // Demonstrate that a single AwsKmsMrkKeyring configured with a replica of the MRK from the
135    // multi-keyring used to encrypt the data is also capable of decrypting the data.
136    // (This is an example for demonstration; you do not need to do this in your own code.)
137
138    // 8. Create a single AwsKmsMrkKeyring with the replica KMS MRK from the second region.
139
140    // Create a client for KMS in the second region which is the region for mrk_replica_key_id.
141    let sdk_config = aws_config::load_defaults(aws_config::BehaviorVersion::latest()).await;
142    let second_region_kms_config = aws_sdk_kms::config::Builder::from(&sdk_config)
143        .region(Region::new(mrk_replica_decrypt_region))
144        .build();
145    let second_region_kms_client = aws_sdk_kms::Client::from_conf(second_region_kms_config);
146
147    let second_region_mrk_keyring = mpl
148        .create_aws_kms_mrk_keyring()
149        .kms_key_id(mrk_replica_key_id)
150        .kms_client(second_region_kms_client)
151        .send()
152        .await?;
153
154    // 9. Decrypt your encrypted data using the second region AwsKmsMrkKeyring
155    let second_region_decryption_response = esdk_client
156        .decrypt()
157        .ciphertext(ciphertext)
158        .keyring(second_region_mrk_keyring)
159        // Provide the encryption context that was supplied to the encrypt method
160        .encryption_context(encryption_context)
161        .send()
162        .await?;
163
164    let second_region_decrypted_plaintext = second_region_decryption_response
165        .plaintext
166        .expect("Unable to unwrap plaintext from decryption response");
167
168    // 10. Demonstrate that the decrypted plaintext is identical to the original plaintext.
169    // (This is an example for demonstration; you do not need to do this in your own code.)
170    assert_eq!(
171        second_region_decrypted_plaintext,
172        aws_smithy_types::Blob::new(plaintext),
173        "Decrypted plaintext should be identical to the original plaintext. Invalid decryption"
174    );
175
176    // Not shown in this example: A KMS Keyring created with `kms_key_id` could also
177    // decrypt this message.
178
179    println!("KMS MRK Multi Keyring Example Completed Successfully");
180
181    Ok(())
182}
Source§

impl Client

Source

pub fn create_aws_kms_mrk_multi_keyring( &self, ) -> CreateAwsKmsMrkMultiKeyringFluentBuilder

Examples found in repository?
examples/keyring/aws_kms_mrk_multi_keyring_example.rs (line 81)
41pub async fn encrypt_and_decrypt_with_keyring(
42    example_data: &str,
43    mrk_key_id: &str,
44    kms_key_id: &str,
45    mrk_replica_key_id: &str,
46    mrk_replica_decrypt_region: String,
47) -> Result<(), crate::BoxError> {
48    // 1. Instantiate the encryption SDK client.
49    // This builds the default client with the RequireEncryptRequireDecrypt commitment policy,
50    // which enforces that this client only encrypts using committing algorithm suites and enforces
51    // that this client will only decrypt encrypted messages that were created with a committing
52    // algorithm suite.
53    let esdk_config = AwsEncryptionSdkConfig::builder().build()?;
54    let esdk_client = esdk_client::Client::from_conf(esdk_config)?;
55
56    // 2. Create encryption context.
57    // Remember that your encryption context is NOT SECRET.
58    // For more information, see
59    // https://docs.aws.amazon.com/encryption-sdk/latest/developer-guide/concepts.html#encryption-context
60    let encryption_context = HashMap::from([
61        ("encryption".to_string(), "context".to_string()),
62        ("is not".to_string(), "secret".to_string()),
63        ("but adds".to_string(), "useful metadata".to_string()),
64        (
65            "that can help you".to_string(),
66            "be confident that".to_string(),
67        ),
68        (
69            "the data you are handling".to_string(),
70            "is what you think it is".to_string(),
71        ),
72    ]);
73
74    // 3. Create an AwsKmsMrkMultiKeyring that protects your data under two different KMS Keys.
75    // The Keys can either be regular KMS keys or MRKs.
76    // Either KMS Key individually is capable of decrypting data encrypted under this keyring.
77    let mpl_config = MaterialProvidersConfig::builder().build()?;
78    let mpl = mpl_client::Client::from_conf(mpl_config)?;
79
80    let kms_mrk_multi_keyring = mpl
81        .create_aws_kms_mrk_multi_keyring()
82        .generator(mrk_key_id)
83        .kms_key_ids(vec![kms_key_id.to_string()])
84        .send()
85        .await?;
86
87    // 4. Encrypt the data with the encryption_context using the kms_mrk_multi_keyring.
88    let plaintext = example_data.as_bytes();
89
90    let encryption_response = esdk_client
91        .encrypt()
92        .plaintext(plaintext)
93        .keyring(kms_mrk_multi_keyring.clone())
94        .encryption_context(encryption_context.clone())
95        .send()
96        .await?;
97
98    let ciphertext = encryption_response
99        .ciphertext
100        .expect("Unable to unwrap ciphertext from encryption response");
101
102    // 5. Demonstrate that the ciphertext and plaintext are different.
103    // (This is an example for demonstration; you do not need to do this in your own code.)
104    assert_ne!(
105        ciphertext,
106        aws_smithy_types::Blob::new(plaintext),
107        "Ciphertext and plaintext data are the same. Invalid encryption"
108    );
109
110    // 6. Decrypt your encrypted data using the same AwsKmsMrkMultiKeyring you used on encrypt.
111    // It will decrypt the data using the generator key (in this case, the MRK), since that is
112    // the first available KMS key on the keyring that is capable of decrypting the data.
113    let decryption_response = esdk_client
114        .decrypt()
115        .ciphertext(ciphertext.clone())
116        .keyring(kms_mrk_multi_keyring)
117        // Provide the encryption context that was supplied to the encrypt method
118        .encryption_context(encryption_context.clone())
119        .send()
120        .await?;
121
122    let decrypted_plaintext = decryption_response
123        .plaintext
124        .expect("Unable to unwrap plaintext from decryption response");
125
126    // 7. Demonstrate that the decrypted plaintext is identical to the original plaintext.
127    // (This is an example for demonstration; you do not need to do this in your own code.)
128    assert_eq!(
129        decrypted_plaintext,
130        aws_smithy_types::Blob::new(plaintext),
131        "Decrypted plaintext should be identical to the original plaintext. Invalid decryption"
132    );
133
134    // Demonstrate that a single AwsKmsMrkKeyring configured with a replica of the MRK from the
135    // multi-keyring used to encrypt the data is also capable of decrypting the data.
136    // (This is an example for demonstration; you do not need to do this in your own code.)
137
138    // 8. Create a single AwsKmsMrkKeyring with the replica KMS MRK from the second region.
139
140    // Create a client for KMS in the second region which is the region for mrk_replica_key_id.
141    let sdk_config = aws_config::load_defaults(aws_config::BehaviorVersion::latest()).await;
142    let second_region_kms_config = aws_sdk_kms::config::Builder::from(&sdk_config)
143        .region(Region::new(mrk_replica_decrypt_region))
144        .build();
145    let second_region_kms_client = aws_sdk_kms::Client::from_conf(second_region_kms_config);
146
147    let second_region_mrk_keyring = mpl
148        .create_aws_kms_mrk_keyring()
149        .kms_key_id(mrk_replica_key_id)
150        .kms_client(second_region_kms_client)
151        .send()
152        .await?;
153
154    // 9. Decrypt your encrypted data using the second region AwsKmsMrkKeyring
155    let second_region_decryption_response = esdk_client
156        .decrypt()
157        .ciphertext(ciphertext)
158        .keyring(second_region_mrk_keyring)
159        // Provide the encryption context that was supplied to the encrypt method
160        .encryption_context(encryption_context)
161        .send()
162        .await?;
163
164    let second_region_decrypted_plaintext = second_region_decryption_response
165        .plaintext
166        .expect("Unable to unwrap plaintext from decryption response");
167
168    // 10. Demonstrate that the decrypted plaintext is identical to the original plaintext.
169    // (This is an example for demonstration; you do not need to do this in your own code.)
170    assert_eq!(
171        second_region_decrypted_plaintext,
172        aws_smithy_types::Blob::new(plaintext),
173        "Decrypted plaintext should be identical to the original plaintext. Invalid decryption"
174    );
175
176    // Not shown in this example: A KMS Keyring created with `kms_key_id` could also
177    // decrypt this message.
178
179    println!("KMS MRK Multi Keyring Example Completed Successfully");
180
181    Ok(())
182}
More examples
Hide additional examples
examples/client_supplier/client_supplier_example.rs (line 74)
27pub async fn encrypt_and_decrypt_with_keyring(
28    example_data: &str,
29    mrk_key_id_encrypt: &str,
30    aws_account_id: &str,
31    aws_regions: Vec<String>,
32) -> Result<(), crate::BoxError> {
33    // 1. Instantiate the encryption SDK client.
34    // This builds the default client with the RequireEncryptRequireDecrypt commitment policy,
35    // which enforces that this client only encrypts using committing algorithm suites and enforces
36    // that this client will only decrypt encrypted messages that were created with a committing
37    // algorithm suite.
38    let esdk_config = AwsEncryptionSdkConfig::builder().build()?;
39    let esdk_client = esdk_client::Client::from_conf(esdk_config)?;
40
41    // 2. Create encryption context.
42    // Remember that your encryption context is NOT SECRET.
43    // For more information, see
44    // https://docs.aws.amazon.com/encryption-sdk/latest/developer-guide/concepts.html#encryption-context
45    let encryption_context = HashMap::from([
46        ("encryption".to_string(), "context".to_string()),
47        ("is not".to_string(), "secret".to_string()),
48        ("but adds".to_string(), "useful metadata".to_string()),
49        (
50            "that can help you".to_string(),
51            "be confident that".to_string(),
52        ),
53        (
54            "the data you are handling".to_string(),
55            "is what you think it is".to_string(),
56        ),
57    ]);
58
59    // 3. Create a single MRK multi-keyring.
60    //    This can be either a single-region KMS key or an MRK.
61    //    For this example to succeed, the key's region must either
62    //    1) be in the regions list, or
63    //    2) the key must be an MRK with a replica defined
64    //    in a region in the regions list, and the client
65    //    must have the correct permissions to access the replica.
66    let mpl_config = MaterialProvidersConfig::builder().build()?;
67    let mpl = mpl_client::Client::from_conf(mpl_config)?;
68
69    // Create the multi-keyring using our custom client supplier
70    // defined in the RegionalRoleClientSupplier class in this directory.
71    // Note: RegionalRoleClientSupplier will internally use the key_arn's region
72    // to retrieve the correct IAM role.
73    let mrk_keyring_with_client_supplier = mpl
74        .create_aws_kms_mrk_multi_keyring()
75        .client_supplier(RegionalRoleClientSupplier {})
76        .generator(mrk_key_id_encrypt)
77        .send()
78        .await?;
79
80    // 4. Encrypt the data with the encryption_context using the encrypt_keyring.
81    let plaintext = example_data.as_bytes();
82
83    let encryption_response = esdk_client
84        .encrypt()
85        .plaintext(plaintext)
86        .keyring(mrk_keyring_with_client_supplier)
87        .encryption_context(encryption_context.clone())
88        .send()
89        .await?;
90
91    let ciphertext = encryption_response
92        .ciphertext
93        .expect("Unable to unwrap ciphertext from encryption response");
94
95    // 5. Demonstrate that the ciphertext and plaintext are different.
96    // (This is an example for demonstration; you do not need to do this in your own code.)
97    assert_ne!(
98        ciphertext,
99        aws_smithy_types::Blob::new(plaintext),
100        "Ciphertext and plaintext data are the same. Invalid encryption"
101    );
102
103    // 6. Create a MRK discovery multi-keyring with a custom client supplier.
104    //    A discovery MRK multi-keyring will be composed of
105    //    multiple discovery MRK keyrings, one for each region.
106    //    Each component keyring has its own KMS client in a particular region.
107    //    When we provide a client supplier to the multi-keyring, all component
108    //    keyrings will use that client supplier configuration.
109    //    In our tests, we make `mrk_key_id_encrypt` an MRK with a replica, and
110    //    provide only the replica region in our discovery filter.
111    let discovery_filter = DiscoveryFilter::builder()
112        .account_ids(vec![aws_account_id.to_string()])
113        .partition("aws".to_string())
114        .build()?;
115
116    let mrk_discovery_client_supplier_keyring = mpl
117        .create_aws_kms_mrk_discovery_multi_keyring()
118        .client_supplier(RegionalRoleClientSupplier {})
119        .discovery_filter(discovery_filter.clone())
120        .regions(aws_regions)
121        .send()
122        .await?;
123
124    // 7. Decrypt your encrypted data using the discovery multi keyring.
125    // On Decrypt, the header of the encrypted message (ciphertext) will be parsed.
126    // The header contains the Encrypted Data Keys (EDKs), which, if the EDK
127    // was encrypted by a KMS Keyring, includes the KMS Key ARN.
128    // For each member of the Multi Keyring, every EDK will try to be decrypted until a decryption
129    // is successful.
130    // Since every member of the Multi Keyring is a Discovery Keyring:
131    //   Each Keyring will filter the EDKs by the Discovery Filter and the Keyring's region.
132    //      For each filtered EDK, the keyring will attempt decryption with the keyring's client.
133    // All of this is done serially, until a success occurs or all keyrings have failed
134    // all (filtered) EDKs. KMS MRK Discovery Keyrings will attempt to decrypt
135    // Multi Region Keys (MRKs) and regular KMS Keys.
136    let decryption_response = esdk_client
137        .decrypt()
138        .ciphertext(ciphertext)
139        .keyring(mrk_discovery_client_supplier_keyring)
140        // Provide the encryption context that was supplied to the encrypt method
141        .encryption_context(encryption_context)
142        .send()
143        .await?;
144
145    let decrypted_plaintext = decryption_response
146        .plaintext
147        .expect("Unable to unwrap plaintext from decryption response");
148
149    // 8. Demonstrate that the decrypted plaintext is identical to the original plaintext.
150    // (This is an example for demonstration; you do not need to do this in your own code.)
151    assert_eq!(
152        decrypted_plaintext,
153        aws_smithy_types::Blob::new(plaintext),
154        "Decrypted plaintext should be identical to the original plaintext. Invalid decryption"
155    );
156
157    // 9. Test the Missing Region Exception
158    // (This is an example for demonstration; you do not need to do this in your own code.)
159    let mrk_discovery_client_supplier_keyring_missing_region = mpl
160        .create_aws_kms_mrk_discovery_multi_keyring()
161        .client_supplier(RegionalRoleClientSupplier {})
162        .discovery_filter(discovery_filter)
163        .regions(vec!["fake-region".to_string()])
164        .send()
165        .await;
166
167    // Swallow the exception
168    // (This is an example for demonstration; you do not need to do this in your own code.)
169    match mrk_discovery_client_supplier_keyring_missing_region {
170        Ok(_) => panic!(
171            "Decryption using discovery keyring with missing region MUST \
172                            raise AwsCryptographicMaterialProvidersException"
173        ),
174        Err(AwsCryptographicMaterialProvidersException { message: _e }) => (),
175        _ => panic!("Unexpected error type"),
176    }
177
178    println!("Client Supplier Example Completed Successfully");
179
180    Ok(())
181}
Source§

impl Client

Source

pub fn create_aws_kms_mrk_discovery_keyring( &self, ) -> CreateAwsKmsMrkDiscoveryKeyringFluentBuilder

Examples found in repository?
examples/keyring/aws_kms_mrk_discovery_keyring_example.rs (line 144)
49pub async fn encrypt_and_decrypt_with_keyring(
50    example_data: &str,
51    mrk_key_id_encrypt: &str,
52    aws_account_id: &str,
53    mrk_encrypt_region: String,
54    mrk_replica_decrypt_region: String,
55) -> Result<(), crate::BoxError> {
56    // 1. Instantiate the encryption SDK client.
57    // This builds the default client with the RequireEncryptRequireDecrypt commitment policy,
58    // which enforces that this client only encrypts using committing algorithm suites and enforces
59    // that this client will only decrypt encrypted messages that were created with a committing
60    // algorithm suite.
61    let esdk_config = AwsEncryptionSdkConfig::builder().build()?;
62    let esdk_client = esdk_client::Client::from_conf(esdk_config)?;
63
64    // 2. Create encryption context.
65    // Remember that your encryption context is NOT SECRET.
66    // For more information, see
67    // https://docs.aws.amazon.com/encryption-sdk/latest/developer-guide/concepts.html#encryption-context
68    let encryption_context = HashMap::from([
69        ("encryption".to_string(), "context".to_string()),
70        ("is not".to_string(), "secret".to_string()),
71        ("but adds".to_string(), "useful metadata".to_string()),
72        (
73            "that can help you".to_string(),
74            "be confident that".to_string(),
75        ),
76        (
77            "the data you are handling".to_string(),
78            "is what you think it is".to_string(),
79        ),
80    ]);
81
82    // 3. Create the keyring that determines how your data keys are protected.
83    // Although this example highlights Discovery keyrings, Discovery keyrings cannot
84    // be used to encrypt, so for encryption we create an MRK keyring without discovery mode.
85    let mpl_config = MaterialProvidersConfig::builder().build()?;
86    let mpl = mpl_client::Client::from_conf(mpl_config)?;
87
88    // Create a KMS client in the first region
89    let sdk_config = aws_config::load_defaults(aws_config::BehaviorVersion::latest()).await;
90    let encrypt_kms_config = aws_sdk_kms::config::Builder::from(&sdk_config)
91        .region(Region::new(mrk_encrypt_region))
92        .build();
93    let encrypt_kms_client = aws_sdk_kms::Client::from_conf(encrypt_kms_config);
94
95    // Create a keyring that will encrypt your data, using a KMS MRK in the first region.
96    let encrypt_kms_keyring = mpl
97        .create_aws_kms_mrk_keyring()
98        .kms_key_id(mrk_key_id_encrypt)
99        .kms_client(encrypt_kms_client)
100        .send()
101        .await?;
102
103    // 4. Encrypt the data with the encryption_context using the encrypt_keyring.
104    let plaintext = example_data.as_bytes();
105
106    let encryption_response = esdk_client
107        .encrypt()
108        .plaintext(plaintext)
109        .keyring(encrypt_kms_keyring)
110        .encryption_context(encryption_context.clone())
111        .send()
112        .await?;
113
114    let ciphertext = encryption_response
115        .ciphertext
116        .expect("Unable to unwrap ciphertext from encryption response");
117
118    // 5. Demonstrate that the ciphertext and plaintext are different.
119    // (This is an example for demonstration; you do not need to do this in your own code.)
120    assert_ne!(
121        ciphertext,
122        aws_smithy_types::Blob::new(plaintext),
123        "Ciphertext and plaintext data are the same. Invalid encryption"
124    );
125
126    // 6. Now create a Discovery keyring to use for decryption.
127    // In order to illustrate the MRK behavior of this keyring, we configure
128    // the keyring to use the second KMS region where the MRK (mrk_key_id_encrypt) is replicated to.
129    // This example assumes you have already replicated your key, but since we
130    // are using a discovery keyring, we don't need to provide the mrk replica key id
131
132    // Create a KMS Client in the second region.
133    let decrypt_kms_config = aws_sdk_kms::config::Builder::from(&sdk_config)
134        .region(Region::new(mrk_replica_decrypt_region.clone()))
135        .build();
136    let decrypt_kms_client = aws_sdk_kms::Client::from_conf(decrypt_kms_config);
137
138    let discovery_filter = DiscoveryFilter::builder()
139        .account_ids(vec![aws_account_id.to_string()])
140        .partition("aws".to_string())
141        .build()?;
142
143    let discovery_keyring = mpl
144        .create_aws_kms_mrk_discovery_keyring()
145        .kms_client(decrypt_kms_client)
146        .region(mrk_replica_decrypt_region)
147        .discovery_filter(discovery_filter)
148        .send()
149        .await?;
150
151    // 7. Decrypt your encrypted data using the discovery keyring.
152    let decryption_response = esdk_client
153        .decrypt()
154        .ciphertext(ciphertext)
155        .keyring(discovery_keyring)
156        // Provide the encryption context that was supplied to the encrypt method
157        .encryption_context(encryption_context)
158        .send()
159        .await?;
160
161    let decrypted_plaintext = decryption_response
162        .plaintext
163        .expect("Unable to unwrap plaintext from decryption response");
164
165    // 8. Demonstrate that the decrypted plaintext is identical to the original plaintext.
166    // (This is an example for demonstration; you do not need to do this in your own code.)
167    assert_eq!(
168        decrypted_plaintext,
169        aws_smithy_types::Blob::new(plaintext),
170        "Decrypted plaintext should be identical to the original plaintext. Invalid decryption"
171    );
172
173    println!("KMS MRK Discovery Keyring Example Completed Successfully");
174
175    Ok(())
176}
Source§

impl Client

Source

pub fn create_aws_kms_mrk_discovery_multi_keyring( &self, ) -> CreateAwsKmsMrkDiscoveryMultiKeyringFluentBuilder

Examples found in repository?
examples/keyring/aws_kms_mrk_discovery_multi_keyring_example.rs (line 144)
51pub async fn encrypt_and_decrypt_with_keyring(
52    example_data: &str,
53    mrk_key_id_encrypt: &str,
54    mrk_encrypt_region: String,
55    aws_account_id: &str,
56    aws_regions: Vec<String>,
57) -> Result<(), crate::BoxError> {
58    // 1. Instantiate the encryption SDK client.
59    // This builds the default client with the RequireEncryptRequireDecrypt commitment policy,
60    // which enforces that this client only encrypts using committing algorithm suites and enforces
61    // that this client will only decrypt encrypted messages that were created with a committing
62    // algorithm suite.
63    let esdk_config = AwsEncryptionSdkConfig::builder().build()?;
64    let esdk_client = esdk_client::Client::from_conf(esdk_config)?;
65
66    // 2. Create encryption context.
67    // Remember that your encryption context is NOT SECRET.
68    // For more information, see
69    // https://docs.aws.amazon.com/encryption-sdk/latest/developer-guide/concepts.html#encryption-context
70    let encryption_context = HashMap::from([
71        ("encryption".to_string(), "context".to_string()),
72        ("is not".to_string(), "secret".to_string()),
73        ("but adds".to_string(), "useful metadata".to_string()),
74        (
75            "that can help you".to_string(),
76            "be confident that".to_string(),
77        ),
78        (
79            "the data you are handling".to_string(),
80            "is what you think it is".to_string(),
81        ),
82    ]);
83
84    // 3. Create the keyring that determines how your data keys are protected.
85    // Although this example highlights Discovery keyrings, Discovery keyrings cannot
86    // be used to encrypt, so for encryption we create an MRK keyring without discovery mode.
87    let mpl_config = MaterialProvidersConfig::builder().build()?;
88    let mpl = mpl_client::Client::from_conf(mpl_config)?;
89
90    // Create a KMS client in the first region
91    let sdk_config = aws_config::load_defaults(aws_config::BehaviorVersion::latest()).await;
92    let encrypt_kms_config = aws_sdk_kms::config::Builder::from(&sdk_config)
93        .region(Region::new(mrk_encrypt_region))
94        .build();
95    let encrypt_kms_client = aws_sdk_kms::Client::from_conf(encrypt_kms_config);
96
97    // Create a keyring that will encrypt your data, using a KMS MRK in the first region.
98    let encrypt_kms_keyring = mpl
99        .create_aws_kms_mrk_keyring()
100        .kms_key_id(mrk_key_id_encrypt)
101        .kms_client(encrypt_kms_client)
102        .send()
103        .await?;
104
105    // 4. Encrypt the data with the encryption_context using the encrypt_keyring.
106    let plaintext = example_data.as_bytes();
107
108    let encryption_response = esdk_client
109        .encrypt()
110        .plaintext(plaintext)
111        .keyring(encrypt_kms_keyring)
112        .encryption_context(encryption_context.clone())
113        .send()
114        .await?;
115
116    let ciphertext = encryption_response
117        .ciphertext
118        .expect("Unable to unwrap ciphertext from encryption response");
119
120    // 5. Demonstrate that the ciphertext and plaintext are different.
121    // (This is an example for demonstration; you do not need to do this in your own code.)
122    assert_ne!(
123        ciphertext,
124        aws_smithy_types::Blob::new(plaintext),
125        "Ciphertext and plaintext data are the same. Invalid encryption"
126    );
127
128    // 6. Now create a MRK Discovery Multi Keyring to use for decryption.
129    // We'll add a discovery filter to limit the set of encrypted data keys
130    // we are willing to decrypt to only ones created by KMS keys in select
131    // accounts and the partition `aws`.
132    // MRK Discovery keyrings also filter encrypted data keys by the region
133    // the keyring is created with.
134    let discovery_filter = DiscoveryFilter::builder()
135        .account_ids(vec![aws_account_id.to_string()])
136        .partition("aws".to_string())
137        .build()?;
138
139    // This is a Multi Keyring composed of Discovery Keyrings.
140    // There is a keyring for every region in `regions`.
141    // All the keyrings have the same Discovery Filter.
142    // Each keyring has its own KMS Client, which is created for the keyring's region.
143    let discovery_multi_keyring = mpl
144        .create_aws_kms_mrk_discovery_multi_keyring()
145        .regions(aws_regions)
146        .discovery_filter(discovery_filter)
147        .send()
148        .await?;
149
150    // 7. Decrypt your encrypted data using the discovery multi keyring.
151    // On Decrypt, the header of the encrypted message (ciphertext) will be parsed.
152    // The header contains the Encrypted Data Keys (EDKs), which, if the EDK
153    // was encrypted by a KMS Keyring, includes the KMS Key ARN.
154    // For each member of the Multi Keyring, every EDK will try to be decrypted until a decryption
155    // is successful.
156    // Since every member of the Multi Keyring is a Discovery Keyring:
157    //   Each Keyring will filter the EDKs by the Discovery Filter and the Keyring's region.
158    //      For each filtered EDK, the keyring will attempt decryption with the keyring's client.
159    // All of this is done serially, until a success occurs or all keyrings have failed
160    // all (filtered) EDKs. KMS MRK Discovery Keyrings will attempt to decrypt
161    // Multi Region Keys (MRKs) and regular KMS Keys.
162    let decryption_response = esdk_client
163        .decrypt()
164        .ciphertext(ciphertext)
165        .keyring(discovery_multi_keyring)
166        // Provide the encryption context that was supplied to the encrypt method
167        .encryption_context(encryption_context)
168        .send()
169        .await?;
170
171    let decrypted_plaintext = decryption_response
172        .plaintext
173        .expect("Unable to unwrap plaintext from decryption response");
174
175    // 8. Demonstrate that the decrypted plaintext is identical to the original plaintext.
176    // (This is an example for demonstration; you do not need to do this in your own code.)
177    assert_eq!(
178        decrypted_plaintext,
179        aws_smithy_types::Blob::new(plaintext),
180        "Decrypted plaintext should be identical to the original plaintext. Invalid decryption"
181    );
182
183    println!("KMS MRK Discovery Multi Keyring Example Completed Successfully");
184
185    Ok(())
186}
More examples
Hide additional examples
examples/client_supplier/client_supplier_example.rs (line 117)
27pub async fn encrypt_and_decrypt_with_keyring(
28    example_data: &str,
29    mrk_key_id_encrypt: &str,
30    aws_account_id: &str,
31    aws_regions: Vec<String>,
32) -> Result<(), crate::BoxError> {
33    // 1. Instantiate the encryption SDK client.
34    // This builds the default client with the RequireEncryptRequireDecrypt commitment policy,
35    // which enforces that this client only encrypts using committing algorithm suites and enforces
36    // that this client will only decrypt encrypted messages that were created with a committing
37    // algorithm suite.
38    let esdk_config = AwsEncryptionSdkConfig::builder().build()?;
39    let esdk_client = esdk_client::Client::from_conf(esdk_config)?;
40
41    // 2. Create encryption context.
42    // Remember that your encryption context is NOT SECRET.
43    // For more information, see
44    // https://docs.aws.amazon.com/encryption-sdk/latest/developer-guide/concepts.html#encryption-context
45    let encryption_context = HashMap::from([
46        ("encryption".to_string(), "context".to_string()),
47        ("is not".to_string(), "secret".to_string()),
48        ("but adds".to_string(), "useful metadata".to_string()),
49        (
50            "that can help you".to_string(),
51            "be confident that".to_string(),
52        ),
53        (
54            "the data you are handling".to_string(),
55            "is what you think it is".to_string(),
56        ),
57    ]);
58
59    // 3. Create a single MRK multi-keyring.
60    //    This can be either a single-region KMS key or an MRK.
61    //    For this example to succeed, the key's region must either
62    //    1) be in the regions list, or
63    //    2) the key must be an MRK with a replica defined
64    //    in a region in the regions list, and the client
65    //    must have the correct permissions to access the replica.
66    let mpl_config = MaterialProvidersConfig::builder().build()?;
67    let mpl = mpl_client::Client::from_conf(mpl_config)?;
68
69    // Create the multi-keyring using our custom client supplier
70    // defined in the RegionalRoleClientSupplier class in this directory.
71    // Note: RegionalRoleClientSupplier will internally use the key_arn's region
72    // to retrieve the correct IAM role.
73    let mrk_keyring_with_client_supplier = mpl
74        .create_aws_kms_mrk_multi_keyring()
75        .client_supplier(RegionalRoleClientSupplier {})
76        .generator(mrk_key_id_encrypt)
77        .send()
78        .await?;
79
80    // 4. Encrypt the data with the encryption_context using the encrypt_keyring.
81    let plaintext = example_data.as_bytes();
82
83    let encryption_response = esdk_client
84        .encrypt()
85        .plaintext(plaintext)
86        .keyring(mrk_keyring_with_client_supplier)
87        .encryption_context(encryption_context.clone())
88        .send()
89        .await?;
90
91    let ciphertext = encryption_response
92        .ciphertext
93        .expect("Unable to unwrap ciphertext from encryption response");
94
95    // 5. Demonstrate that the ciphertext and plaintext are different.
96    // (This is an example for demonstration; you do not need to do this in your own code.)
97    assert_ne!(
98        ciphertext,
99        aws_smithy_types::Blob::new(plaintext),
100        "Ciphertext and plaintext data are the same. Invalid encryption"
101    );
102
103    // 6. Create a MRK discovery multi-keyring with a custom client supplier.
104    //    A discovery MRK multi-keyring will be composed of
105    //    multiple discovery MRK keyrings, one for each region.
106    //    Each component keyring has its own KMS client in a particular region.
107    //    When we provide a client supplier to the multi-keyring, all component
108    //    keyrings will use that client supplier configuration.
109    //    In our tests, we make `mrk_key_id_encrypt` an MRK with a replica, and
110    //    provide only the replica region in our discovery filter.
111    let discovery_filter = DiscoveryFilter::builder()
112        .account_ids(vec![aws_account_id.to_string()])
113        .partition("aws".to_string())
114        .build()?;
115
116    let mrk_discovery_client_supplier_keyring = mpl
117        .create_aws_kms_mrk_discovery_multi_keyring()
118        .client_supplier(RegionalRoleClientSupplier {})
119        .discovery_filter(discovery_filter.clone())
120        .regions(aws_regions)
121        .send()
122        .await?;
123
124    // 7. Decrypt your encrypted data using the discovery multi keyring.
125    // On Decrypt, the header of the encrypted message (ciphertext) will be parsed.
126    // The header contains the Encrypted Data Keys (EDKs), which, if the EDK
127    // was encrypted by a KMS Keyring, includes the KMS Key ARN.
128    // For each member of the Multi Keyring, every EDK will try to be decrypted until a decryption
129    // is successful.
130    // Since every member of the Multi Keyring is a Discovery Keyring:
131    //   Each Keyring will filter the EDKs by the Discovery Filter and the Keyring's region.
132    //      For each filtered EDK, the keyring will attempt decryption with the keyring's client.
133    // All of this is done serially, until a success occurs or all keyrings have failed
134    // all (filtered) EDKs. KMS MRK Discovery Keyrings will attempt to decrypt
135    // Multi Region Keys (MRKs) and regular KMS Keys.
136    let decryption_response = esdk_client
137        .decrypt()
138        .ciphertext(ciphertext)
139        .keyring(mrk_discovery_client_supplier_keyring)
140        // Provide the encryption context that was supplied to the encrypt method
141        .encryption_context(encryption_context)
142        .send()
143        .await?;
144
145    let decrypted_plaintext = decryption_response
146        .plaintext
147        .expect("Unable to unwrap plaintext from decryption response");
148
149    // 8. Demonstrate that the decrypted plaintext is identical to the original plaintext.
150    // (This is an example for demonstration; you do not need to do this in your own code.)
151    assert_eq!(
152        decrypted_plaintext,
153        aws_smithy_types::Blob::new(plaintext),
154        "Decrypted plaintext should be identical to the original plaintext. Invalid decryption"
155    );
156
157    // 9. Test the Missing Region Exception
158    // (This is an example for demonstration; you do not need to do this in your own code.)
159    let mrk_discovery_client_supplier_keyring_missing_region = mpl
160        .create_aws_kms_mrk_discovery_multi_keyring()
161        .client_supplier(RegionalRoleClientSupplier {})
162        .discovery_filter(discovery_filter)
163        .regions(vec!["fake-region".to_string()])
164        .send()
165        .await;
166
167    // Swallow the exception
168    // (This is an example for demonstration; you do not need to do this in your own code.)
169    match mrk_discovery_client_supplier_keyring_missing_region {
170        Ok(_) => panic!(
171            "Decryption using discovery keyring with missing region MUST \
172                            raise AwsCryptographicMaterialProvidersException"
173        ),
174        Err(AwsCryptographicMaterialProvidersException { message: _e }) => (),
175        _ => panic!("Unexpected error type"),
176    }
177
178    println!("Client Supplier Example Completed Successfully");
179
180    Ok(())
181}
Source§

impl Client

Source

pub fn create_aws_kms_hierarchical_keyring( &self, ) -> CreateAwsKmsHierarchicalKeyringFluentBuilder

Examples found in repository?
examples/keyring/aws_kms_hierarchical/aws_kms_hierarchical_keyring_example.rs (line 109)
52pub async fn encrypt_and_decrypt_with_keyring(
53    example_data: &str,
54    key_store_table_name: &str,
55    logical_key_store_name: &str,
56    key_store_kms_key_id: &str,
57) -> Result<(), crate::BoxError> {
58    // 1. Instantiate the encryption SDK client.
59    // This builds the default client with the RequireEncryptRequireDecrypt commitment policy,
60    // which enforces that this client only encrypts using committing algorithm suites and enforces
61    // that this client will only decrypt encrypted messages that were created with a committing
62    // algorithm suite.
63    let esdk_config = AwsEncryptionSdkConfig::builder().build()?;
64    let esdk_client = esdk_client::Client::from_conf(esdk_config)?;
65
66    // 2. Create a KMS client and DynamoDB client.
67    let sdk_config = aws_config::load_defaults(aws_config::BehaviorVersion::latest()).await;
68    let kms_client = aws_sdk_kms::Client::new(&sdk_config);
69    let ddb_client = aws_sdk_dynamodb::Client::new(&sdk_config);
70
71    // 3. Configure your KeyStore resource.
72    //    This SHOULD be the same configuration that you used
73    //    to initially create and populate your KeyStore.
74    let key_store_config = KeyStoreConfig::builder()
75        .kms_client(kms_client)
76        .ddb_client(ddb_client)
77        .ddb_table_name(key_store_table_name)
78        .logical_key_store_name(logical_key_store_name)
79        .kms_configuration(KmsConfiguration::KmsKeyArn(
80            key_store_kms_key_id.to_string(),
81        ))
82        .build()?;
83
84    let key_store = keystore_client::Client::from_conf(key_store_config)?;
85
86    // 4. Call CreateKey to create two new active branch keys
87    let branch_key_id_a: String = create_branch_key_id(
88        key_store_table_name,
89        logical_key_store_name,
90        key_store_kms_key_id,
91    )
92    .await?;
93    let branch_key_id_b: String = create_branch_key_id(
94        key_store_table_name,
95        logical_key_store_name,
96        key_store_kms_key_id,
97    )
98    .await?;
99
100    // 5. Create a branch key supplier that maps the branch key id to a more readable format
101    let branch_key_id_supplier =
102        ExampleBranchKeyIdSupplier::new(&branch_key_id_a, &branch_key_id_b);
103
104    // 6. Create the Hierarchical Keyring.
105    let mpl_config = MaterialProvidersConfig::builder().build()?;
106    let mpl = mpl_client::Client::from_conf(mpl_config)?;
107
108    let hierarchical_keyring = mpl
109        .create_aws_kms_hierarchical_keyring()
110        .key_store(key_store.clone())
111        .branch_key_id_supplier(branch_key_id_supplier)
112        .ttl_seconds(600)
113        .send()
114        .await?;
115
116    // 7. Create encryption context for both tenants.
117    //    The Branch Key Id supplier uses the encryption context to determine which branch key id will
118    //    be used to encrypt data.
119    // Remember that your encryption context is NOT SECRET.
120    // For more information, see
121    // https://docs.aws.amazon.com/encryption-sdk/latest/developer-guide/concepts.html#encryption-context
122
123    // Create encryption context for TenantA
124    let encryption_context_a = HashMap::from([
125        ("tenant".to_string(), "TenantA".to_string()),
126        ("encryption".to_string(), "context".to_string()),
127        ("is not".to_string(), "secret".to_string()),
128        ("but adds".to_string(), "useful metadata".to_string()),
129        (
130            "that can help you".to_string(),
131            "be confident that".to_string(),
132        ),
133        (
134            "the data you are handling".to_string(),
135            "is what you think it is".to_string(),
136        ),
137    ]);
138
139    // Create encryption context for TenantB
140    let encryption_context_b = HashMap::from([
141        ("tenant".to_string(), "TenantB".to_string()),
142        ("encryption".to_string(), "context".to_string()),
143        ("is not".to_string(), "secret".to_string()),
144        ("but adds".to_string(), "useful metadata".to_string()),
145        (
146            "that can help you".to_string(),
147            "be confident that".to_string(),
148        ),
149        (
150            "the data you are handling".to_string(),
151            "is what you think it is".to_string(),
152        ),
153    ]);
154
155    // 8. Encrypt the data with encryption_contextA & encryption_contextB
156    let plaintext = example_data.as_bytes();
157
158    let encryption_response_a = esdk_client
159        .encrypt()
160        .plaintext(plaintext)
161        .keyring(hierarchical_keyring.clone())
162        .encryption_context(encryption_context_a.clone())
163        .send()
164        .await?;
165
166    let ciphertext_a = encryption_response_a
167        .ciphertext
168        .expect("Unable to unwrap ciphertext from encryption response");
169
170    let encryption_response_b = esdk_client
171        .encrypt()
172        .plaintext(plaintext)
173        .keyring(hierarchical_keyring.clone())
174        .encryption_context(encryption_context_b.clone())
175        .send()
176        .await?;
177
178    let ciphertext_b = encryption_response_b
179        .ciphertext
180        .expect("Unable to unwrap ciphertext from encryption response");
181
182    // 9. Demonstrate that the ciphertexts and plaintext are different.
183    // (This is an example for demonstration; you do not need to do this in your own code.)
184    assert_ne!(
185        ciphertext_a,
186        aws_smithy_types::Blob::new(plaintext),
187        "Ciphertext and plaintext data are the same. Invalid encryption"
188    );
189
190    assert_ne!(
191        ciphertext_b,
192        aws_smithy_types::Blob::new(plaintext),
193        "Ciphertext and plaintext data are the same. Invalid encryption"
194    );
195
196    // 10. To attest that TenantKeyB cannot decrypt a message written by TenantKeyA,
197    //    and vice versa, let's construct more restrictive hierarchical keyrings.
198    let hierarchical_keyring_a = mpl
199        .create_aws_kms_hierarchical_keyring()
200        .key_store(key_store.clone())
201        .branch_key_id(branch_key_id_a)
202        .ttl_seconds(600)
203        .send()
204        .await?;
205
206    let hierarchical_keyring_b = mpl
207        .create_aws_kms_hierarchical_keyring()
208        .key_store(key_store)
209        .branch_key_id(branch_key_id_b)
210        .ttl_seconds(600)
211        .send()
212        .await?;
213
214    // 11. Demonstrate that data encrypted by one tenant's key
215    // cannot be decrypted with by a keyring specific to another tenant.
216
217    // Keyring with tenant B's branch key cannot decrypt data encrypted with tenant A's branch key
218    // This will fail and raise a AwsCryptographicMaterialProvidersError,
219    // which we swallow ONLY for demonstration purposes.
220    let decryption_response_mismatch_1 = esdk_client
221        .decrypt()
222        .ciphertext(ciphertext_a.clone())
223        .keyring(hierarchical_keyring_b.clone())
224        // Provide the encryption context that was supplied to the encrypt method
225        .encryption_context(encryption_context_a.clone())
226        .send()
227        .await;
228
229    match decryption_response_mismatch_1 {
230        Ok(_) => panic!(
231            "Decrypt with wrong tenant's hierarchical keyring MUST \
232                            raise AwsCryptographicMaterialProvidersError"
233        ),
234        Err(AwsCryptographicMaterialProvidersError { error: _e }) => (),
235        _ => panic!("Unexpected error type"),
236    }
237
238    // Keyring with tenant A's branch key cannot decrypt data encrypted with tenant B's branch key.
239    // This will fail and raise a AwsCryptographicMaterialProvidersError,
240    // which we swallow ONLY for demonstration purposes.
241    let decryption_response_mismatch_2 = esdk_client
242        .decrypt()
243        .ciphertext(ciphertext_b.clone())
244        .keyring(hierarchical_keyring_a.clone())
245        // Provide the encryption context that was supplied to the encrypt method
246        .encryption_context(encryption_context_b.clone())
247        .send()
248        .await;
249
250    match decryption_response_mismatch_2 {
251        Ok(_) => panic!(
252            "Decrypt with wrong tenant's hierarchical keyring MUST \
253                            raise AwsCryptographicMaterialProvidersError"
254        ),
255        Err(AwsCryptographicMaterialProvidersError { error: _e }) => (),
256        _ => panic!("Unexpected error type"),
257    }
258
259    // 12. Demonstrate that data encrypted by one tenant's branch key can be decrypted by that tenant,
260    //     and that the decrypted data matches the input data.
261    let decryption_response_a = esdk_client
262        .decrypt()
263        .ciphertext(ciphertext_a)
264        .keyring(hierarchical_keyring_a)
265        // Provide the encryption context that was supplied to the encrypt method
266        .encryption_context(encryption_context_a)
267        .send()
268        .await?;
269
270    let decrypted_plaintext_a = decryption_response_a
271        .plaintext
272        .expect("Unable to unwrap plaintext from decryption response");
273
274    // Demonstrate that the decrypted plaintext is identical to the original plaintext.
275    // (This is an example for demonstration; you do not need to do this in your own code.)
276    assert_eq!(
277        decrypted_plaintext_a,
278        aws_smithy_types::Blob::new(plaintext),
279        "Decrypted plaintext should be identical to the original plaintext. Invalid decryption"
280    );
281
282    // Similarly for TenantB
283    let decryption_response_b = esdk_client
284        .decrypt()
285        .ciphertext(ciphertext_b)
286        .keyring(hierarchical_keyring_b)
287        // Provide the encryption context that was supplied to the encrypt method
288        .encryption_context(encryption_context_b)
289        .send()
290        .await?;
291
292    let decrypted_plaintext_b = decryption_response_b
293        .plaintext
294        .expect("Unable to unwrap plaintext from decryption response");
295
296    // Demonstrate that the decrypted plaintext is identical to the original plaintext.
297    // (This is an example for demonstration; you do not need to do this in your own code.)
298    assert_eq!(
299        decrypted_plaintext_b,
300        aws_smithy_types::Blob::new(plaintext),
301        "Decrypted plaintext should be identical to the original plaintext. Invalid decryption"
302    );
303
304    println!("Hierarchical Keyring Example Completed Successfully");
305
306    Ok(())
307}
More examples
Hide additional examples
examples/keyring/aws_kms_hierarchical/shared_cache_across_hierarchical_keyrings_example.rs (line 156)
78pub async fn encrypt_and_decrypt_with_keyring(
79    example_data: &str,
80    key_store_table_name: &str,
81    logical_key_store_name: &str,
82    key_store_kms_key_id: &str,
83) -> Result<(), crate::BoxError> {
84    // 1a. Create the CryptographicMaterialsCache (CMC) to share across multiple Hierarchical Keyrings
85    // using the Material Providers Library
86    //    This CMC takes in:
87    //     - CacheType
88    let mpl_config = MaterialProvidersConfig::builder().build()?;
89    let mpl = mpl_client::Client::from_conf(mpl_config)?;
90
91    let cache: CacheType = CacheType::Default(DefaultCache::builder().entry_capacity(100).build()?);
92
93    let shared_cryptographic_materials_cache: CryptographicMaterialsCacheRef = mpl
94        .create_cryptographic_materials_cache()
95        .cache(cache)
96        .send()
97        .await?;
98
99    // 1b. Create a CacheType object for the shared_cryptographic_materials_cache
100    // Note that the `cache` parameter in the Hierarchical Keyring Input takes a `CacheType` as input
101    // Here, we pass a `Shared` CacheType that passes an already initialized shared cache.
102
103    // If you want to use a Shared Cache, you need to initialize it only once, and
104    // pass the same cache `shared_cache` to different hierarchical keyrings.
105
106    // CryptographicMaterialsCacheRef is an Rc (Reference Counted), so if you clone it to
107    // pass it to different Hierarchical Keyrings, it will still point to the same
108    // underlying cache, and increment the reference count accordingly.
109    let shared_cache: CacheType = CacheType::Shared(shared_cryptographic_materials_cache);
110
111    // 2. Instantiate the encryption SDK client.
112    // This builds the default client with the RequireEncryptRequireDecrypt commitment policy,
113    // which enforces that this client only encrypts using committing algorithm suites and enforces
114    // that this client will only decrypt encrypted messages that were created with a committing
115    // algorithm suite.
116    let esdk_config = AwsEncryptionSdkConfig::builder().build()?;
117    let esdk_client = esdk_client::Client::from_conf(esdk_config)?;
118
119    // 3. Configure your Key Store resource key_store1.
120    //    This SHOULD be the same configuration that you used
121    //    to initially create and populate your physical Key Store.
122    // Note that key_store_table_name is the physical Key Store,
123    // and key_store1 is instances of this physical Key Store.
124    let sdk_config = aws_config::load_defaults(aws_config::BehaviorVersion::latest()).await;
125    let key_store_config = KeyStoreConfig::builder()
126        .kms_client(aws_sdk_kms::Client::new(&sdk_config))
127        .ddb_client(aws_sdk_dynamodb::Client::new(&sdk_config))
128        .ddb_table_name(key_store_table_name)
129        .logical_key_store_name(logical_key_store_name)
130        .kms_configuration(KmsConfiguration::KmsKeyArn(
131            key_store_kms_key_id.to_string(),
132        ))
133        .build()?;
134
135    let key_store1 = keystore_client::Client::from_conf(key_store_config.clone())?;
136
137    // 4. Call create_branch_key_id to create one new active branch key
138    let branch_key_id: String = create_branch_key_id(
139        key_store_table_name,
140        logical_key_store_name,
141        key_store_kms_key_id,
142    )
143    .await?;
144
145    // 5. Create the Hierarchical Keyring HK1 with Key Store instance K1, partition_id,
146    // the shared_cache and the branch_key_id.
147    // Note that we are now providing an already initialized shared cache instead of just mentioning
148    // the cache type and the Hierarchical Keyring initializing a cache at initialization.
149
150    // partition_id for this example is a random UUID
151    let partition_id = "91c1b6a2-6fc3-4539-ad5e-938d597ed730".to_string();
152
153    // Please make sure that you read the guidance on how to set Partition ID, Logical Key Store Name and
154    // Branch Key ID at the top of this example before creating Hierarchical Keyrings with a Shared Cache
155    let keyring1 = mpl
156        .create_aws_kms_hierarchical_keyring()
157        .key_store(key_store1)
158        .branch_key_id(branch_key_id.clone())
159        // CryptographicMaterialsCacheRef is an Rc (Reference Counted), so if you clone it to
160        // pass it to different Hierarchical Keyrings, it will still point to the same
161        // underlying cache, and increment the reference count accordingly.
162        .cache(shared_cache.clone())
163        .ttl_seconds(600)
164        .partition_id(partition_id.clone())
165        .send()
166        .await?;
167
168    // 6. Create encryption context.
169    // Remember that your encryption context is NOT SECRET.
170    // For more information, see
171    // https://docs.aws.amazon.com/encryption-sdk/latest/developer-guide/concepts.html#encryption-context
172    let encryption_context = HashMap::from([
173        ("encryption".to_string(), "context".to_string()),
174        ("is not".to_string(), "secret".to_string()),
175        ("but adds".to_string(), "useful metadata".to_string()),
176        (
177            "that can help you".to_string(),
178            "be confident that".to_string(),
179        ),
180        (
181            "the data you are handling".to_string(),
182            "is what you think it is".to_string(),
183        ),
184    ]);
185
186    // 7. Encrypt the data for encryption_context using keyring1
187    let plaintext = example_data.as_bytes();
188
189    let encryption_response1 = esdk_client
190        .encrypt()
191        .plaintext(plaintext)
192        .keyring(keyring1.clone())
193        .encryption_context(encryption_context.clone())
194        .send()
195        .await?;
196
197    let ciphertext1 = encryption_response1
198        .ciphertext
199        .expect("Unable to unwrap ciphertext from encryption response");
200
201    // 8. Demonstrate that the ciphertexts and plaintext are different.
202    // (This is an example for demonstration; you do not need to do this in your own code.)
203    assert_ne!(
204        ciphertext1,
205        aws_smithy_types::Blob::new(plaintext),
206        "Ciphertext and plaintext data are the same. Invalid encryption"
207    );
208
209    // 9. Decrypt your encrypted data using the same keyring HK1 you used on encrypt.
210    let decryption_response1 = esdk_client
211        .decrypt()
212        .ciphertext(ciphertext1)
213        .keyring(keyring1)
214        // Provide the encryption context that was supplied to the encrypt method
215        .encryption_context(encryption_context.clone())
216        .send()
217        .await?;
218
219    let decrypted_plaintext1 = decryption_response1
220        .plaintext
221        .expect("Unable to unwrap plaintext from decryption response");
222
223    // 10. Demonstrate that the decrypted plaintext is identical to the original plaintext.
224    // (This is an example for demonstration; you do not need to do this in your own code.)
225    assert_eq!(
226        decrypted_plaintext1,
227        aws_smithy_types::Blob::new(plaintext),
228        "Decrypted plaintext should be identical to the original plaintext. Invalid decryption"
229    );
230
231    // 11. Through the above encrypt and decrypt roundtrip, the cache will be populated and
232    // the cache entries can be used by another Hierarchical Keyring with the
233    // - Same Partition ID
234    // - Same Logical Key Store Name of the Key Store for the Hierarchical Keyring
235    // - Same Branch Key ID
236
237    // Configure your Key Store resource key_store2.
238    //    This SHOULD be the same configuration that you used
239    //    to initially create and populate your physical Key Store.
240    // Note that key_store_table_name is the physical Key Store,
241    // and key_store2 is instances of this physical Key Store.
242
243    // Note that for this example, key_store2 is identical to key_store1.
244    // You can optionally change configurations like KMS Client or KMS Key ID based
245    // on your use-case.
246    // Make sure you have the required permissions to use different configurations.
247
248    // - If you want to share cache entries across two keyrings HK1 and HK2,
249    //   you should set the Logical Key Store Names for both
250    //   Key Store instances (K1 and K2) to be the same.
251    // - If you set the Logical Key Store Names for K1 and K2 to be different,
252    //   HK1 (which uses Key Store instance K1) and HK2 (which uses Key Store
253    //   instance K2) will NOT be able to share cache entries.
254    let key_store2 = keystore_client::Client::from_conf(key_store_config.clone())?;
255
256    // 12. Create the Hierarchical Keyring HK2 with Key Store instance K2, the shared_cache
257    // and the same partition_id and branch_key_id used in HK1 because we want to share cache entries
258    // (and experience cache HITS).
259
260    // Please make sure that you read the guidance on how to set Partition ID, Logical Key Store Name and
261    // Branch Key ID at the top of this example before creating Hierarchical Keyrings with a Shared Cache
262    let keyring2 = mpl
263        .create_aws_kms_hierarchical_keyring()
264        .key_store(key_store2)
265        .branch_key_id(branch_key_id)
266        .cache(shared_cache)
267        .ttl_seconds(600)
268        .partition_id(partition_id)
269        .send()
270        .await?;
271
272    // 13. This encrypt-decrypt roundtrip with HK2 will experience Cache HITS from previous HK1 roundtrip
273    // Encrypt the data for encryption_context using keyring2
274    let encryption_response2 = esdk_client
275        .encrypt()
276        .plaintext(plaintext)
277        .keyring(keyring2.clone())
278        .encryption_context(encryption_context.clone())
279        .send()
280        .await?;
281
282    let ciphertext2 = encryption_response2
283        .ciphertext
284        .expect("Unable to unwrap ciphertext from encryption response");
285
286    // 14. Demonstrate that the ciphertexts and plaintext are different.
287    // (This is an example for demonstration; you do not need to do this in your own code.)
288    assert_ne!(
289        ciphertext2,
290        aws_smithy_types::Blob::new(plaintext),
291        "Ciphertext and plaintext data are the same. Invalid encryption"
292    );
293
294    // 15. Decrypt your encrypted data using the same keyring HK2 you used on encrypt.
295    let decryption_response2 = esdk_client
296        .decrypt()
297        .ciphertext(ciphertext2)
298        .keyring(keyring2)
299        // Provide the encryption context that was supplied to the encrypt method
300        .encryption_context(encryption_context)
301        .send()
302        .await?;
303
304    let decrypted_plaintext2 = decryption_response2
305        .plaintext
306        .expect("Unable to unwrap plaintext from decryption response");
307
308    // 10. Demonstrate that the decrypted plaintext is identical to the original plaintext.
309    // (This is an example for demonstration; you do not need to do this in your own code.)
310    assert_eq!(
311        decrypted_plaintext2,
312        aws_smithy_types::Blob::new(plaintext),
313        "Decrypted plaintext should be identical to the original plaintext. Invalid decryption"
314    );
315
316    println!("Shared Cache Across Hierarchical Keyrings Example Completed Successfully");
317
318    Ok(())
319}
Source§

impl Client

Source

pub fn create_aws_kms_rsa_keyring(&self) -> CreateAwsKmsRsaKeyringFluentBuilder

Examples found in repository?
examples/keyring/aws_kms_rsa_keyring_example.rs (line 70)
28pub async fn encrypt_and_decrypt_with_keyring(
29    example_data: &str,
30    kms_rsa_key_id: &str,
31    kms_rsa_public_key: &str,
32) -> Result<(), crate::BoxError> {
33    // 1. Instantiate the encryption SDK client.
34    // This builds the default client with the RequireEncryptRequireDecrypt commitment policy,
35    // which enforces that this client only encrypts using committing algorithm suites and enforces
36    // that this client will only decrypt encrypted messages that were created with a committing
37    // algorithm suite.
38    let esdk_config = AwsEncryptionSdkConfig::builder().build()?;
39    let esdk_client = esdk_client::Client::from_conf(esdk_config)?;
40
41    // 2. Create a KMS client.
42    let sdk_config = aws_config::load_defaults(aws_config::BehaviorVersion::latest()).await;
43    let kms_client = aws_sdk_kms::Client::new(&sdk_config);
44
45    // 3. Create encryption context.
46    // Remember that your encryption context is NOT SECRET.
47    // For more information, see
48    // https://docs.aws.amazon.com/encryption-sdk/latest/developer-guide/concepts.html#encryption-context
49    let encryption_context = HashMap::from([
50        ("encryption".to_string(), "context".to_string()),
51        ("is not".to_string(), "secret".to_string()),
52        ("but adds".to_string(), "useful metadata".to_string()),
53        (
54            "that can help you".to_string(),
55            "be confident that".to_string(),
56        ),
57        (
58            "the data you are handling".to_string(),
59            "is what you think it is".to_string(),
60        ),
61    ]);
62
63    // 4. Create a KMS RSA keyring
64    let mpl_config = MaterialProvidersConfig::builder().build()?;
65    let mpl = mpl_client::Client::from_conf(mpl_config)?;
66
67    // For more information on the allowed encryption algorithms, please see
68    // https://docs.aws.amazon.com/kms/latest/developerguide/asymmetric-key-specs.html#key-spec-rsa
69    let kms_rsa_keyring = mpl
70        .create_aws_kms_rsa_keyring()
71        .kms_key_id(kms_rsa_key_id)
72        .public_key(aws_smithy_types::Blob::new(kms_rsa_public_key))
73        .encryption_algorithm(aws_sdk_kms::types::EncryptionAlgorithmSpec::RsaesOaepSha256)
74        .kms_client(kms_client)
75        .send()
76        .await?;
77
78    // 5. Encrypt the data with the encryption_context
79    let plaintext = example_data.as_bytes();
80
81    let encryption_response = esdk_client
82        .encrypt()
83        .plaintext(plaintext)
84        .keyring(kms_rsa_keyring.clone())
85        .encryption_context(encryption_context.clone())
86        .algorithm_suite_id(EsdkAlgorithmSuiteId::AlgAes256GcmHkdfSha512CommitKey)
87        .send()
88        .await?;
89
90    let ciphertext = encryption_response
91        .ciphertext
92        .expect("Unable to unwrap ciphertext from encryption response");
93
94    // 6. Demonstrate that the ciphertext and plaintext are different.
95    // (This is an example for demonstration; you do not need to do this in your own code.)
96    assert_ne!(
97        ciphertext,
98        aws_smithy_types::Blob::new(plaintext),
99        "Ciphertext and plaintext data are the same. Invalid encryption"
100    );
101
102    // 7. Decrypt your encrypted data using the same keyring you used on encrypt.
103    let decryption_response = esdk_client
104        .decrypt()
105        .ciphertext(ciphertext)
106        .keyring(kms_rsa_keyring)
107        // Provide the encryption context that was supplied to the encrypt method
108        .encryption_context(encryption_context)
109        .send()
110        .await?;
111
112    let decrypted_plaintext = decryption_response
113        .plaintext
114        .expect("Unable to unwrap plaintext from decryption response");
115
116    // 8. Demonstrate that the decrypted plaintext is identical to the original plaintext.
117    // (This is an example for demonstration; you do not need to do this in your own code.)
118    assert_eq!(
119        decrypted_plaintext,
120        aws_smithy_types::Blob::new(plaintext),
121        "Decrypted plaintext should be identical to the original plaintext. Invalid decryption"
122    );
123
124    println!("KMS RSA Keyring Example Completed Successfully");
125
126    Ok(())
127}
Source§

impl Client

Source

pub fn create_aws_kms_ecdh_keyring( &self, ) -> CreateAwsKmsEcdhKeyringFluentBuilder

Examples found in repository?
examples/keyring/ecdh/kms_ecdh_discovery_keyring_example.rs (line 104)
43pub async fn decrypt_with_keyring(
44    example_data: &str,
45    ecdh_curve_spec: EcdhCurveSpec,
46    ecc_recipient_key_arn: &str,
47) -> Result<(), crate::BoxError> {
48    // 1. Instantiate the encryption SDK client.
49    // This builds the default client with the RequireEncryptRequireDecrypt commitment policy,
50    // which enforces that this client only encrypts using committing algorithm suites and enforces
51    // that this client will only decrypt encrypted messages that were created with a committing
52    // algorithm suite.
53    let esdk_config = AwsEncryptionSdkConfig::builder().build()?;
54    let esdk_client = esdk_client::Client::from_conf(esdk_config)?;
55
56    // 2. Create a KMS client.
57    let sdk_config = aws_config::load_defaults(aws_config::BehaviorVersion::latest()).await;
58    let kms_client = aws_sdk_kms::Client::new(&sdk_config);
59
60    // 3. Create encryption context.
61    // Remember that your encryption context is NOT SECRET.
62    // For more information, see
63    // https://docs.aws.amazon.com/encryption-sdk/latest/developer-guide/concepts.html#encryption-context
64    let encryption_context = HashMap::from([
65        ("encryption".to_string(), "context".to_string()),
66        ("is not".to_string(), "secret".to_string()),
67        ("but adds".to_string(), "useful metadata".to_string()),
68        (
69            "that can help you".to_string(),
70            "be confident that".to_string(),
71        ),
72        (
73            "the data you are handling".to_string(),
74            "is what you think it is".to_string(),
75        ),
76    ]);
77
78    // 4. Create the KmsPublicKeyDiscoveryInput
79    let kms_ecdh_discovery_static_configuration_input = KmsPublicKeyDiscoveryInput::builder()
80        .recipient_kms_identifier(ecc_recipient_key_arn)
81        .build()?;
82
83    let kms_ecdh_discovery_static_configuration =
84        KmsEcdhStaticConfigurations::KmsPublicKeyDiscovery(
85            kms_ecdh_discovery_static_configuration_input,
86        );
87
88    // 5. Create the KMS ECDH keyring.
89    let mpl_config = MaterialProvidersConfig::builder().build()?;
90    let mpl = mpl_client::Client::from_conf(mpl_config)?;
91
92    // Create a KMS ECDH Discovery keyring.
93    // This keyring uses the KmsPublicKeyDiscovery configuration.
94    // On encrypt, the keyring will fail as it is not allowed to encrypt data under this configuration.
95    // On decrypt, the keyring will check if its corresponding public key is stored in the message header. It
96    // will AWS KMS to derive the shared from the recipient's KMS ECC Key ARN and the sender's public key;
97    // For more information on this configuration see:
98    // https://docs.aws.amazon.com/encryption-sdk/latest/developer-guide/use-kms-ecdh-keyring.html#kms-ecdh-discovery
99    // This keyring takes in:
100    //  - kmsClient
101    //  - recipientKmsIdentifier: Must be an ARN representing a KMS ECC key meant for KeyAgreement
102    //  - curveSpec: The curve name where the public keys lie
103    let kms_ecdh_discovery_keyring = mpl
104        .create_aws_kms_ecdh_keyring()
105        .kms_client(kms_client.clone())
106        .curve_spec(ecdh_curve_spec)
107        .key_agreement_scheme(kms_ecdh_discovery_static_configuration)
108        .send()
109        .await?;
110
111    // 6. Get ciphertext by creating a KMS ECDH keyring WITHOUT discovery
112    // because the KMS ECDH keyring WITH discovery CANNOT encrypt data.
113    let plaintext = example_data.as_bytes();
114
115    // Get ciphertext by creating a KMS ECDH keyring WITHOUT discovery.
116    // The recipient's public key used in the encrypting KMS ECDH keyring WITHOUT discovery
117    // is a public key generated from ecc_recipient_key_arn, the same ecc key used
118    // when creating the KMS ECDH keyring WITH discovery used for decryption in this example.
119    // We then decrypt this ciphertext using a KMS ECDH keyring WITH discovery
120    let ciphertext = get_ciphertext(
121        example_data,
122        encryption_context.clone(),
123        ecc_recipient_key_arn,
124        ecdh_curve_spec,
125        kms_client,
126        esdk_client.clone(),
127    )
128    .await?;
129
130    // 7. Decrypt your encrypted data using the same keyring you used on encrypt.
131    let decryption_response = esdk_client
132        .decrypt()
133        .ciphertext(ciphertext)
134        .keyring(kms_ecdh_discovery_keyring)
135        // Provide the encryption context that was supplied to the encrypt method
136        .encryption_context(encryption_context)
137        .send()
138        .await?;
139
140    let decrypted_plaintext = decryption_response
141        .plaintext
142        .expect("Unable to unwrap plaintext from decryption response");
143
144    // 8. Demonstrate that the decrypted plaintext is identical to the original plaintext.
145    // (This is an example for demonstration; you do not need to do this in your own code.)
146    assert_eq!(
147        decrypted_plaintext,
148        aws_smithy_types::Blob::new(plaintext),
149        "Decrypted plaintext should be identical to the original plaintext. Invalid decryption"
150    );
151
152    println!("KMS ECDH Discovery Keyring Example Completed Successfully");
153
154    Ok(())
155}
156
157async fn get_ciphertext(
158    example_data: &str,
159    encryption_context: HashMap<String, String>,
160    ecc_recipient_key_arn: &str,
161    ecdh_curve_spec: EcdhCurveSpec,
162    kms_client: aws_sdk_kms::Client,
163    esdk_client: esdk_client::Client,
164) -> Result<Blob, crate::BoxError> {
165    // 1. Create the public keys for sender and recipient
166    // Recipient keys are taken as input for this example
167    // Sender ECC key used in this example is TEST_KMS_ECDH_KEY_ID_P256_SENDER
168    let public_key_sender_utf8_bytes =
169        generate_kms_ecc_public_key(TEST_KMS_ECDH_KEY_ID_P256_SENDER).await?;
170    let public_key_recipient_utf8_bytes =
171        generate_kms_ecc_public_key(ecc_recipient_key_arn).await?;
172
173    // 2. Create the KmsPrivateKeyToStaticPublicKeyInput
174    let kms_ecdh_static_configuration_input = KmsPrivateKeyToStaticPublicKeyInput::builder()
175        .sender_kms_identifier(TEST_KMS_ECDH_KEY_ID_P256_SENDER)
176        // Must be a UTF8 DER-encoded X.509 public key
177        .sender_public_key(public_key_sender_utf8_bytes)
178        // Must be a UTF8 DER-encoded X.509 public key
179        .recipient_public_key(public_key_recipient_utf8_bytes)
180        .build()?;
181
182    let kms_ecdh_static_configuration = KmsEcdhStaticConfigurations::KmsPrivateKeyToStaticPublicKey(
183        kms_ecdh_static_configuration_input,
184    );
185
186    // 3. Create the KMS ECDH keyring.
187    let mpl_config = MaterialProvidersConfig::builder().build()?;
188    let mpl = mpl_client::Client::from_conf(mpl_config)?;
189
190    let kms_ecdh_keyring = mpl
191        .create_aws_kms_ecdh_keyring()
192        .kms_client(kms_client)
193        .curve_spec(ecdh_curve_spec)
194        .key_agreement_scheme(kms_ecdh_static_configuration)
195        .send()
196        .await?;
197
198    // 4. Encrypt the data with the encryption_context
199    let plaintext = example_data.as_bytes();
200
201    let encryption_response = esdk_client
202        .encrypt()
203        .plaintext(plaintext)
204        .keyring(kms_ecdh_keyring.clone())
205        .encryption_context(encryption_context.clone())
206        .send()
207        .await?;
208
209    let ciphertext = encryption_response
210        .ciphertext
211        .expect("Unable to unwrap ciphertext from encryption response");
212
213    // 5. Demonstrate that the ciphertext and plaintext are different.
214    // (This is an example for demonstration; you do not need to do this in your own code.)
215    assert_ne!(
216        ciphertext,
217        aws_smithy_types::Blob::new(plaintext),
218        "Ciphertext and plaintext data are the same. Invalid encryption"
219    );
220
221    Ok(ciphertext)
222}
More examples
Hide additional examples
examples/keyring/ecdh/kms_ecdh_keyring_example.rs (line 165)
59pub async fn encrypt_and_decrypt_with_keyring(
60    example_data: &str,
61    ecc_key_arn: &str,
62    ecdh_curve_spec: EcdhCurveSpec,
63    ecc_recipient_key_arn: Option<&str>,
64) -> Result<(), crate::BoxError> {
65    // 1. If ecc_recipient_key_arn is not provided, set the private key for the recipient to TEST_KMS_ECDH_KEY_ID_P256_RECIPIENT
66    let ecc_recipient_key_arn = ecc_recipient_key_arn
67        .unwrap_or(crate::example_utils::utils::TEST_KMS_ECDH_KEY_ID_P256_RECIPIENT);
68
69    // 2. Instantiate the encryption SDK client.
70    // This builds the default client with the RequireEncryptRequireDecrypt commitment policy,
71    // which enforces that this client only encrypts using committing algorithm suites and enforces
72    // that this client will only decrypt encrypted messages that were created with a committing
73    // algorithm suite.
74    let esdk_config = AwsEncryptionSdkConfig::builder().build()?;
75    let esdk_client = esdk_client::Client::from_conf(esdk_config)?;
76
77    // 3. Create a KMS client.
78    let sdk_config = aws_config::load_defaults(aws_config::BehaviorVersion::latest()).await;
79    let kms_client = aws_sdk_kms::Client::new(&sdk_config);
80
81    // 4. Create encryption context.
82    // Remember that your encryption context is NOT SECRET.
83    // For more information, see
84    // https://docs.aws.amazon.com/encryption-sdk/latest/developer-guide/concepts.html#encryption-context
85    let encryption_context = HashMap::from([
86        ("encryption".to_string(), "context".to_string()),
87        ("is not".to_string(), "secret".to_string()),
88        ("but adds".to_string(), "useful metadata".to_string()),
89        (
90            "that can help you".to_string(),
91            "be confident that".to_string(),
92        ),
93        (
94            "the data you are handling".to_string(),
95            "is what you think it is".to_string(),
96        ),
97    ]);
98
99    // 5. You may provide your own ECC keys in the files located at
100    // - EXAMPLE_KMS_ECC_PUBLIC_KEY_FILENAME_SENDER
101    // - EXAMPLE_KMS_ECC_PUBLIC_KEY_FILENAME_RECIPIENT
102
103    // If not, the main method in this class will call
104    // the KMS ECC key, retrieve its public key, and store it
105    // in a PEM file for example use.
106    if should_generate_new_kms_ecc_public_key(EXAMPLE_KMS_ECC_PUBLIC_KEY_FILENAME_SENDER)? {
107        write_kms_ecdh_ecc_public_key(ecc_key_arn, EXAMPLE_KMS_ECC_PUBLIC_KEY_FILENAME_SENDER)
108            .await?;
109    }
110
111    if should_generate_new_kms_ecc_public_key(EXAMPLE_KMS_ECC_PUBLIC_KEY_FILENAME_RECIPIENT)? {
112        write_kms_ecdh_ecc_public_key(
113            ecc_recipient_key_arn,
114            EXAMPLE_KMS_ECC_PUBLIC_KEY_FILENAME_RECIPIENT,
115        )
116        .await?;
117    }
118
119    // 6. Load public key from UTF-8 encoded PEM files into a DER encoded public key.
120    let public_key_file_content_sender =
121        std::fs::read_to_string(Path::new(EXAMPLE_KMS_ECC_PUBLIC_KEY_FILENAME_SENDER))?;
122    let parsed_public_key_file_content_sender = parse(public_key_file_content_sender)?;
123    let public_key_sender_utf8_bytes = parsed_public_key_file_content_sender.contents();
124
125    let public_key_file_content_recipient =
126        std::fs::read_to_string(Path::new(EXAMPLE_KMS_ECC_PUBLIC_KEY_FILENAME_RECIPIENT))?;
127    let parsed_public_key_file_content_recipient = parse(public_key_file_content_recipient)?;
128    let public_key_recipient_utf8_bytes = parsed_public_key_file_content_recipient.contents();
129
130    // 7. Create the KmsPrivateKeyToStaticPublicKeyInput
131    let kms_ecdh_static_configuration_input = KmsPrivateKeyToStaticPublicKeyInput::builder()
132        .sender_kms_identifier(ecc_key_arn)
133        // Must be a UTF8 DER-encoded X.509 public key
134        .sender_public_key(public_key_sender_utf8_bytes)
135        // Must be a UTF8 DER-encoded X.509 public key
136        .recipient_public_key(public_key_recipient_utf8_bytes)
137        .build()?;
138
139    let kms_ecdh_static_configuration = KmsEcdhStaticConfigurations::KmsPrivateKeyToStaticPublicKey(
140        kms_ecdh_static_configuration_input,
141    );
142
143    // 8. Create the KMS ECDH keyring.
144    let mpl_config = MaterialProvidersConfig::builder().build()?;
145    let mpl = mpl_client::Client::from_conf(mpl_config)?;
146
147    // Create a KMS ECDH keyring.
148    // This keyring uses the KmsPrivateKeyToStaticPublicKey configuration. This configuration calls for both of
149    // the keys to be on the same curve (P256, P384, P521).
150    // On encrypt, the keyring calls AWS KMS to derive the shared secret from the sender's KMS ECC Key ARN and the recipient's public key.
151    // For this example, on decrypt, the keyring calls AWS KMS to derive the shared secret from the sender's KMS ECC Key ARN and the recipient's public key;
152    // however, on decrypt, the recipient can construct a keyring such that the shared secret is calculated with
153    // the recipient's private key and the sender's public key. In both scenarios the shared secret will be the same.
154    // For more information on this configuration see:
155    // https://docs.aws.amazon.com/encryption-sdk/latest/developer-guide/use-kms-ecdh-keyring.html#kms-ecdh-create
156    // This keyring takes in:
157    //  - kmsClient
158    //  - kmsKeyId: Must be an ARN representing a KMS ECC key meant for KeyAgreement
159    //  - curveSpec: The curve name where the public keys lie
160    //  - senderPublicKey: A ByteBuffer of a UTF-8 encoded public
161    //               key for the key passed into kmsKeyId in DER format
162    //  - recipientPublicKey: A ByteBuffer of a UTF-8 encoded public
163    //               key for the key passed into kmsKeyId in DER format
164    let kms_ecdh_keyring = mpl
165        .create_aws_kms_ecdh_keyring()
166        .kms_client(kms_client)
167        .curve_spec(ecdh_curve_spec)
168        .key_agreement_scheme(kms_ecdh_static_configuration)
169        .send()
170        .await?;
171
172    // 9. Encrypt the data with the encryption_context
173    let plaintext = example_data.as_bytes();
174
175    let encryption_response = esdk_client
176        .encrypt()
177        .plaintext(plaintext)
178        .keyring(kms_ecdh_keyring.clone())
179        .encryption_context(encryption_context.clone())
180        .send()
181        .await?;
182
183    let ciphertext = encryption_response
184        .ciphertext
185        .expect("Unable to unwrap ciphertext from encryption response");
186
187    // 10. Demonstrate that the ciphertext and plaintext are different.
188    // (This is an example for demonstration; you do not need to do this in your own code.)
189    assert_ne!(
190        ciphertext,
191        aws_smithy_types::Blob::new(plaintext),
192        "Ciphertext and plaintext data are the same. Invalid encryption"
193    );
194
195    // 11. Decrypt your encrypted data using the same keyring you used on encrypt.
196    let decryption_response = esdk_client
197        .decrypt()
198        .ciphertext(ciphertext)
199        .keyring(kms_ecdh_keyring)
200        // Provide the encryption context that was supplied to the encrypt method
201        .encryption_context(encryption_context)
202        .send()
203        .await?;
204
205    let decrypted_plaintext = decryption_response
206        .plaintext
207        .expect("Unable to unwrap plaintext from decryption response");
208
209    // 12. Demonstrate that the decrypted plaintext is identical to the original plaintext.
210    // (This is an example for demonstration; you do not need to do this in your own code.)
211    assert_eq!(
212        decrypted_plaintext,
213        aws_smithy_types::Blob::new(plaintext),
214        "Decrypted plaintext should be identical to the original plaintext. Invalid decryption"
215    );
216
217    println!("KMS ECDH Keyring Example Completed Successfully");
218
219    Ok(())
220}
Source§

impl Client

Source

pub fn create_multi_keyring(&self) -> CreateMultiKeyringFluentBuilder

Examples found in repository?
examples/limit_encrypted_data_keys_example.rs (line 103)
29pub async fn encrypt_and_decrypt_with_keyring(
30    example_data: &str,
31    max_encrypted_data_keys: u16,
32) -> Result<(), crate::BoxError> {
33    // 1. Instantiate the encryption SDK client.
34    // This builds the default client with the RequireEncryptRequireDecrypt commitment policy,
35    // which enforces that this client only encrypts using committing algorithm suites and enforces
36    // that this client will only decrypt encrypted messages that were created with a committing
37    // algorithm suite.
38    // Also, set the EncryptionSDK's max_encrypted_data_keys parameter here
39    let esdk_config = AwsEncryptionSdkConfig::builder()
40        .max_encrypted_data_keys(max_encrypted_data_keys)
41        .build()?;
42    let esdk_client = esdk_client::Client::from_conf(esdk_config)?;
43
44    // 2. The key namespace and key name are defined by you.
45    // and are used by the Raw AES keyring to determine
46    // whether it should attempt to decrypt an encrypted data key.
47    // For more information, see
48    // https://docs.aws.amazon.com/encryption-sdk/latest/developer-guide/use-raw-aes-keyring.html
49    let key_namespace: &str = "my-key-namespace";
50    let key_name: &str = "my-aes-key-name";
51
52    // 3. Create encryption context.
53    // Remember that your encryption context is NOT SECRET.
54    // For more information, see
55    // https://docs.aws.amazon.com/encryption-sdk/latest/developer-guide/concepts.html#encryption-context
56    let encryption_context = HashMap::from([
57        ("encryption".to_string(), "context".to_string()),
58        ("is not".to_string(), "secret".to_string()),
59        ("but adds".to_string(), "useful metadata".to_string()),
60        (
61            "that can help you".to_string(),
62            "be confident that".to_string(),
63        ),
64        (
65            "the data you are handling".to_string(),
66            "is what you think it is".to_string(),
67        ),
68    ]);
69
70    // 4. Generate `max_encrypted_data_keys` AES keyrings to use with your keyring.
71    // In practice, you should get this key from a secure key management system such as an HSM.
72    let mpl_config = MaterialProvidersConfig::builder().build()?;
73    let mpl = mpl_client::Client::from_conf(mpl_config)?;
74
75    let mut raw_aes_keyrings: Vec<KeyringRef> = vec![];
76
77    assert!(
78        max_encrypted_data_keys > 0,
79        "max_encrypted_data_keys MUST be greater than 0"
80    );
81
82    let mut i = 0;
83    while i < max_encrypted_data_keys {
84        let aes_key_bytes = generate_aes_key_bytes();
85
86        let raw_aes_keyring = mpl
87            .create_raw_aes_keyring()
88            .key_name(key_name)
89            .key_namespace(key_namespace)
90            .wrapping_key(aes_key_bytes)
91            .wrapping_alg(AesWrappingAlg::AlgAes256GcmIv12Tag16)
92            .send()
93            .await?;
94
95        raw_aes_keyrings.push(raw_aes_keyring);
96        i += 1;
97    }
98
99    // 5. Create a Multi Keyring with `max_encrypted_data_keys` AES Keyrings
100    let generator_keyring = raw_aes_keyrings.remove(0);
101
102    let multi_keyring = mpl
103        .create_multi_keyring()
104        .generator(generator_keyring)
105        .child_keyrings(raw_aes_keyrings)
106        .send()
107        .await?;
108
109    // 6. Encrypt the data with the encryption_context
110    let plaintext = example_data.as_bytes();
111
112    let encryption_response = esdk_client
113        .encrypt()
114        .plaintext(plaintext)
115        .keyring(multi_keyring.clone())
116        .encryption_context(encryption_context.clone())
117        .send()
118        .await?;
119
120    let ciphertext = encryption_response
121        .ciphertext
122        .expect("Unable to unwrap ciphertext from encryption response");
123
124    // 7. Demonstrate that the ciphertext and plaintext are different.
125    // (This is an example for demonstration; you do not need to do this in your own code.)
126    assert_ne!(
127        ciphertext,
128        aws_smithy_types::Blob::new(plaintext),
129        "Ciphertext and plaintext data are the same. Invalid encryption"
130    );
131
132    // 8. Decrypt your encrypted data using the same keyring you used on encrypt.
133    let decryption_response = esdk_client
134        .decrypt()
135        .ciphertext(ciphertext.clone())
136        .keyring(multi_keyring.clone())
137        // Provide the encryption context that was supplied to the encrypt method
138        .encryption_context(encryption_context.clone())
139        .send()
140        .await?;
141
142    let decrypted_plaintext = decryption_response
143        .plaintext
144        .expect("Unable to unwrap plaintext from decryption response");
145
146    // 9. Demonstrate that the decrypted plaintext is identical to the original plaintext.
147    // (This is an example for demonstration; you do not need to do this in your own code.)
148    assert_eq!(
149        decrypted_plaintext,
150        aws_smithy_types::Blob::new(plaintext),
151        "Decrypted plaintext should be identical to the original plaintext. Invalid decryption"
152    );
153
154    // 10. Demonstrate that an EncryptionSDK with a lower MaxEncryptedDataKeys
155    // will fail to decrypt the encrypted message.
156    let esdk_config = AwsEncryptionSdkConfig::builder()
157        .max_encrypted_data_keys(max_encrypted_data_keys - 1)
158        .build()?;
159    let esdk_client_incorrect_max_encrypted_keys = esdk_client::Client::from_conf(esdk_config)?;
160
161    let decryption_response_incorrect_max_encrypted_keys = esdk_client_incorrect_max_encrypted_keys
162        .decrypt()
163        .ciphertext(ciphertext)
164        .keyring(multi_keyring)
165        // Provide the encryption context that was supplied to the encrypt method
166        .encryption_context(encryption_context)
167        .send()
168        .await;
169
170    match decryption_response_incorrect_max_encrypted_keys {
171        Ok(_) => panic!(
172            "Decrypt using discovery keyring with wrong AWS Account ID MUST \
173                            raise AwsCryptographicMaterialProvidersError"
174        ),
175        Err(AwsEncryptionSdkException { message: m }) => assert_eq!(
176            m,
177            "Ciphertext encrypted data keys exceed maxEncryptedDataKeys"
178        ),
179        _ => panic!("Unexpected error type"),
180    }
181
182    println!("Limit Encrypted Data Keys Example Completed Successfully");
183
184    Ok(())
185}
More examples
Hide additional examples
examples/keyring/multi_keyring_example.rs (line 124)
52pub async fn encrypt_and_decrypt_with_keyring(
53    example_data: &str,
54    kms_key_id: &str,
55) -> Result<(), crate::BoxError> {
56    // 1. Instantiate the encryption SDK client.
57    // This builds the default client with the RequireEncryptRequireDecrypt commitment policy,
58    // which enforces that this client only encrypts using committing algorithm suites and enforces
59    // that this client will only decrypt encrypted messages that were created with a committing
60    // algorithm suite.
61    let esdk_config = AwsEncryptionSdkConfig::builder().build()?;
62    let esdk_client = esdk_client::Client::from_conf(esdk_config)?;
63
64    // 2. Create a KMS client.
65    let sdk_config = aws_config::load_defaults(aws_config::BehaviorVersion::latest()).await;
66    let kms_client = aws_sdk_kms::Client::new(&sdk_config);
67
68    // 3. Create encryption context.
69    // Remember that your encryption context is NOT SECRET.
70    // For more information, see
71    // https://docs.aws.amazon.com/encryption-sdk/latest/developer-guide/concepts.html#encryption-context
72    let encryption_context = HashMap::from([
73        ("encryption".to_string(), "context".to_string()),
74        ("is not".to_string(), "secret".to_string()),
75        ("but adds".to_string(), "useful metadata".to_string()),
76        (
77            "that can help you".to_string(),
78            "be confident that".to_string(),
79        ),
80        (
81            "the data you are handling".to_string(),
82            "is what you think it is".to_string(),
83        ),
84    ]);
85
86    // 4. Create a KMS keyring
87    let mpl_config = MaterialProvidersConfig::builder().build()?;
88    let mpl = mpl_client::Client::from_conf(mpl_config)?;
89
90    let kms_keyring = mpl
91        .create_aws_kms_keyring()
92        .kms_key_id(kms_key_id)
93        .kms_client(kms_client)
94        .send()
95        .await?;
96
97    // 5. Create a raw AES keyring to additionally encrypt under as child_keyring
98
99    // The key namespace and key name are defined by you.
100    // and are used by the Raw AES keyring to determine
101    // whether it should attempt to decrypt an encrypted data key.
102    // For more information, see
103    // https://docs.aws.amazon.com/encryption-sdk/latest/developer-guide/use-raw-aes-keyring.html
104    let key_namespace: &str = "my-key-namespace";
105    let key_name: &str = "my-aes-key-name";
106
107    // Generate a 256-bit AES key to use with your raw AES keyring.
108    // In practice, you should get this key from a secure key management system such as an HSM.
109    let aes_key_bytes = generate_aes_key_bytes();
110
111    let raw_aes_keyring = mpl
112        .create_raw_aes_keyring()
113        .key_name(key_name)
114        .key_namespace(key_namespace)
115        .wrapping_key(aes_key_bytes)
116        .wrapping_alg(AesWrappingAlg::AlgAes256GcmIv12Tag16)
117        .send()
118        .await?;
119
120    // 6. Create a multi_keyring that consists of the previously created keyrings.
121    // When using this multi_keyring to encrypt data, either `kms_keyring` or
122    // `raw_aes_keyring` (or a multi_keyring containing either) may be used to decrypt the data.
123    let multi_keyring = mpl
124        .create_multi_keyring()
125        .generator(kms_keyring.clone())
126        .child_keyrings(vec![raw_aes_keyring.clone()])
127        .send()
128        .await?;
129
130    // 7. Encrypt the data with the encryption_context
131    let plaintext = example_data.as_bytes();
132
133    let encryption_response = esdk_client
134        .encrypt()
135        .plaintext(plaintext)
136        .keyring(multi_keyring.clone())
137        .encryption_context(encryption_context.clone())
138        .send()
139        .await?;
140
141    let ciphertext = encryption_response
142        .ciphertext
143        .expect("Unable to unwrap ciphertext from encryption response");
144
145    // 8. Demonstrate that the ciphertext and plaintext are different.
146    // (This is an example for demonstration; you do not need to do this in your own code.)
147    assert_ne!(
148        ciphertext,
149        aws_smithy_types::Blob::new(plaintext),
150        "Ciphertext and plaintext data are the same. Invalid encryption"
151    );
152
153    // 9a. Decrypt your encrypted data using the same multi_keyring you used on encrypt.
154    let decryption_response_multi_keyring = esdk_client
155        .decrypt()
156        .ciphertext(ciphertext.clone())
157        .keyring(multi_keyring)
158        // Provide the encryption context that was supplied to the encrypt method
159        .encryption_context(encryption_context.clone())
160        .send()
161        .await?;
162
163    let decrypted_plaintext_multi_keyring = decryption_response_multi_keyring
164        .plaintext
165        .expect("Unable to unwrap plaintext from decryption response");
166
167    // 9b. Demonstrate that the decrypted plaintext is identical to the original plaintext.
168    // (This is an example for demonstration; you do not need to do this in your own code.)
169    assert_eq!(
170        decrypted_plaintext_multi_keyring,
171        aws_smithy_types::Blob::new(plaintext),
172        "Decrypted plaintext should be identical to the original plaintext. Invalid decryption"
173    );
174
175    // Because you used a multi_keyring on Encrypt, you can use either the
176    // `kms_keyring` or `raw_aes_keyring` individually to decrypt the data.
177
178    // 10. Demonstrate that you can successfully decrypt data using just the `kms_keyring`
179    // directly.
180    // (This is an example for demonstration; you do not need to do this in your own code.)
181
182    // 10a. Decrypt your encrypted data using the kms_keyring.
183    let decryption_response_kms_keyring = esdk_client
184        .decrypt()
185        .ciphertext(ciphertext.clone())
186        .keyring(kms_keyring)
187        // Provide the encryption context that was supplied to the encrypt method
188        .encryption_context(encryption_context.clone())
189        .send()
190        .await?;
191
192    let decrypted_plaintext_kms_keyring = decryption_response_kms_keyring
193        .plaintext
194        .expect("Unable to unwrap plaintext from decryption response");
195
196    // 10b. Demonstrate that the decrypted plaintext is identical to the original plaintext.
197    // (This is an example for demonstration; you do not need to do this in your own code.)
198    assert_eq!(
199        decrypted_plaintext_kms_keyring,
200        aws_smithy_types::Blob::new(plaintext),
201        "Decrypted plaintext should be identical to the original plaintext. Invalid decryption"
202    );
203
204    // 11. Demonstrate that you can also successfully decrypt data using the `raw_aes_keyring`
205    // directly.
206    // (This is an example for demonstration; you do not need to do this in your own code.)
207
208    // 11a. Decrypt your encrypted data using the raw_aes_keyring.
209    let decryption_response_raw_aes_keyring = esdk_client
210        .decrypt()
211        .ciphertext(ciphertext)
212        .keyring(raw_aes_keyring)
213        // Provide the encryption context that was supplied to the encrypt method
214        .encryption_context(encryption_context)
215        .send()
216        .await?;
217
218    let decrypted_plaintext_raw_aes_keyring = decryption_response_raw_aes_keyring
219        .plaintext
220        .expect("Unable to unwrap plaintext from decryption response");
221
222    // 11b. Demonstrate that the decrypted plaintext is identical to the original plaintext.
223    // (This is an example for demonstration; you do not need to do this in your own code.)
224    assert_eq!(
225        decrypted_plaintext_raw_aes_keyring,
226        aws_smithy_types::Blob::new(plaintext),
227        "Decrypted plaintext should be identical to the original plaintext. Invalid decryption"
228    );
229
230    println!("Multi Keyring Example Completed Successfully");
231
232    Ok(())
233}
Source§

impl Client

Source

pub fn create_raw_aes_keyring(&self) -> CreateRawAesKeyringFluentBuilder

Examples found in repository?
examples/keyring/raw_aes_keyring_example.rs (line 78)
34pub async fn encrypt_and_decrypt_with_keyring(example_data: &str) -> Result<(), crate::BoxError> {
35    // 1. Instantiate the encryption SDK client.
36    // This builds the default client with the RequireEncryptRequireDecrypt commitment policy,
37    // which enforces that this client only encrypts using committing algorithm suites and enforces
38    // that this client will only decrypt encrypted messages that were created with a committing
39    // algorithm suite.
40    let esdk_config = AwsEncryptionSdkConfig::builder().build()?;
41    let esdk_client = esdk_client::Client::from_conf(esdk_config)?;
42
43    // 2. The key namespace and key name are defined by you.
44    // and are used by the Raw AES keyring to determine
45    // whether it should attempt to decrypt an encrypted data key.
46    // For more information, see
47    // https://docs.aws.amazon.com/encryption-sdk/latest/developer-guide/use-raw-aes-keyring.html
48    let key_namespace: &str = "my-key-namespace";
49    let key_name: &str = "my-aes-key-name";
50
51    // 3. Create encryption context.
52    // Remember that your encryption context is NOT SECRET.
53    // For more information, see
54    // https://docs.aws.amazon.com/encryption-sdk/latest/developer-guide/concepts.html#encryption-context
55    let encryption_context = HashMap::from([
56        ("encryption".to_string(), "context".to_string()),
57        ("is not".to_string(), "secret".to_string()),
58        ("but adds".to_string(), "useful metadata".to_string()),
59        (
60            "that can help you".to_string(),
61            "be confident that".to_string(),
62        ),
63        (
64            "the data you are handling".to_string(),
65            "is what you think it is".to_string(),
66        ),
67    ]);
68
69    // 4. Generate a 256-bit AES key to use with your keyring.
70    // In practice, you should get this key from a secure key management system such as an HSM.
71    let aes_key_bytes = generate_aes_key_bytes();
72
73    // 5. Create a Raw AES Keyring
74    let mpl_config = MaterialProvidersConfig::builder().build()?;
75    let mpl = mpl_client::Client::from_conf(mpl_config)?;
76
77    let raw_aes_keyring = mpl
78        .create_raw_aes_keyring()
79        .key_name(key_name)
80        .key_namespace(key_namespace)
81        .wrapping_key(aes_key_bytes)
82        .wrapping_alg(AesWrappingAlg::AlgAes256GcmIv12Tag16)
83        .send()
84        .await?;
85
86    // 6. Encrypt the data with the encryption_context
87    let plaintext = example_data.as_bytes();
88
89    let encryption_response = esdk_client
90        .encrypt()
91        .plaintext(plaintext)
92        .keyring(raw_aes_keyring.clone())
93        .encryption_context(encryption_context.clone())
94        .send()
95        .await?;
96
97    let ciphertext = encryption_response
98        .ciphertext
99        .expect("Unable to unwrap ciphertext from encryption response");
100
101    // 7. Demonstrate that the ciphertext and plaintext are different.
102    // (This is an example for demonstration; you do not need to do this in your own code.)
103    assert_ne!(
104        ciphertext,
105        aws_smithy_types::Blob::new(plaintext),
106        "Ciphertext and plaintext data are the same. Invalid encryption"
107    );
108
109    // 8. Decrypt your encrypted data using the same keyring you used on encrypt.
110    let decryption_response = esdk_client
111        .decrypt()
112        .ciphertext(ciphertext)
113        .keyring(raw_aes_keyring)
114        // Provide the encryption context that was supplied to the encrypt method
115        .encryption_context(encryption_context)
116        .send()
117        .await?;
118
119    let decrypted_plaintext = decryption_response
120        .plaintext
121        .expect("Unable to unwrap plaintext from decryption response");
122
123    // 9. Demonstrate that the decrypted plaintext is identical to the original plaintext.
124    // (This is an example for demonstration; you do not need to do this in your own code.)
125    assert_eq!(
126        decrypted_plaintext,
127        aws_smithy_types::Blob::new(plaintext),
128        "Decrypted plaintext should be identical to the original plaintext. Invalid decryption"
129    );
130
131    println!("Raw AES Keyring Example Completed Successfully");
132
133    Ok(())
134}
More examples
Hide additional examples
examples/set_encryption_algorithm_suite_example.rs (line 96)
51pub async fn encrypt_and_decrypt_with_keyring(example_data: &str) -> Result<(), crate::BoxError> {
52    // 1. Instantiate the encryption SDK client.
53    // This builds the default client with the RequireEncryptRequireDecrypt commitment policy,
54    // which enforces that this client only encrypts using committing algorithm suites and enforces
55    // that this client will only decrypt encrypted messages that were created with a committing
56    // algorithm suite.
57    let esdk_config = AwsEncryptionSdkConfig::builder().build()?;
58    let esdk_client = esdk_client::Client::from_conf(esdk_config)?;
59
60    // 2. The key namespace and key name are defined by you.
61    // and are used by the Raw AES keyring to determine
62    // whether it should attempt to decrypt an encrypted data key.
63    // For more information, see
64    // https://docs.aws.amazon.com/encryption-sdk/latest/developer-guide/use-raw-aes-keyring.html
65    let key_namespace: &str = "my-key-namespace";
66    let key_name: &str = "my-aes-key-name";
67
68    // 3. Create encryption context.
69    // Remember that your encryption context is NOT SECRET.
70    // For more information, see
71    // https://docs.aws.amazon.com/encryption-sdk/latest/developer-guide/concepts.html#encryption-context
72    let encryption_context = HashMap::from([
73        ("encryption".to_string(), "context".to_string()),
74        ("is not".to_string(), "secret".to_string()),
75        ("but adds".to_string(), "useful metadata".to_string()),
76        (
77            "that can help you".to_string(),
78            "be confident that".to_string(),
79        ),
80        (
81            "the data you are handling".to_string(),
82            "is what you think it is".to_string(),
83        ),
84    ]);
85
86    // 4. Generate a 256-bit AES key to use with your keyring.
87    // In practice, you should get this key from a secure key management system such as an HSM.
88    let aes_key_bytes = generate_aes_key_bytes();
89
90    // 5. Create a Raw AES Keyring
91    let mpl_config = MaterialProvidersConfig::builder().build()?;
92    let mpl = mpl_client::Client::from_conf(mpl_config)?;
93
94    // The wrapping algorithm here is NOT the algorithm suite we set in this example.
95    let raw_aes_keyring = mpl
96        .create_raw_aes_keyring()
97        .key_name(key_name)
98        .key_namespace(key_namespace)
99        .wrapping_key(aes_key_bytes)
100        .wrapping_alg(AesWrappingAlg::AlgAes256GcmIv12Tag16)
101        .send()
102        .await?;
103
104    // 6. Encrypt the data with the encryption_context
105    let plaintext = example_data.as_bytes();
106
107    // This is the important step in this example where we specify the algorithm suite
108    // you want to use for encrypting your data
109    let encryption_response = esdk_client
110        .encrypt()
111        .plaintext(plaintext)
112        .keyring(raw_aes_keyring.clone())
113        .encryption_context(encryption_context.clone())
114        .algorithm_suite_id(AlgAes256GcmHkdfSha512CommitKey)
115        .send()
116        .await?;
117
118    let ciphertext = encryption_response
119        .ciphertext
120        .expect("Unable to unwrap ciphertext from encryption response");
121
122    // 7. Demonstrate that the ciphertext and plaintext are different.
123    // (This is an example for demonstration; you do not need to do this in your own code.)
124    assert_ne!(
125        ciphertext,
126        aws_smithy_types::Blob::new(plaintext),
127        "Ciphertext and plaintext data are the same. Invalid encryption"
128    );
129
130    // 8. Decrypt your encrypted data using the same keyring you used on encrypt.
131    let decryption_response = esdk_client
132        .decrypt()
133        .ciphertext(ciphertext)
134        .keyring(raw_aes_keyring)
135        // Provide the encryption context that was supplied to the encrypt method
136        .encryption_context(encryption_context)
137        .send()
138        .await?;
139
140    let decrypted_plaintext = decryption_response
141        .plaintext
142        .expect("Unable to unwrap plaintext from decryption response");
143
144    // 9. Demonstrate that the decrypted plaintext is identical to the original plaintext.
145    // (This is an example for demonstration; you do not need to do this in your own code.)
146    assert_eq!(
147        decrypted_plaintext,
148        aws_smithy_types::Blob::new(plaintext),
149        "Decrypted plaintext should be identical to the original plaintext. Invalid decryption"
150    );
151
152    println!("Set Encryption Algorithm Suite Example Completed Successfully");
153
154    Ok(())
155}
examples/limit_encrypted_data_keys_example.rs (line 87)
29pub async fn encrypt_and_decrypt_with_keyring(
30    example_data: &str,
31    max_encrypted_data_keys: u16,
32) -> Result<(), crate::BoxError> {
33    // 1. Instantiate the encryption SDK client.
34    // This builds the default client with the RequireEncryptRequireDecrypt commitment policy,
35    // which enforces that this client only encrypts using committing algorithm suites and enforces
36    // that this client will only decrypt encrypted messages that were created with a committing
37    // algorithm suite.
38    // Also, set the EncryptionSDK's max_encrypted_data_keys parameter here
39    let esdk_config = AwsEncryptionSdkConfig::builder()
40        .max_encrypted_data_keys(max_encrypted_data_keys)
41        .build()?;
42    let esdk_client = esdk_client::Client::from_conf(esdk_config)?;
43
44    // 2. The key namespace and key name are defined by you.
45    // and are used by the Raw AES keyring to determine
46    // whether it should attempt to decrypt an encrypted data key.
47    // For more information, see
48    // https://docs.aws.amazon.com/encryption-sdk/latest/developer-guide/use-raw-aes-keyring.html
49    let key_namespace: &str = "my-key-namespace";
50    let key_name: &str = "my-aes-key-name";
51
52    // 3. Create encryption context.
53    // Remember that your encryption context is NOT SECRET.
54    // For more information, see
55    // https://docs.aws.amazon.com/encryption-sdk/latest/developer-guide/concepts.html#encryption-context
56    let encryption_context = HashMap::from([
57        ("encryption".to_string(), "context".to_string()),
58        ("is not".to_string(), "secret".to_string()),
59        ("but adds".to_string(), "useful metadata".to_string()),
60        (
61            "that can help you".to_string(),
62            "be confident that".to_string(),
63        ),
64        (
65            "the data you are handling".to_string(),
66            "is what you think it is".to_string(),
67        ),
68    ]);
69
70    // 4. Generate `max_encrypted_data_keys` AES keyrings to use with your keyring.
71    // In practice, you should get this key from a secure key management system such as an HSM.
72    let mpl_config = MaterialProvidersConfig::builder().build()?;
73    let mpl = mpl_client::Client::from_conf(mpl_config)?;
74
75    let mut raw_aes_keyrings: Vec<KeyringRef> = vec![];
76
77    assert!(
78        max_encrypted_data_keys > 0,
79        "max_encrypted_data_keys MUST be greater than 0"
80    );
81
82    let mut i = 0;
83    while i < max_encrypted_data_keys {
84        let aes_key_bytes = generate_aes_key_bytes();
85
86        let raw_aes_keyring = mpl
87            .create_raw_aes_keyring()
88            .key_name(key_name)
89            .key_namespace(key_namespace)
90            .wrapping_key(aes_key_bytes)
91            .wrapping_alg(AesWrappingAlg::AlgAes256GcmIv12Tag16)
92            .send()
93            .await?;
94
95        raw_aes_keyrings.push(raw_aes_keyring);
96        i += 1;
97    }
98
99    // 5. Create a Multi Keyring with `max_encrypted_data_keys` AES Keyrings
100    let generator_keyring = raw_aes_keyrings.remove(0);
101
102    let multi_keyring = mpl
103        .create_multi_keyring()
104        .generator(generator_keyring)
105        .child_keyrings(raw_aes_keyrings)
106        .send()
107        .await?;
108
109    // 6. Encrypt the data with the encryption_context
110    let plaintext = example_data.as_bytes();
111
112    let encryption_response = esdk_client
113        .encrypt()
114        .plaintext(plaintext)
115        .keyring(multi_keyring.clone())
116        .encryption_context(encryption_context.clone())
117        .send()
118        .await?;
119
120    let ciphertext = encryption_response
121        .ciphertext
122        .expect("Unable to unwrap ciphertext from encryption response");
123
124    // 7. Demonstrate that the ciphertext and plaintext are different.
125    // (This is an example for demonstration; you do not need to do this in your own code.)
126    assert_ne!(
127        ciphertext,
128        aws_smithy_types::Blob::new(plaintext),
129        "Ciphertext and plaintext data are the same. Invalid encryption"
130    );
131
132    // 8. Decrypt your encrypted data using the same keyring you used on encrypt.
133    let decryption_response = esdk_client
134        .decrypt()
135        .ciphertext(ciphertext.clone())
136        .keyring(multi_keyring.clone())
137        // Provide the encryption context that was supplied to the encrypt method
138        .encryption_context(encryption_context.clone())
139        .send()
140        .await?;
141
142    let decrypted_plaintext = decryption_response
143        .plaintext
144        .expect("Unable to unwrap plaintext from decryption response");
145
146    // 9. Demonstrate that the decrypted plaintext is identical to the original plaintext.
147    // (This is an example for demonstration; you do not need to do this in your own code.)
148    assert_eq!(
149        decrypted_plaintext,
150        aws_smithy_types::Blob::new(plaintext),
151        "Decrypted plaintext should be identical to the original plaintext. Invalid decryption"
152    );
153
154    // 10. Demonstrate that an EncryptionSDK with a lower MaxEncryptedDataKeys
155    // will fail to decrypt the encrypted message.
156    let esdk_config = AwsEncryptionSdkConfig::builder()
157        .max_encrypted_data_keys(max_encrypted_data_keys - 1)
158        .build()?;
159    let esdk_client_incorrect_max_encrypted_keys = esdk_client::Client::from_conf(esdk_config)?;
160
161    let decryption_response_incorrect_max_encrypted_keys = esdk_client_incorrect_max_encrypted_keys
162        .decrypt()
163        .ciphertext(ciphertext)
164        .keyring(multi_keyring)
165        // Provide the encryption context that was supplied to the encrypt method
166        .encryption_context(encryption_context)
167        .send()
168        .await;
169
170    match decryption_response_incorrect_max_encrypted_keys {
171        Ok(_) => panic!(
172            "Decrypt using discovery keyring with wrong AWS Account ID MUST \
173                            raise AwsCryptographicMaterialProvidersError"
174        ),
175        Err(AwsEncryptionSdkException { message: m }) => assert_eq!(
176            m,
177            "Ciphertext encrypted data keys exceed maxEncryptedDataKeys"
178        ),
179        _ => panic!("Unexpected error type"),
180    }
181
182    println!("Limit Encrypted Data Keys Example Completed Successfully");
183
184    Ok(())
185}
examples/keyring/multi_keyring_example.rs (line 112)
52pub async fn encrypt_and_decrypt_with_keyring(
53    example_data: &str,
54    kms_key_id: &str,
55) -> Result<(), crate::BoxError> {
56    // 1. Instantiate the encryption SDK client.
57    // This builds the default client with the RequireEncryptRequireDecrypt commitment policy,
58    // which enforces that this client only encrypts using committing algorithm suites and enforces
59    // that this client will only decrypt encrypted messages that were created with a committing
60    // algorithm suite.
61    let esdk_config = AwsEncryptionSdkConfig::builder().build()?;
62    let esdk_client = esdk_client::Client::from_conf(esdk_config)?;
63
64    // 2. Create a KMS client.
65    let sdk_config = aws_config::load_defaults(aws_config::BehaviorVersion::latest()).await;
66    let kms_client = aws_sdk_kms::Client::new(&sdk_config);
67
68    // 3. Create encryption context.
69    // Remember that your encryption context is NOT SECRET.
70    // For more information, see
71    // https://docs.aws.amazon.com/encryption-sdk/latest/developer-guide/concepts.html#encryption-context
72    let encryption_context = HashMap::from([
73        ("encryption".to_string(), "context".to_string()),
74        ("is not".to_string(), "secret".to_string()),
75        ("but adds".to_string(), "useful metadata".to_string()),
76        (
77            "that can help you".to_string(),
78            "be confident that".to_string(),
79        ),
80        (
81            "the data you are handling".to_string(),
82            "is what you think it is".to_string(),
83        ),
84    ]);
85
86    // 4. Create a KMS keyring
87    let mpl_config = MaterialProvidersConfig::builder().build()?;
88    let mpl = mpl_client::Client::from_conf(mpl_config)?;
89
90    let kms_keyring = mpl
91        .create_aws_kms_keyring()
92        .kms_key_id(kms_key_id)
93        .kms_client(kms_client)
94        .send()
95        .await?;
96
97    // 5. Create a raw AES keyring to additionally encrypt under as child_keyring
98
99    // The key namespace and key name are defined by you.
100    // and are used by the Raw AES keyring to determine
101    // whether it should attempt to decrypt an encrypted data key.
102    // For more information, see
103    // https://docs.aws.amazon.com/encryption-sdk/latest/developer-guide/use-raw-aes-keyring.html
104    let key_namespace: &str = "my-key-namespace";
105    let key_name: &str = "my-aes-key-name";
106
107    // Generate a 256-bit AES key to use with your raw AES keyring.
108    // In practice, you should get this key from a secure key management system such as an HSM.
109    let aes_key_bytes = generate_aes_key_bytes();
110
111    let raw_aes_keyring = mpl
112        .create_raw_aes_keyring()
113        .key_name(key_name)
114        .key_namespace(key_namespace)
115        .wrapping_key(aes_key_bytes)
116        .wrapping_alg(AesWrappingAlg::AlgAes256GcmIv12Tag16)
117        .send()
118        .await?;
119
120    // 6. Create a multi_keyring that consists of the previously created keyrings.
121    // When using this multi_keyring to encrypt data, either `kms_keyring` or
122    // `raw_aes_keyring` (or a multi_keyring containing either) may be used to decrypt the data.
123    let multi_keyring = mpl
124        .create_multi_keyring()
125        .generator(kms_keyring.clone())
126        .child_keyrings(vec![raw_aes_keyring.clone()])
127        .send()
128        .await?;
129
130    // 7. Encrypt the data with the encryption_context
131    let plaintext = example_data.as_bytes();
132
133    let encryption_response = esdk_client
134        .encrypt()
135        .plaintext(plaintext)
136        .keyring(multi_keyring.clone())
137        .encryption_context(encryption_context.clone())
138        .send()
139        .await?;
140
141    let ciphertext = encryption_response
142        .ciphertext
143        .expect("Unable to unwrap ciphertext from encryption response");
144
145    // 8. Demonstrate that the ciphertext and plaintext are different.
146    // (This is an example for demonstration; you do not need to do this in your own code.)
147    assert_ne!(
148        ciphertext,
149        aws_smithy_types::Blob::new(plaintext),
150        "Ciphertext and plaintext data are the same. Invalid encryption"
151    );
152
153    // 9a. Decrypt your encrypted data using the same multi_keyring you used on encrypt.
154    let decryption_response_multi_keyring = esdk_client
155        .decrypt()
156        .ciphertext(ciphertext.clone())
157        .keyring(multi_keyring)
158        // Provide the encryption context that was supplied to the encrypt method
159        .encryption_context(encryption_context.clone())
160        .send()
161        .await?;
162
163    let decrypted_plaintext_multi_keyring = decryption_response_multi_keyring
164        .plaintext
165        .expect("Unable to unwrap plaintext from decryption response");
166
167    // 9b. Demonstrate that the decrypted plaintext is identical to the original plaintext.
168    // (This is an example for demonstration; you do not need to do this in your own code.)
169    assert_eq!(
170        decrypted_plaintext_multi_keyring,
171        aws_smithy_types::Blob::new(plaintext),
172        "Decrypted plaintext should be identical to the original plaintext. Invalid decryption"
173    );
174
175    // Because you used a multi_keyring on Encrypt, you can use either the
176    // `kms_keyring` or `raw_aes_keyring` individually to decrypt the data.
177
178    // 10. Demonstrate that you can successfully decrypt data using just the `kms_keyring`
179    // directly.
180    // (This is an example for demonstration; you do not need to do this in your own code.)
181
182    // 10a. Decrypt your encrypted data using the kms_keyring.
183    let decryption_response_kms_keyring = esdk_client
184        .decrypt()
185        .ciphertext(ciphertext.clone())
186        .keyring(kms_keyring)
187        // Provide the encryption context that was supplied to the encrypt method
188        .encryption_context(encryption_context.clone())
189        .send()
190        .await?;
191
192    let decrypted_plaintext_kms_keyring = decryption_response_kms_keyring
193        .plaintext
194        .expect("Unable to unwrap plaintext from decryption response");
195
196    // 10b. Demonstrate that the decrypted plaintext is identical to the original plaintext.
197    // (This is an example for demonstration; you do not need to do this in your own code.)
198    assert_eq!(
199        decrypted_plaintext_kms_keyring,
200        aws_smithy_types::Blob::new(plaintext),
201        "Decrypted plaintext should be identical to the original plaintext. Invalid decryption"
202    );
203
204    // 11. Demonstrate that you can also successfully decrypt data using the `raw_aes_keyring`
205    // directly.
206    // (This is an example for demonstration; you do not need to do this in your own code.)
207
208    // 11a. Decrypt your encrypted data using the raw_aes_keyring.
209    let decryption_response_raw_aes_keyring = esdk_client
210        .decrypt()
211        .ciphertext(ciphertext)
212        .keyring(raw_aes_keyring)
213        // Provide the encryption context that was supplied to the encrypt method
214        .encryption_context(encryption_context)
215        .send()
216        .await?;
217
218    let decrypted_plaintext_raw_aes_keyring = decryption_response_raw_aes_keyring
219        .plaintext
220        .expect("Unable to unwrap plaintext from decryption response");
221
222    // 11b. Demonstrate that the decrypted plaintext is identical to the original plaintext.
223    // (This is an example for demonstration; you do not need to do this in your own code.)
224    assert_eq!(
225        decrypted_plaintext_raw_aes_keyring,
226        aws_smithy_types::Blob::new(plaintext),
227        "Decrypted plaintext should be identical to the original plaintext. Invalid decryption"
228    );
229
230    println!("Multi Keyring Example Completed Successfully");
231
232    Ok(())
233}
Source§

impl Client

Source

pub fn create_raw_rsa_keyring(&self) -> CreateRawRsaKeyringFluentBuilder

Examples found in repository?
examples/keyring/raw_rsa_keyring_example.rs (line 123)
64pub async fn encrypt_and_decrypt_with_keyring(example_data: &str) -> Result<(), crate::BoxError> {
65    // 1. Instantiate the encryption SDK client.
66    // This builds the default client with the RequireEncryptRequireDecrypt commitment policy,
67    // which enforces that this client only encrypts using committing algorithm suites and enforces
68    // that this client will only decrypt encrypted messages that were created with a committing
69    // algorithm suite.
70    let esdk_config = AwsEncryptionSdkConfig::builder().build()?;
71    let esdk_client = esdk_client::Client::from_conf(esdk_config)?;
72
73    // 2. Create encryption context.
74    // Remember that your encryption context is NOT SECRET.
75    // For more information, see
76    // https://docs.aws.amazon.com/encryption-sdk/latest/developer-guide/concepts.html#encryption-context
77    let encryption_context = HashMap::from([
78        ("encryption".to_string(), "context".to_string()),
79        ("is not".to_string(), "secret".to_string()),
80        ("but adds".to_string(), "useful metadata".to_string()),
81        (
82            "that can help you".to_string(),
83            "be confident that".to_string(),
84        ),
85        (
86            "the data you are handling".to_string(),
87            "is what you think it is".to_string(),
88        ),
89    ]);
90
91    // 3. You may provide your own RSA key pair in the files located at
92    //  - EXAMPLE_RSA_PRIVATE_KEY_FILENAME
93    //  - EXAMPLE_RSA_PUBLIC_KEY_FILENAME
94    // If these files are not present, this will generate a pair for you
95    if should_generate_new_rsa_key_pair()? {
96        generate_rsa_key_pair()?;
97    }
98
99    // 4. Load key pair from UTF-8 encoded PEM files.
100    //    You may provide your own PEM files to use here.
101    //    If you do not, the main method in this class will generate PEM
102    //    files for example use. Do not use these files for any other purpose.
103    let mut file = File::open(Path::new(EXAMPLE_RSA_PUBLIC_KEY_FILENAME))?;
104    let mut public_key_utf8_bytes = Vec::new();
105    file.read_to_end(&mut public_key_utf8_bytes)?;
106
107    let mut file = File::open(Path::new(EXAMPLE_RSA_PRIVATE_KEY_FILENAME))?;
108    let mut private_key_utf8_bytes = Vec::new();
109    file.read_to_end(&mut private_key_utf8_bytes)?;
110
111    // 5. The key namespace and key name are defined by you.
112    // and are used by the Raw RSA keyring
113    // For more information, see
114    // https://docs.aws.amazon.com/encryption-sdk/latest/developer-guide/use-raw-rsa-keyring.html
115    let key_namespace: &str = "my-key-namespace";
116    let key_name: &str = "my-rsa-key-name";
117
118    // 6. Create the Raw RSA keyring.
119    let mpl_config = MaterialProvidersConfig::builder().build()?;
120    let mpl = mpl_client::Client::from_conf(mpl_config)?;
121
122    let raw_rsa_keyring = mpl
123        .create_raw_rsa_keyring()
124        .key_name(key_name)
125        .key_namespace(key_namespace)
126        .padding_scheme(PaddingScheme::OaepSha256Mgf1)
127        .public_key(public_key_utf8_bytes)
128        .private_key(private_key_utf8_bytes)
129        .send()
130        .await?;
131
132    // 7. Encrypt the data with the encryption_context
133    let plaintext = example_data.as_bytes();
134
135    let encryption_response = esdk_client
136        .encrypt()
137        .plaintext(plaintext)
138        .keyring(raw_rsa_keyring.clone())
139        .encryption_context(encryption_context.clone())
140        .send()
141        .await?;
142
143    let ciphertext = encryption_response
144        .ciphertext
145        .expect("Unable to unwrap ciphertext from encryption response");
146
147    // 8. Demonstrate that the ciphertext and plaintext are different.
148    // (This is an example for demonstration; you do not need to do this in your own code.)
149    assert_ne!(
150        ciphertext,
151        aws_smithy_types::Blob::new(plaintext),
152        "Ciphertext and plaintext data are the same. Invalid encryption"
153    );
154
155    // 9. Decrypt your encrypted data using the same keyring you used on encrypt.
156    let decryption_response = esdk_client
157        .decrypt()
158        .ciphertext(ciphertext)
159        .keyring(raw_rsa_keyring)
160        // Provide the encryption context that was supplied to the encrypt method
161        .encryption_context(encryption_context)
162        .send()
163        .await?;
164
165    let decrypted_plaintext = decryption_response
166        .plaintext
167        .expect("Unable to unwrap plaintext from decryption response");
168
169    // 10. Demonstrate that the decrypted plaintext is identical to the original plaintext.
170    // (This is an example for demonstration; you do not need to do this in your own code.)
171    assert_eq!(
172        decrypted_plaintext,
173        aws_smithy_types::Blob::new(plaintext),
174        "Decrypted plaintext should be identical to the original plaintext. Invalid decryption"
175    );
176
177    println!("Raw RSA Keyring Example Completed Successfully");
178
179    Ok(())
180}
Source§

impl Client

Source

pub fn create_raw_ecdh_keyring(&self) -> CreateRawEcdhKeyringFluentBuilder

Examples found in repository?
examples/keyring/ecdh/public_key_discovery_raw_ecdh_keyring_example.rs (line 144)
66pub async fn decrypt_with_keyring(
67    example_data: &str,
68    ecdh_curve_spec: EcdhCurveSpec,
69) -> Result<(), crate::BoxError> {
70    // 1. Instantiate the encryption SDK client.
71    // This builds the default client with the RequireEncryptRequireDecrypt commitment policy,
72    // which enforces that this client only encrypts using committing algorithm suites and enforces
73    // that this client will only decrypt encrypted messages that were created with a committing
74    // algorithm suite.
75    let esdk_config = AwsEncryptionSdkConfig::builder().build()?;
76    let esdk_client = esdk_client::Client::from_conf(esdk_config)?;
77
78    let mpl_config = MaterialProvidersConfig::builder().build()?;
79    let mpl = mpl_client::Client::from_conf(mpl_config)?;
80
81    // 2. Create encryption context.
82    // Remember that your encryption context is NOT SECRET.
83    // For more information, see
84    // https://docs.aws.amazon.com/encryption-sdk/latest/developer-guide/concepts.html#encryption-context
85    let encryption_context = HashMap::from([
86        ("encryption".to_string(), "context".to_string()),
87        ("is not".to_string(), "secret".to_string()),
88        ("but adds".to_string(), "useful metadata".to_string()),
89        (
90            "that can help you".to_string(),
91            "be confident that".to_string(),
92        ),
93        (
94            "the data you are handling".to_string(),
95            "is what you think it is".to_string(),
96        ),
97    ]);
98
99    // 3. You may provide your own ECC keys in the files located at
100    // - EXAMPLE_ECC_PRIVATE_KEY_FILENAME_RECIPIENT
101
102    // If you do not provide these files, running this example through this
103    // class' main method will generate three files required for all raw ECDH examples
104    // EXAMPLE_ECC_PRIVATE_KEY_FILENAME_SENDER, EXAMPLE_ECC_PRIVATE_KEY_FILENAME_RECIPIENT
105    // and EXAMPLE_ECC_PUBLIC_KEY_FILENAME_RECIPIENT for you.
106
107    // Do not use these files for any other purpose.
108    if should_generate_new_ecc_key_pair_discovery_raw_ecdh()? {
109        write_raw_ecdh_ecc_keys(ecdh_curve_spec)?;
110    }
111
112    // 4. Load keys from UTF-8 encoded PEM files.
113    let mut file = File::open(Path::new(EXAMPLE_ECC_PRIVATE_KEY_FILENAME_RECIPIENT))?;
114    let mut private_key_recipient_utf8_bytes = Vec::new();
115    file.read_to_end(&mut private_key_recipient_utf8_bytes)?;
116
117    // Generate the ciphertext
118    let ciphertext = get_ciphertext(
119        example_data,
120        ecdh_curve_spec,
121        encryption_context.clone(),
122        esdk_client.clone(),
123        mpl.clone(),
124    )
125    .await?;
126
127    // 5. Create the PublicKeyDiscoveryInput
128    let discovery_raw_ecdh_static_configuration_input = PublicKeyDiscoveryInput::builder()
129        // Must be a UTF8 PEM-encoded private key
130        .recipient_static_private_key(private_key_recipient_utf8_bytes)
131        .build()?;
132
133    let discovery_raw_ecdh_static_configuration = RawEcdhStaticConfigurations::PublicKeyDiscovery(
134        discovery_raw_ecdh_static_configuration_input,
135    );
136
137    // 6. Create the Public Key Discovery Raw ECDH keyring.
138
139    // Create the keyring.
140    // This keyring uses a discovery configuration. This configuration will check on decrypt
141    // if it is meant to decrypt the message by checking if the configured public key is stored on the message.
142    // The discovery configuration can only decrypt messages and CANNOT encrypt messages.
143    let discovery_raw_ecdh_keyring = mpl
144        .create_raw_ecdh_keyring()
145        .curve_spec(ecdh_curve_spec)
146        .key_agreement_scheme(discovery_raw_ecdh_static_configuration)
147        .send()
148        .await?;
149
150    // 7. Decrypt your encrypted data using the same keyring you used on encrypt.
151    let decryption_response = esdk_client
152        .decrypt()
153        .ciphertext(ciphertext)
154        .keyring(discovery_raw_ecdh_keyring)
155        // Provide the encryption context that was supplied to the encrypt method
156        .encryption_context(encryption_context)
157        .send()
158        .await?;
159
160    let decrypted_plaintext = decryption_response
161        .plaintext
162        .expect("Unable to unwrap plaintext from decryption response");
163
164    // 8. Demonstrate that the decrypted plaintext is identical to the original plaintext.
165    // (This is an example for demonstration; you do not need to do this in your own code.)
166    let plaintext = example_data.as_bytes();
167
168    assert_eq!(
169        decrypted_plaintext,
170        aws_smithy_types::Blob::new(plaintext),
171        "Decrypted plaintext should be identical to the original plaintext. Invalid decryption"
172    );
173
174    println!("Public Key Discovery Raw ECDH Keyring Example Completed Successfully");
175
176    Ok(())
177}
178
179fn should_generate_new_ecc_key_pair_discovery_raw_ecdh() -> Result<bool, String> {
180    // If keys already exist: do not overwrite existing keys
181    if exists(EXAMPLE_ECC_PRIVATE_KEY_FILENAME_RECIPIENT)
182        && exists(EXAMPLE_ECC_PUBLIC_KEY_FILENAME_RECIPIENT)
183    {
184        Ok(false)
185    }
186    // If only one file is present: throw exception
187    else if !exists(EXAMPLE_ECC_PRIVATE_KEY_FILENAME_RECIPIENT)
188        && exists(EXAMPLE_ECC_PUBLIC_KEY_FILENAME_RECIPIENT)
189    {
190        Err("Missing key file at ".to_string() + EXAMPLE_ECC_PRIVATE_KEY_FILENAME_RECIPIENT)
191    } else if exists(EXAMPLE_ECC_PRIVATE_KEY_FILENAME_RECIPIENT)
192        && !exists(EXAMPLE_ECC_PUBLIC_KEY_FILENAME_RECIPIENT)
193    {
194        Err("Missing key file at ".to_string() + EXAMPLE_ECC_PUBLIC_KEY_FILENAME_RECIPIENT)
195    }
196    // If neither file is present, generate a new key pair
197    else {
198        Ok(true)
199    }
200}
201
202async fn get_ciphertext(
203    example_data: &str,
204    ecdh_curve_spec: EcdhCurveSpec,
205    encryption_context: HashMap<String, String>,
206    esdk_client: esdk_client::Client,
207    mpl: mpl_client::Client,
208) -> Result<Blob, crate::BoxError> {
209    // 1. Load keys from UTF-8 encoded PEM files.
210
211    // Load public key from UTF-8 encoded PEM files into a DER encoded public key.
212    let public_key_file_content =
213        std::fs::read_to_string(Path::new(EXAMPLE_ECC_PUBLIC_KEY_FILENAME_RECIPIENT))?;
214    let parsed_public_key_file_content = parse(public_key_file_content)?;
215    let public_key_recipient_utf8_bytes = parsed_public_key_file_content.contents();
216
217    // 2. Create the EphemeralPrivateKeyToStaticPublicKeyInput to generate the ciphertext
218    let ephemeral_raw_ecdh_static_configuration_input =
219        EphemeralPrivateKeyToStaticPublicKeyInput::builder()
220            // Must be a UTF8 DER-encoded X.509 public key
221            .recipient_public_key(public_key_recipient_utf8_bytes)
222            .build()?;
223
224    let ephemeral_raw_ecdh_static_configuration =
225        RawEcdhStaticConfigurations::EphemeralPrivateKeyToStaticPublicKey(
226            ephemeral_raw_ecdh_static_configuration_input,
227        );
228
229    // 3. Create the Ephemeral Raw ECDH keyring.
230
231    // Create the keyring.
232    // This keyring uses an ephemeral configuration. This configuration will always create a new
233    // key pair as the sender key pair for the key agreement operation. The ephemeral configuration can only
234    // encrypt data and CANNOT decrypt messages.
235    let ephemeral_raw_ecdh_keyring = mpl
236        .create_raw_ecdh_keyring()
237        .curve_spec(ecdh_curve_spec)
238        .key_agreement_scheme(ephemeral_raw_ecdh_static_configuration)
239        .send()
240        .await?;
241
242    // 4. Encrypt the data with the encryption_context
243
244    // A raw ecdh keyring with Ephemeral configuration cannot decrypt data since the key pair
245    // used as the sender is ephemeral. This means that at decrypt time it does not have
246    // the private key that corresponds to the public key that is stored on the message.
247    let plaintext = example_data.as_bytes();
248
249    let encryption_response = esdk_client
250        .encrypt()
251        .plaintext(plaintext)
252        .keyring(ephemeral_raw_ecdh_keyring)
253        .encryption_context(encryption_context)
254        .send()
255        .await?;
256
257    let ciphertext = encryption_response
258        .ciphertext
259        .expect("Unable to unwrap ciphertext from encryption response");
260
261    // 5. Demonstrate that the ciphertext and plaintext are different.
262    // (This is an example for demonstration; you do not need to do this in your own code.)
263    assert_ne!(
264        ciphertext,
265        aws_smithy_types::Blob::new(plaintext),
266        "Ciphertext and plaintext data are the same. Invalid encryption"
267    );
268
269    Ok(ciphertext)
270}
More examples
Hide additional examples
examples/keyring/ecdh/ephemeral_raw_ecdh_keyring_example.rs (line 127)
55pub async fn encrypt_with_keyring(
56    example_data: &str,
57    ecdh_curve_spec: EcdhCurveSpec,
58) -> Result<(), crate::BoxError> {
59    // 1. Instantiate the encryption SDK client.
60    // This builds the default client with the RequireEncryptRequireDecrypt commitment policy,
61    // which enforces that this client only encrypts using committing algorithm suites and enforces
62    // that this client will only decrypt encrypted messages that were created with a committing
63    // algorithm suite.
64    let esdk_config = AwsEncryptionSdkConfig::builder().build()?;
65    let esdk_client = esdk_client::Client::from_conf(esdk_config)?;
66
67    // 2. Create encryption context.
68    // Remember that your encryption context is NOT SECRET.
69    // For more information, see
70    // https://docs.aws.amazon.com/encryption-sdk/latest/developer-guide/concepts.html#encryption-context
71    let encryption_context = HashMap::from([
72        ("encryption".to_string(), "context".to_string()),
73        ("is not".to_string(), "secret".to_string()),
74        ("but adds".to_string(), "useful metadata".to_string()),
75        (
76            "that can help you".to_string(),
77            "be confident that".to_string(),
78        ),
79        (
80            "the data you are handling".to_string(),
81            "is what you think it is".to_string(),
82        ),
83    ]);
84
85    // 3. You may provide your own ECC keys in the files located at
86    // - EXAMPLE_ECC_PUBLIC_KEY_FILENAME_RECIPIENT
87
88    // If you do not provide these files, running this example through this
89    // class' main method will generate three files required for all raw ECDH examples
90    // EXAMPLE_ECC_PRIVATE_KEY_FILENAME_SENDER, EXAMPLE_ECC_PRIVATE_KEY_FILENAME_RECIPIENT
91    // and EXAMPLE_ECC_PUBLIC_KEY_FILENAME_RECIPIENT for you.
92
93    // Do not use these files for any other purpose.
94    if should_generate_new_ecc_key_pair_ephemeral_raw_ecdh()? {
95        write_raw_ecdh_ecc_keys(ecdh_curve_spec)?;
96    }
97
98    // 4. Load keys from UTF-8 encoded PEM files.
99
100    // Load public key from UTF-8 encoded PEM files into a DER encoded public key.
101    let public_key_file_content =
102        std::fs::read_to_string(Path::new(EXAMPLE_ECC_PUBLIC_KEY_FILENAME_RECIPIENT))?;
103    let parsed_public_key_file_content = parse(public_key_file_content)?;
104    let public_key_recipient_utf8_bytes = parsed_public_key_file_content.contents();
105
106    // 5. Create the EphemeralPrivateKeyToStaticPublicKeyInput
107    let ephemeral_raw_ecdh_static_configuration_input =
108        EphemeralPrivateKeyToStaticPublicKeyInput::builder()
109            // Must be a UTF8 DER-encoded X.509 public key
110            .recipient_public_key(public_key_recipient_utf8_bytes)
111            .build()?;
112
113    let ephemeral_raw_ecdh_static_configuration =
114        RawEcdhStaticConfigurations::EphemeralPrivateKeyToStaticPublicKey(
115            ephemeral_raw_ecdh_static_configuration_input,
116        );
117
118    // 6. Create the Ephemeral Raw ECDH keyring.
119    let mpl_config = MaterialProvidersConfig::builder().build()?;
120    let mpl = mpl_client::Client::from_conf(mpl_config)?;
121
122    // Create the keyring.
123    // This keyring uses an ephemeral configuration. This configuration will always create a new
124    // key pair as the sender key pair for the key agreement operation. The ephemeral configuration can only
125    // encrypt data and CANNOT decrypt messages.
126    let ephemeral_raw_ecdh_keyring = mpl
127        .create_raw_ecdh_keyring()
128        .curve_spec(ecdh_curve_spec)
129        .key_agreement_scheme(ephemeral_raw_ecdh_static_configuration)
130        .send()
131        .await?;
132
133    // 7. Encrypt the data with the encryption_context
134
135    // A raw ecdh keyring with Ephemeral configuration cannot decrypt data since the key pair
136    // used as the sender is ephemeral. This means that at decrypt time it does not have
137    // the private key that corresponds to the public key that is stored on the message.
138    let plaintext = example_data.as_bytes();
139
140    let encryption_response = esdk_client
141        .encrypt()
142        .plaintext(plaintext)
143        .keyring(ephemeral_raw_ecdh_keyring)
144        .encryption_context(encryption_context)
145        .send()
146        .await?;
147
148    let ciphertext = encryption_response
149        .ciphertext
150        .expect("Unable to unwrap ciphertext from encryption response");
151
152    // 8. Demonstrate that the ciphertext and plaintext are different.
153    // (This is an example for demonstration; you do not need to do this in your own code.)
154    assert_ne!(
155        ciphertext,
156        aws_smithy_types::Blob::new(plaintext),
157        "Ciphertext and plaintext data are the same. Invalid encryption"
158    );
159
160    println!("Ephemeral Raw ECDH Keyring Example Completed Successfully");
161
162    Ok(())
163}
examples/keyring/ecdh/raw_ecdh_keyring_example.rs (line 146)
67pub async fn encrypt_and_decrypt_with_keyring(
68    example_data: &str,
69    ecdh_curve_spec: EcdhCurveSpec,
70) -> Result<(), crate::BoxError> {
71    // 1. Instantiate the encryption SDK client.
72    // This builds the default client with the RequireEncryptRequireDecrypt commitment policy,
73    // which enforces that this client only encrypts using committing algorithm suites and enforces
74    // that this client will only decrypt encrypted messages that were created with a committing
75    // algorithm suite.
76    let esdk_config = AwsEncryptionSdkConfig::builder().build()?;
77    let esdk_client = esdk_client::Client::from_conf(esdk_config)?;
78
79    // 2. Create encryption context.
80    // Remember that your encryption context is NOT SECRET.
81    // For more information, see
82    // https://docs.aws.amazon.com/encryption-sdk/latest/developer-guide/concepts.html#encryption-context
83    let encryption_context = HashMap::from([
84        ("encryption".to_string(), "context".to_string()),
85        ("is not".to_string(), "secret".to_string()),
86        ("but adds".to_string(), "useful metadata".to_string()),
87        (
88            "that can help you".to_string(),
89            "be confident that".to_string(),
90        ),
91        (
92            "the data you are handling".to_string(),
93            "is what you think it is".to_string(),
94        ),
95    ]);
96
97    // 3. You may provide your own ECC keys in the files located at
98    // - EXAMPLE_ECC_PRIVATE_KEY_FILENAME_SENDER
99    // - EXAMPLE_ECC_PUBLIC_KEY_FILENAME_RECIPIENT
100
101    // If you do not provide these files, running this example through this
102    // class' main method will generate three files required for all raw ECDH examples
103    // EXAMPLE_ECC_PRIVATE_KEY_FILENAME_SENDER, EXAMPLE_ECC_PRIVATE_KEY_FILENAME_RECIPIENT
104    // and EXAMPLE_ECC_PUBLIC_KEY_FILENAME_RECIPIENT for you.
105
106    // Do not use these files for any other purpose.
107    if should_generate_new_ecc_key_pair_raw_ecdh()? {
108        write_raw_ecdh_ecc_keys(ecdh_curve_spec)?;
109    }
110
111    // 4. Load keys from UTF-8 encoded PEM files.
112    let mut file = File::open(Path::new(EXAMPLE_ECC_PRIVATE_KEY_FILENAME_SENDER))?;
113    let mut private_key_sender_utf8_bytes = Vec::new();
114    file.read_to_end(&mut private_key_sender_utf8_bytes)?;
115
116    // Load public key from UTF-8 encoded PEM files into a DER encoded public key.
117    let public_key_file_content =
118        std::fs::read_to_string(Path::new(EXAMPLE_ECC_PUBLIC_KEY_FILENAME_RECIPIENT))?;
119    let parsed_public_key_file_content = parse(public_key_file_content)?;
120    let public_key_recipient_utf8_bytes = parsed_public_key_file_content.contents();
121
122    // 5. Create the RawPrivateKeyToStaticPublicKeyInput
123    let raw_ecdh_static_configuration_input = RawPrivateKeyToStaticPublicKeyInput::builder()
124        // Must be a UTF8 PEM-encoded private key
125        .sender_static_private_key(private_key_sender_utf8_bytes)
126        // Must be a UTF8 DER-encoded X.509 public key
127        .recipient_public_key(public_key_recipient_utf8_bytes)
128        .build()?;
129
130    let raw_ecdh_static_configuration = RawEcdhStaticConfigurations::RawPrivateKeyToStaticPublicKey(
131        raw_ecdh_static_configuration_input,
132    );
133
134    // 6. Create the Raw ECDH keyring.
135    let mpl_config = MaterialProvidersConfig::builder().build()?;
136    let mpl = mpl_client::Client::from_conf(mpl_config)?;
137
138    // Create the keyring.
139    // This keyring uses static sender and recipient keys. This configuration calls for both of
140    // the keys to be on the same curve (P256 / P384 / P521).
141    // On encrypt, the shared secret is derived from the sender's private key and the recipient's public key.
142    // For this example, on decrypt, the shared secret is derived from the sender's private key and the recipient's public key;
143    // However, on decrypt, the recipient can construct a keyring such that the shared secret is calculated with
144    // the recipient's private key and the sender's public key. In both scenarios the shared secret will be the same.
145    let raw_ecdh_keyring = mpl
146        .create_raw_ecdh_keyring()
147        .curve_spec(ecdh_curve_spec)
148        .key_agreement_scheme(raw_ecdh_static_configuration)
149        .send()
150        .await?;
151
152    // 7. Encrypt the data with the encryption_context
153    let plaintext = example_data.as_bytes();
154
155    let encryption_response = esdk_client
156        .encrypt()
157        .plaintext(plaintext)
158        .keyring(raw_ecdh_keyring.clone())
159        .encryption_context(encryption_context.clone())
160        .send()
161        .await?;
162
163    let ciphertext = encryption_response
164        .ciphertext
165        .expect("Unable to unwrap ciphertext from encryption response");
166
167    // 8. Demonstrate that the ciphertext and plaintext are different.
168    // (This is an example for demonstration; you do not need to do this in your own code.)
169    assert_ne!(
170        ciphertext,
171        aws_smithy_types::Blob::new(plaintext),
172        "Ciphertext and plaintext data are the same. Invalid encryption"
173    );
174
175    // 9. Decrypt your encrypted data using the same keyring you used on encrypt.
176    let decryption_response = esdk_client
177        .decrypt()
178        .ciphertext(ciphertext)
179        .keyring(raw_ecdh_keyring)
180        // Provide the encryption context that was supplied to the encrypt method
181        .encryption_context(encryption_context)
182        .send()
183        .await?;
184
185    let decrypted_plaintext = decryption_response
186        .plaintext
187        .expect("Unable to unwrap plaintext from decryption response");
188
189    // 10. Demonstrate that the decrypted plaintext is identical to the original plaintext.
190    // (This is an example for demonstration; you do not need to do this in your own code.)
191    assert_eq!(
192        decrypted_plaintext,
193        aws_smithy_types::Blob::new(plaintext),
194        "Decrypted plaintext should be identical to the original plaintext. Invalid decryption"
195    );
196
197    println!("Raw ECDH Keyring Example Completed Successfully");
198
199    Ok(())
200}
Source§

impl Client

Source

pub fn create_default_cryptographic_materials_manager( &self, ) -> CreateDefaultCryptographicMaterialsManagerFluentBuilder

Examples found in repository?
examples/cryptographic_materials_manager/restrict_algorithm_suite/signing_suite_only_cmm.rs (line 49)
33    pub fn new(keyring: KeyringRef) -> Self {
34        let mpl_config = MaterialProvidersConfig::builder().build().unwrap();
35        let mpl = mpl_client::Client::from_conf(mpl_config).unwrap();
36
37        Self {
38            approved_algos: vec![
39                EsdkAlgorithmSuiteId::AlgAes128GcmIv12Tag16HkdfSha256EcdsaP256,
40                EsdkAlgorithmSuiteId::AlgAes192GcmIv12Tag16HkdfSha384EcdsaP384,
41                EsdkAlgorithmSuiteId::AlgAes256GcmIv12Tag16HkdfSha384EcdsaP384,
42                EsdkAlgorithmSuiteId::AlgAes256GcmHkdfSha512CommitKeyEcdsaP384,
43            ],
44            // Create a DefaultCryptographicMaterialsManager to facilitate
45            // GetEncryptionMaterials and DecryptionMaterials
46            // after this CMM approves the Algorithm Suite.
47            cmm: tokio::task::block_in_place(|| {
48                tokio::runtime::Handle::current().block_on(async {
49                    mpl.create_default_cryptographic_materials_manager()
50                        .keyring(keyring)
51                        .send()
52                        .await
53                })
54            })
55            .unwrap(),
56        }
57    }
More examples
Hide additional examples
examples/cryptographic_materials_manager/required_encryption_context/required_encryption_context_example.rs (line 75)
19pub async fn encrypt_and_decrypt_with_cmm(
20    example_data: &str,
21    kms_key_id: &str,
22) -> Result<(), crate::BoxError> {
23    // 1. Instantiate the encryption SDK client.
24    // This builds the default client with the RequireEncryptRequireDecrypt commitment policy,
25    // which enforces that this client only encrypts using committing algorithm suites and enforces
26    // that this client will only decrypt encrypted messages that were created with a committing
27    // algorithm suite.
28    let esdk_config = AwsEncryptionSdkConfig::builder().build()?;
29    let esdk_client = esdk_client::Client::from_conf(esdk_config)?;
30
31    // 2. Create a KMS client.
32    let sdk_config = aws_config::load_defaults(aws_config::BehaviorVersion::latest()).await;
33    let kms_client = aws_sdk_kms::Client::new(&sdk_config);
34
35    // 3. Create encryption context.
36    // Remember that your encryption context is NOT SECRET.
37    // For more information, see
38    // https://docs.aws.amazon.com/encryption-sdk/latest/developer-guide/concepts.html#encryption-context
39    let encryption_context = HashMap::from([
40        ("encryption".to_string(), "context".to_string()),
41        ("is not".to_string(), "secret".to_string()),
42        ("but adds".to_string(), "useful metadata".to_string()),
43        (
44            "that can help you".to_string(),
45            "be confident that".to_string(),
46        ),
47        (
48            "the data you are handling".to_string(),
49            "is what you think it is".to_string(),
50        ),
51        ("requiredKey1".to_string(), "requiredValue1".to_string()),
52        ("requiredKey2".to_string(), "requiredValue2".to_string()),
53    ]);
54
55    // 4. Create your required encryption context keys.
56    // These keys MUST be in your encryption context.
57    // These keys and their corresponding values WILL NOT be stored on the message but will be used
58    // for authentication.
59    let required_encryption_context_keys: Vec<String> =
60        vec!["requiredKey1".to_string(), "requiredKey2".to_string()];
61
62    // 5. Create a KMS keyring
63    let mpl_config = MaterialProvidersConfig::builder().build()?;
64    let mpl = mpl_client::Client::from_conf(mpl_config)?;
65
66    let kms_keyring = mpl
67        .create_aws_kms_keyring()
68        .kms_key_id(kms_key_id)
69        .kms_client(kms_client)
70        .send()
71        .await?;
72
73    // 6. Create the required encryption context CMM.
74    let underlying_cmm = mpl
75        .create_default_cryptographic_materials_manager()
76        .keyring(kms_keyring)
77        .send()
78        .await?;
79
80    let required_ec_cmm = mpl
81        .create_required_encryption_context_cmm()
82        .underlying_cmm(underlying_cmm.clone())
83        .required_encryption_context_keys(required_encryption_context_keys)
84        .send()
85        .await?;
86
87    // 7. Encrypt the data with the encryption_context
88    // NOTE: the keys "requiredKey1", and "requiredKey2"
89    // WILL NOT be stored in the message header, but "encryption", "is not",
90    // "but adds", "that can help you", and "the data you are handling" WILL be stored.
91    let plaintext = example_data.as_bytes();
92
93    let encryption_response = esdk_client
94        .encrypt()
95        .plaintext(plaintext)
96        .materials_manager(required_ec_cmm.clone())
97        .encryption_context(encryption_context.clone())
98        .send()
99        .await?;
100
101    let ciphertext = encryption_response
102        .ciphertext
103        .expect("Unable to unwrap ciphertext from encryption response");
104
105    // 8. Demonstrate that the ciphertext and plaintext are different.
106    // (This is an example for demonstration; you do not need to do this in your own code.)
107    assert_ne!(
108        ciphertext,
109        aws_smithy_types::Blob::new(plaintext),
110        "Ciphertext and plaintext data are the same. Invalid encryption"
111    );
112
113    // 9. Decrypt your encrypted data using the same keyring you used on encrypt.
114    let decryption_response = esdk_client
115        .decrypt()
116        .ciphertext(ciphertext.clone())
117        .materials_manager(required_ec_cmm.clone())
118        // Provide the encryption context that was supplied to the encrypt method
119        .encryption_context(encryption_context.clone())
120        .send()
121        .await?;
122
123    let decrypted_plaintext = decryption_response
124        .plaintext
125        .expect("Unable to unwrap plaintext from decryption response");
126
127    // 10. Demonstrate that the decrypted plaintext is identical to the original plaintext.
128    // (This is an example for demonstration; you do not need to do this in your own code.)
129    assert_eq!(
130        decrypted_plaintext,
131        aws_smithy_types::Blob::new(plaintext),
132        "Decrypted plaintext should be identical to the original plaintext. Invalid decryption"
133    );
134
135    // 11. Attempt to decrypt your encrypted data using the same cryptographic material manager
136    // you used on encrypt, but we won't pass the encryption context we DID NOT store on the message.
137    // This will fail
138    let decryption_response_without_ec = esdk_client
139        .decrypt()
140        .ciphertext(ciphertext.clone())
141        .materials_manager(required_ec_cmm.clone())
142        .send()
143        .await;
144
145    match decryption_response_without_ec {
146        Ok(_) => panic!(
147            "Decrypt without encryption context MUST \
148                            raise AwsCryptographicMaterialProvidersError"
149        ),
150        Err(AwsCryptographicMaterialProvidersError { error: _e }) => (),
151        _ => panic!("Unexpected error type"),
152    }
153
154    // 12. Decrypt your encrypted data using the same cryptographic material manager
155    // you used to encrypt, but supply encryption context that contains ONLY the encryption context that
156    // was NOT stored. This will pass.
157    let reproduced_encryption_context = HashMap::from([
158        ("requiredKey1".to_string(), "requiredValue1".to_string()),
159        ("requiredKey2".to_string(), "requiredValue2".to_string()),
160    ]);
161
162    let decryption_response_with_reproduced_ec = esdk_client
163        .decrypt()
164        .ciphertext(ciphertext.clone())
165        .materials_manager(required_ec_cmm)
166        // Provide the encryption context that was supplied to the encrypt method
167        .encryption_context(reproduced_encryption_context)
168        .send()
169        .await?;
170
171    let decrypted_plaintext_with_reproduced_ec = decryption_response_with_reproduced_ec
172        .plaintext
173        .expect("Unable to unwrap plaintext from decryption response");
174
175    // Demonstrate that the decrypted plaintext is identical to the original plaintext.
176    // (This is an example for demonstration; you do not need to do this in your own code.)
177    assert_eq!(
178        decrypted_plaintext_with_reproduced_ec,
179        aws_smithy_types::Blob::new(plaintext),
180        "Decrypted plaintext should be identical to the original plaintext. Invalid decryption"
181    );
182
183    // 13. You can decrypt the ciphertext using the underlying cmm, but not providing the
184    // encryption context with the request will result in an AwsCryptographicMaterialProvidersError
185
186    // This will pass
187    let decryption_response_with_ec_underlying_cmm = esdk_client
188        .decrypt()
189        .ciphertext(ciphertext.clone())
190        .materials_manager(underlying_cmm.clone())
191        // Provide the encryption context that was supplied to the encrypt method
192        .encryption_context(encryption_context)
193        .send()
194        .await?;
195
196    let decrypted_plaintext_with_ec_underlying_cmm = decryption_response_with_ec_underlying_cmm
197        .plaintext
198        .expect("Unable to unwrap plaintext from decryption response");
199
200    // Demonstrate that the decrypted plaintext is identical to the original plaintext.
201    // (This is an example for demonstration; you do not need to do this in your own code.)
202    assert_eq!(
203        decrypted_plaintext_with_ec_underlying_cmm,
204        aws_smithy_types::Blob::new(plaintext),
205        "Decrypted plaintext should be identical to the original plaintext. Invalid decryption"
206    );
207
208    // This will fail
209    let decryption_response_without_ec_underlying_cmm = esdk_client
210        .decrypt()
211        .ciphertext(ciphertext)
212        .materials_manager(underlying_cmm)
213        .send()
214        .await;
215
216    match decryption_response_without_ec_underlying_cmm {
217        Ok(_) => panic!(
218            "Decrypt without encryption context MUST \
219                            raise AwsCryptographicMaterialProvidersError"
220        ),
221        Err(AwsCryptographicMaterialProvidersError { error: _e }) => (),
222        _ => panic!("Unexpected error type"),
223    }
224
225    println!("Required Encryption Context CMM Example Completed Successfully");
226
227    Ok(())
228}
Source§

impl Client

Source

pub fn create_required_encryption_context_cmm( &self, ) -> CreateRequiredEncryptionContextCmmFluentBuilder

Examples found in repository?
examples/cryptographic_materials_manager/required_encryption_context/required_encryption_context_example.rs (line 81)
19pub async fn encrypt_and_decrypt_with_cmm(
20    example_data: &str,
21    kms_key_id: &str,
22) -> Result<(), crate::BoxError> {
23    // 1. Instantiate the encryption SDK client.
24    // This builds the default client with the RequireEncryptRequireDecrypt commitment policy,
25    // which enforces that this client only encrypts using committing algorithm suites and enforces
26    // that this client will only decrypt encrypted messages that were created with a committing
27    // algorithm suite.
28    let esdk_config = AwsEncryptionSdkConfig::builder().build()?;
29    let esdk_client = esdk_client::Client::from_conf(esdk_config)?;
30
31    // 2. Create a KMS client.
32    let sdk_config = aws_config::load_defaults(aws_config::BehaviorVersion::latest()).await;
33    let kms_client = aws_sdk_kms::Client::new(&sdk_config);
34
35    // 3. Create encryption context.
36    // Remember that your encryption context is NOT SECRET.
37    // For more information, see
38    // https://docs.aws.amazon.com/encryption-sdk/latest/developer-guide/concepts.html#encryption-context
39    let encryption_context = HashMap::from([
40        ("encryption".to_string(), "context".to_string()),
41        ("is not".to_string(), "secret".to_string()),
42        ("but adds".to_string(), "useful metadata".to_string()),
43        (
44            "that can help you".to_string(),
45            "be confident that".to_string(),
46        ),
47        (
48            "the data you are handling".to_string(),
49            "is what you think it is".to_string(),
50        ),
51        ("requiredKey1".to_string(), "requiredValue1".to_string()),
52        ("requiredKey2".to_string(), "requiredValue2".to_string()),
53    ]);
54
55    // 4. Create your required encryption context keys.
56    // These keys MUST be in your encryption context.
57    // These keys and their corresponding values WILL NOT be stored on the message but will be used
58    // for authentication.
59    let required_encryption_context_keys: Vec<String> =
60        vec!["requiredKey1".to_string(), "requiredKey2".to_string()];
61
62    // 5. Create a KMS keyring
63    let mpl_config = MaterialProvidersConfig::builder().build()?;
64    let mpl = mpl_client::Client::from_conf(mpl_config)?;
65
66    let kms_keyring = mpl
67        .create_aws_kms_keyring()
68        .kms_key_id(kms_key_id)
69        .kms_client(kms_client)
70        .send()
71        .await?;
72
73    // 6. Create the required encryption context CMM.
74    let underlying_cmm = mpl
75        .create_default_cryptographic_materials_manager()
76        .keyring(kms_keyring)
77        .send()
78        .await?;
79
80    let required_ec_cmm = mpl
81        .create_required_encryption_context_cmm()
82        .underlying_cmm(underlying_cmm.clone())
83        .required_encryption_context_keys(required_encryption_context_keys)
84        .send()
85        .await?;
86
87    // 7. Encrypt the data with the encryption_context
88    // NOTE: the keys "requiredKey1", and "requiredKey2"
89    // WILL NOT be stored in the message header, but "encryption", "is not",
90    // "but adds", "that can help you", and "the data you are handling" WILL be stored.
91    let plaintext = example_data.as_bytes();
92
93    let encryption_response = esdk_client
94        .encrypt()
95        .plaintext(plaintext)
96        .materials_manager(required_ec_cmm.clone())
97        .encryption_context(encryption_context.clone())
98        .send()
99        .await?;
100
101    let ciphertext = encryption_response
102        .ciphertext
103        .expect("Unable to unwrap ciphertext from encryption response");
104
105    // 8. Demonstrate that the ciphertext and plaintext are different.
106    // (This is an example for demonstration; you do not need to do this in your own code.)
107    assert_ne!(
108        ciphertext,
109        aws_smithy_types::Blob::new(plaintext),
110        "Ciphertext and plaintext data are the same. Invalid encryption"
111    );
112
113    // 9. Decrypt your encrypted data using the same keyring you used on encrypt.
114    let decryption_response = esdk_client
115        .decrypt()
116        .ciphertext(ciphertext.clone())
117        .materials_manager(required_ec_cmm.clone())
118        // Provide the encryption context that was supplied to the encrypt method
119        .encryption_context(encryption_context.clone())
120        .send()
121        .await?;
122
123    let decrypted_plaintext = decryption_response
124        .plaintext
125        .expect("Unable to unwrap plaintext from decryption response");
126
127    // 10. Demonstrate that the decrypted plaintext is identical to the original plaintext.
128    // (This is an example for demonstration; you do not need to do this in your own code.)
129    assert_eq!(
130        decrypted_plaintext,
131        aws_smithy_types::Blob::new(plaintext),
132        "Decrypted plaintext should be identical to the original plaintext. Invalid decryption"
133    );
134
135    // 11. Attempt to decrypt your encrypted data using the same cryptographic material manager
136    // you used on encrypt, but we won't pass the encryption context we DID NOT store on the message.
137    // This will fail
138    let decryption_response_without_ec = esdk_client
139        .decrypt()
140        .ciphertext(ciphertext.clone())
141        .materials_manager(required_ec_cmm.clone())
142        .send()
143        .await;
144
145    match decryption_response_without_ec {
146        Ok(_) => panic!(
147            "Decrypt without encryption context MUST \
148                            raise AwsCryptographicMaterialProvidersError"
149        ),
150        Err(AwsCryptographicMaterialProvidersError { error: _e }) => (),
151        _ => panic!("Unexpected error type"),
152    }
153
154    // 12. Decrypt your encrypted data using the same cryptographic material manager
155    // you used to encrypt, but supply encryption context that contains ONLY the encryption context that
156    // was NOT stored. This will pass.
157    let reproduced_encryption_context = HashMap::from([
158        ("requiredKey1".to_string(), "requiredValue1".to_string()),
159        ("requiredKey2".to_string(), "requiredValue2".to_string()),
160    ]);
161
162    let decryption_response_with_reproduced_ec = esdk_client
163        .decrypt()
164        .ciphertext(ciphertext.clone())
165        .materials_manager(required_ec_cmm)
166        // Provide the encryption context that was supplied to the encrypt method
167        .encryption_context(reproduced_encryption_context)
168        .send()
169        .await?;
170
171    let decrypted_plaintext_with_reproduced_ec = decryption_response_with_reproduced_ec
172        .plaintext
173        .expect("Unable to unwrap plaintext from decryption response");
174
175    // Demonstrate that the decrypted plaintext is identical to the original plaintext.
176    // (This is an example for demonstration; you do not need to do this in your own code.)
177    assert_eq!(
178        decrypted_plaintext_with_reproduced_ec,
179        aws_smithy_types::Blob::new(plaintext),
180        "Decrypted plaintext should be identical to the original plaintext. Invalid decryption"
181    );
182
183    // 13. You can decrypt the ciphertext using the underlying cmm, but not providing the
184    // encryption context with the request will result in an AwsCryptographicMaterialProvidersError
185
186    // This will pass
187    let decryption_response_with_ec_underlying_cmm = esdk_client
188        .decrypt()
189        .ciphertext(ciphertext.clone())
190        .materials_manager(underlying_cmm.clone())
191        // Provide the encryption context that was supplied to the encrypt method
192        .encryption_context(encryption_context)
193        .send()
194        .await?;
195
196    let decrypted_plaintext_with_ec_underlying_cmm = decryption_response_with_ec_underlying_cmm
197        .plaintext
198        .expect("Unable to unwrap plaintext from decryption response");
199
200    // Demonstrate that the decrypted plaintext is identical to the original plaintext.
201    // (This is an example for demonstration; you do not need to do this in your own code.)
202    assert_eq!(
203        decrypted_plaintext_with_ec_underlying_cmm,
204        aws_smithy_types::Blob::new(plaintext),
205        "Decrypted plaintext should be identical to the original plaintext. Invalid decryption"
206    );
207
208    // This will fail
209    let decryption_response_without_ec_underlying_cmm = esdk_client
210        .decrypt()
211        .ciphertext(ciphertext)
212        .materials_manager(underlying_cmm)
213        .send()
214        .await;
215
216    match decryption_response_without_ec_underlying_cmm {
217        Ok(_) => panic!(
218            "Decrypt without encryption context MUST \
219                            raise AwsCryptographicMaterialProvidersError"
220        ),
221        Err(AwsCryptographicMaterialProvidersError { error: _e }) => (),
222        _ => panic!("Unexpected error type"),
223    }
224
225    println!("Required Encryption Context CMM Example Completed Successfully");
226
227    Ok(())
228}
Source§

impl Client

Source

pub fn create_cryptographic_materials_cache( &self, ) -> CreateCryptographicMaterialsCacheFluentBuilder

Examples found in repository?
examples/keyring/aws_kms_hierarchical/shared_cache_across_hierarchical_keyrings_example.rs (line 94)
78pub async fn encrypt_and_decrypt_with_keyring(
79    example_data: &str,
80    key_store_table_name: &str,
81    logical_key_store_name: &str,
82    key_store_kms_key_id: &str,
83) -> Result<(), crate::BoxError> {
84    // 1a. Create the CryptographicMaterialsCache (CMC) to share across multiple Hierarchical Keyrings
85    // using the Material Providers Library
86    //    This CMC takes in:
87    //     - CacheType
88    let mpl_config = MaterialProvidersConfig::builder().build()?;
89    let mpl = mpl_client::Client::from_conf(mpl_config)?;
90
91    let cache: CacheType = CacheType::Default(DefaultCache::builder().entry_capacity(100).build()?);
92
93    let shared_cryptographic_materials_cache: CryptographicMaterialsCacheRef = mpl
94        .create_cryptographic_materials_cache()
95        .cache(cache)
96        .send()
97        .await?;
98
99    // 1b. Create a CacheType object for the shared_cryptographic_materials_cache
100    // Note that the `cache` parameter in the Hierarchical Keyring Input takes a `CacheType` as input
101    // Here, we pass a `Shared` CacheType that passes an already initialized shared cache.
102
103    // If you want to use a Shared Cache, you need to initialize it only once, and
104    // pass the same cache `shared_cache` to different hierarchical keyrings.
105
106    // CryptographicMaterialsCacheRef is an Rc (Reference Counted), so if you clone it to
107    // pass it to different Hierarchical Keyrings, it will still point to the same
108    // underlying cache, and increment the reference count accordingly.
109    let shared_cache: CacheType = CacheType::Shared(shared_cryptographic_materials_cache);
110
111    // 2. Instantiate the encryption SDK client.
112    // This builds the default client with the RequireEncryptRequireDecrypt commitment policy,
113    // which enforces that this client only encrypts using committing algorithm suites and enforces
114    // that this client will only decrypt encrypted messages that were created with a committing
115    // algorithm suite.
116    let esdk_config = AwsEncryptionSdkConfig::builder().build()?;
117    let esdk_client = esdk_client::Client::from_conf(esdk_config)?;
118
119    // 3. Configure your Key Store resource key_store1.
120    //    This SHOULD be the same configuration that you used
121    //    to initially create and populate your physical Key Store.
122    // Note that key_store_table_name is the physical Key Store,
123    // and key_store1 is instances of this physical Key Store.
124    let sdk_config = aws_config::load_defaults(aws_config::BehaviorVersion::latest()).await;
125    let key_store_config = KeyStoreConfig::builder()
126        .kms_client(aws_sdk_kms::Client::new(&sdk_config))
127        .ddb_client(aws_sdk_dynamodb::Client::new(&sdk_config))
128        .ddb_table_name(key_store_table_name)
129        .logical_key_store_name(logical_key_store_name)
130        .kms_configuration(KmsConfiguration::KmsKeyArn(
131            key_store_kms_key_id.to_string(),
132        ))
133        .build()?;
134
135    let key_store1 = keystore_client::Client::from_conf(key_store_config.clone())?;
136
137    // 4. Call create_branch_key_id to create one new active branch key
138    let branch_key_id: String = create_branch_key_id(
139        key_store_table_name,
140        logical_key_store_name,
141        key_store_kms_key_id,
142    )
143    .await?;
144
145    // 5. Create the Hierarchical Keyring HK1 with Key Store instance K1, partition_id,
146    // the shared_cache and the branch_key_id.
147    // Note that we are now providing an already initialized shared cache instead of just mentioning
148    // the cache type and the Hierarchical Keyring initializing a cache at initialization.
149
150    // partition_id for this example is a random UUID
151    let partition_id = "91c1b6a2-6fc3-4539-ad5e-938d597ed730".to_string();
152
153    // Please make sure that you read the guidance on how to set Partition ID, Logical Key Store Name and
154    // Branch Key ID at the top of this example before creating Hierarchical Keyrings with a Shared Cache
155    let keyring1 = mpl
156        .create_aws_kms_hierarchical_keyring()
157        .key_store(key_store1)
158        .branch_key_id(branch_key_id.clone())
159        // CryptographicMaterialsCacheRef is an Rc (Reference Counted), so if you clone it to
160        // pass it to different Hierarchical Keyrings, it will still point to the same
161        // underlying cache, and increment the reference count accordingly.
162        .cache(shared_cache.clone())
163        .ttl_seconds(600)
164        .partition_id(partition_id.clone())
165        .send()
166        .await?;
167
168    // 6. Create encryption context.
169    // Remember that your encryption context is NOT SECRET.
170    // For more information, see
171    // https://docs.aws.amazon.com/encryption-sdk/latest/developer-guide/concepts.html#encryption-context
172    let encryption_context = HashMap::from([
173        ("encryption".to_string(), "context".to_string()),
174        ("is not".to_string(), "secret".to_string()),
175        ("but adds".to_string(), "useful metadata".to_string()),
176        (
177            "that can help you".to_string(),
178            "be confident that".to_string(),
179        ),
180        (
181            "the data you are handling".to_string(),
182            "is what you think it is".to_string(),
183        ),
184    ]);
185
186    // 7. Encrypt the data for encryption_context using keyring1
187    let plaintext = example_data.as_bytes();
188
189    let encryption_response1 = esdk_client
190        .encrypt()
191        .plaintext(plaintext)
192        .keyring(keyring1.clone())
193        .encryption_context(encryption_context.clone())
194        .send()
195        .await?;
196
197    let ciphertext1 = encryption_response1
198        .ciphertext
199        .expect("Unable to unwrap ciphertext from encryption response");
200
201    // 8. Demonstrate that the ciphertexts and plaintext are different.
202    // (This is an example for demonstration; you do not need to do this in your own code.)
203    assert_ne!(
204        ciphertext1,
205        aws_smithy_types::Blob::new(plaintext),
206        "Ciphertext and plaintext data are the same. Invalid encryption"
207    );
208
209    // 9. Decrypt your encrypted data using the same keyring HK1 you used on encrypt.
210    let decryption_response1 = esdk_client
211        .decrypt()
212        .ciphertext(ciphertext1)
213        .keyring(keyring1)
214        // Provide the encryption context that was supplied to the encrypt method
215        .encryption_context(encryption_context.clone())
216        .send()
217        .await?;
218
219    let decrypted_plaintext1 = decryption_response1
220        .plaintext
221        .expect("Unable to unwrap plaintext from decryption response");
222
223    // 10. Demonstrate that the decrypted plaintext is identical to the original plaintext.
224    // (This is an example for demonstration; you do not need to do this in your own code.)
225    assert_eq!(
226        decrypted_plaintext1,
227        aws_smithy_types::Blob::new(plaintext),
228        "Decrypted plaintext should be identical to the original plaintext. Invalid decryption"
229    );
230
231    // 11. Through the above encrypt and decrypt roundtrip, the cache will be populated and
232    // the cache entries can be used by another Hierarchical Keyring with the
233    // - Same Partition ID
234    // - Same Logical Key Store Name of the Key Store for the Hierarchical Keyring
235    // - Same Branch Key ID
236
237    // Configure your Key Store resource key_store2.
238    //    This SHOULD be the same configuration that you used
239    //    to initially create and populate your physical Key Store.
240    // Note that key_store_table_name is the physical Key Store,
241    // and key_store2 is instances of this physical Key Store.
242
243    // Note that for this example, key_store2 is identical to key_store1.
244    // You can optionally change configurations like KMS Client or KMS Key ID based
245    // on your use-case.
246    // Make sure you have the required permissions to use different configurations.
247
248    // - If you want to share cache entries across two keyrings HK1 and HK2,
249    //   you should set the Logical Key Store Names for both
250    //   Key Store instances (K1 and K2) to be the same.
251    // - If you set the Logical Key Store Names for K1 and K2 to be different,
252    //   HK1 (which uses Key Store instance K1) and HK2 (which uses Key Store
253    //   instance K2) will NOT be able to share cache entries.
254    let key_store2 = keystore_client::Client::from_conf(key_store_config.clone())?;
255
256    // 12. Create the Hierarchical Keyring HK2 with Key Store instance K2, the shared_cache
257    // and the same partition_id and branch_key_id used in HK1 because we want to share cache entries
258    // (and experience cache HITS).
259
260    // Please make sure that you read the guidance on how to set Partition ID, Logical Key Store Name and
261    // Branch Key ID at the top of this example before creating Hierarchical Keyrings with a Shared Cache
262    let keyring2 = mpl
263        .create_aws_kms_hierarchical_keyring()
264        .key_store(key_store2)
265        .branch_key_id(branch_key_id)
266        .cache(shared_cache)
267        .ttl_seconds(600)
268        .partition_id(partition_id)
269        .send()
270        .await?;
271
272    // 13. This encrypt-decrypt roundtrip with HK2 will experience Cache HITS from previous HK1 roundtrip
273    // Encrypt the data for encryption_context using keyring2
274    let encryption_response2 = esdk_client
275        .encrypt()
276        .plaintext(plaintext)
277        .keyring(keyring2.clone())
278        .encryption_context(encryption_context.clone())
279        .send()
280        .await?;
281
282    let ciphertext2 = encryption_response2
283        .ciphertext
284        .expect("Unable to unwrap ciphertext from encryption response");
285
286    // 14. Demonstrate that the ciphertexts and plaintext are different.
287    // (This is an example for demonstration; you do not need to do this in your own code.)
288    assert_ne!(
289        ciphertext2,
290        aws_smithy_types::Blob::new(plaintext),
291        "Ciphertext and plaintext data are the same. Invalid encryption"
292    );
293
294    // 15. Decrypt your encrypted data using the same keyring HK2 you used on encrypt.
295    let decryption_response2 = esdk_client
296        .decrypt()
297        .ciphertext(ciphertext2)
298        .keyring(keyring2)
299        // Provide the encryption context that was supplied to the encrypt method
300        .encryption_context(encryption_context)
301        .send()
302        .await?;
303
304    let decrypted_plaintext2 = decryption_response2
305        .plaintext
306        .expect("Unable to unwrap plaintext from decryption response");
307
308    // 10. Demonstrate that the decrypted plaintext is identical to the original plaintext.
309    // (This is an example for demonstration; you do not need to do this in your own code.)
310    assert_eq!(
311        decrypted_plaintext2,
312        aws_smithy_types::Blob::new(plaintext),
313        "Decrypted plaintext should be identical to the original plaintext. Invalid decryption"
314    );
315
316    println!("Shared Cache Across Hierarchical Keyrings Example Completed Successfully");
317
318    Ok(())
319}
Source§

impl Client

Source

pub fn create_default_client_supplier( &self, ) -> CreateDefaultClientSupplierFluentBuilder

Constructs a fluent builder for the CreateDefaultClientSupplier operation.

Source§

impl Client

Source

pub fn initialize_encryption_materials( &self, ) -> InitializeEncryptionMaterialsFluentBuilder

Constructs a fluent builder for the InitializeEncryptionMaterials operation.

Source§

impl Client

Source

pub fn initialize_decryption_materials( &self, ) -> InitializeDecryptionMaterialsFluentBuilder

Source§

impl Client

Source§

impl Client

Source§

impl Client

Source

pub fn encryption_materials_has_plaintext_data_key( &self, ) -> EncryptionMaterialsHasPlaintextDataKeyFluentBuilder

Constructs a fluent builder for the EncryptionMaterialsHasPlaintextDataKey operation.

Source§

impl Client

Source§

impl Client

Source§

impl Client

Source

pub fn valid_algorithm_suite_info(&self) -> ValidAlgorithmSuiteInfoFluentBuilder

Constructs a fluent builder for the ValidAlgorithmSuiteInfo operation.

Source§

impl Client

Source§

impl Client

Source§

impl Client

Source

pub fn from_conf(input: MaterialProvidersConfig) -> Result<Self, Error>

Creates a new client from the service Config.

Examples found in repository?
examples/cryptographic_materials_manager/restrict_algorithm_suite/signing_suite_only_cmm.rs (line 35)
33    pub fn new(keyring: KeyringRef) -> Self {
34        let mpl_config = MaterialProvidersConfig::builder().build().unwrap();
35        let mpl = mpl_client::Client::from_conf(mpl_config).unwrap();
36
37        Self {
38            approved_algos: vec![
39                EsdkAlgorithmSuiteId::AlgAes128GcmIv12Tag16HkdfSha256EcdsaP256,
40                EsdkAlgorithmSuiteId::AlgAes192GcmIv12Tag16HkdfSha384EcdsaP384,
41                EsdkAlgorithmSuiteId::AlgAes256GcmIv12Tag16HkdfSha384EcdsaP384,
42                EsdkAlgorithmSuiteId::AlgAes256GcmHkdfSha512CommitKeyEcdsaP384,
43            ],
44            // Create a DefaultCryptographicMaterialsManager to facilitate
45            // GetEncryptionMaterials and DecryptionMaterials
46            // after this CMM approves the Algorithm Suite.
47            cmm: tokio::task::block_in_place(|| {
48                tokio::runtime::Handle::current().block_on(async {
49                    mpl.create_default_cryptographic_materials_manager()
50                        .keyring(keyring)
51                        .send()
52                        .await
53                })
54            })
55            .unwrap(),
56        }
57    }
More examples
Hide additional examples
examples/keyring/aws_kms_keyring_example.rs (line 66)
30pub async fn encrypt_and_decrypt_with_keyring(
31    example_data: &str,
32    kms_key_id: &str,
33) -> Result<(), crate::BoxError> {
34    // 1. Instantiate the encryption SDK client.
35    // This builds the default client with the RequireEncryptRequireDecrypt commitment policy,
36    // which enforces that this client only encrypts using committing algorithm suites and enforces
37    // that this client will only decrypt encrypted messages that were created with a committing
38    // algorithm suite.
39    let esdk_config = AwsEncryptionSdkConfig::builder().build()?;
40    let esdk_client = esdk_client::Client::from_conf(esdk_config)?;
41
42    // 2. Create a KMS client.
43    let sdk_config = aws_config::load_defaults(aws_config::BehaviorVersion::latest()).await;
44    let kms_client = aws_sdk_kms::Client::new(&sdk_config);
45
46    // 3. Create encryption context.
47    // Remember that your encryption context is NOT SECRET.
48    // For more information, see
49    // https://docs.aws.amazon.com/encryption-sdk/latest/developer-guide/concepts.html#encryption-context
50    let encryption_context = HashMap::from([
51        ("encryption".to_string(), "context".to_string()),
52        ("is not".to_string(), "secret".to_string()),
53        ("but adds".to_string(), "useful metadata".to_string()),
54        (
55            "that can help you".to_string(),
56            "be confident that".to_string(),
57        ),
58        (
59            "the data you are handling".to_string(),
60            "is what you think it is".to_string(),
61        ),
62    ]);
63
64    // 4. Create a KMS keyring
65    let mpl_config = MaterialProvidersConfig::builder().build()?;
66    let mpl = mpl_client::Client::from_conf(mpl_config)?;
67
68    let kms_keyring = mpl
69        .create_aws_kms_keyring()
70        .kms_key_id(kms_key_id)
71        .kms_client(kms_client)
72        .send()
73        .await?;
74
75    // 5. Encrypt the data with the encryption_context
76    let plaintext = example_data.as_bytes();
77
78    let encryption_response = esdk_client
79        .encrypt()
80        .plaintext(plaintext)
81        .keyring(kms_keyring.clone())
82        .encryption_context(encryption_context.clone())
83        .send()
84        .await?;
85
86    let ciphertext = encryption_response
87        .ciphertext
88        .expect("Unable to unwrap ciphertext from encryption response");
89
90    // 6. Demonstrate that the ciphertext and plaintext are different.
91    // (This is an example for demonstration; you do not need to do this in your own code.)
92    assert_ne!(
93        ciphertext,
94        aws_smithy_types::Blob::new(plaintext),
95        "Ciphertext and plaintext data are the same. Invalid encryption"
96    );
97
98    // 7. Decrypt your encrypted data using the same keyring you used on encrypt.
99    let decryption_response = esdk_client
100        .decrypt()
101        .ciphertext(ciphertext)
102        .keyring(kms_keyring)
103        // Provide the encryption context that was supplied to the encrypt method
104        .encryption_context(encryption_context)
105        .send()
106        .await?;
107
108    let decrypted_plaintext = decryption_response
109        .plaintext
110        .expect("Unable to unwrap plaintext from decryption response");
111
112    // 8. Demonstrate that the decrypted plaintext is identical to the original plaintext.
113    // (This is an example for demonstration; you do not need to do this in your own code.)
114    assert_eq!(
115        decrypted_plaintext,
116        aws_smithy_types::Blob::new(plaintext),
117        "Decrypted plaintext should be identical to the original plaintext. Invalid decryption"
118    );
119
120    println!("KMS Keyring Example Completed Successfully");
121
122    Ok(())
123}
examples/keyring/aws_kms_rsa_keyring_example.rs (line 65)
28pub async fn encrypt_and_decrypt_with_keyring(
29    example_data: &str,
30    kms_rsa_key_id: &str,
31    kms_rsa_public_key: &str,
32) -> Result<(), crate::BoxError> {
33    // 1. Instantiate the encryption SDK client.
34    // This builds the default client with the RequireEncryptRequireDecrypt commitment policy,
35    // which enforces that this client only encrypts using committing algorithm suites and enforces
36    // that this client will only decrypt encrypted messages that were created with a committing
37    // algorithm suite.
38    let esdk_config = AwsEncryptionSdkConfig::builder().build()?;
39    let esdk_client = esdk_client::Client::from_conf(esdk_config)?;
40
41    // 2. Create a KMS client.
42    let sdk_config = aws_config::load_defaults(aws_config::BehaviorVersion::latest()).await;
43    let kms_client = aws_sdk_kms::Client::new(&sdk_config);
44
45    // 3. Create encryption context.
46    // Remember that your encryption context is NOT SECRET.
47    // For more information, see
48    // https://docs.aws.amazon.com/encryption-sdk/latest/developer-guide/concepts.html#encryption-context
49    let encryption_context = HashMap::from([
50        ("encryption".to_string(), "context".to_string()),
51        ("is not".to_string(), "secret".to_string()),
52        ("but adds".to_string(), "useful metadata".to_string()),
53        (
54            "that can help you".to_string(),
55            "be confident that".to_string(),
56        ),
57        (
58            "the data you are handling".to_string(),
59            "is what you think it is".to_string(),
60        ),
61    ]);
62
63    // 4. Create a KMS RSA keyring
64    let mpl_config = MaterialProvidersConfig::builder().build()?;
65    let mpl = mpl_client::Client::from_conf(mpl_config)?;
66
67    // For more information on the allowed encryption algorithms, please see
68    // https://docs.aws.amazon.com/kms/latest/developerguide/asymmetric-key-specs.html#key-spec-rsa
69    let kms_rsa_keyring = mpl
70        .create_aws_kms_rsa_keyring()
71        .kms_key_id(kms_rsa_key_id)
72        .public_key(aws_smithy_types::Blob::new(kms_rsa_public_key))
73        .encryption_algorithm(aws_sdk_kms::types::EncryptionAlgorithmSpec::RsaesOaepSha256)
74        .kms_client(kms_client)
75        .send()
76        .await?;
77
78    // 5. Encrypt the data with the encryption_context
79    let plaintext = example_data.as_bytes();
80
81    let encryption_response = esdk_client
82        .encrypt()
83        .plaintext(plaintext)
84        .keyring(kms_rsa_keyring.clone())
85        .encryption_context(encryption_context.clone())
86        .algorithm_suite_id(EsdkAlgorithmSuiteId::AlgAes256GcmHkdfSha512CommitKey)
87        .send()
88        .await?;
89
90    let ciphertext = encryption_response
91        .ciphertext
92        .expect("Unable to unwrap ciphertext from encryption response");
93
94    // 6. Demonstrate that the ciphertext and plaintext are different.
95    // (This is an example for demonstration; you do not need to do this in your own code.)
96    assert_ne!(
97        ciphertext,
98        aws_smithy_types::Blob::new(plaintext),
99        "Ciphertext and plaintext data are the same. Invalid encryption"
100    );
101
102    // 7. Decrypt your encrypted data using the same keyring you used on encrypt.
103    let decryption_response = esdk_client
104        .decrypt()
105        .ciphertext(ciphertext)
106        .keyring(kms_rsa_keyring)
107        // Provide the encryption context that was supplied to the encrypt method
108        .encryption_context(encryption_context)
109        .send()
110        .await?;
111
112    let decrypted_plaintext = decryption_response
113        .plaintext
114        .expect("Unable to unwrap plaintext from decryption response");
115
116    // 8. Demonstrate that the decrypted plaintext is identical to the original plaintext.
117    // (This is an example for demonstration; you do not need to do this in your own code.)
118    assert_eq!(
119        decrypted_plaintext,
120        aws_smithy_types::Blob::new(plaintext),
121        "Decrypted plaintext should be identical to the original plaintext. Invalid decryption"
122    );
123
124    println!("KMS RSA Keyring Example Completed Successfully");
125
126    Ok(())
127}
examples/keyring/raw_aes_keyring_example.rs (line 75)
34pub async fn encrypt_and_decrypt_with_keyring(example_data: &str) -> Result<(), crate::BoxError> {
35    // 1. Instantiate the encryption SDK client.
36    // This builds the default client with the RequireEncryptRequireDecrypt commitment policy,
37    // which enforces that this client only encrypts using committing algorithm suites and enforces
38    // that this client will only decrypt encrypted messages that were created with a committing
39    // algorithm suite.
40    let esdk_config = AwsEncryptionSdkConfig::builder().build()?;
41    let esdk_client = esdk_client::Client::from_conf(esdk_config)?;
42
43    // 2. The key namespace and key name are defined by you.
44    // and are used by the Raw AES keyring to determine
45    // whether it should attempt to decrypt an encrypted data key.
46    // For more information, see
47    // https://docs.aws.amazon.com/encryption-sdk/latest/developer-guide/use-raw-aes-keyring.html
48    let key_namespace: &str = "my-key-namespace";
49    let key_name: &str = "my-aes-key-name";
50
51    // 3. Create encryption context.
52    // Remember that your encryption context is NOT SECRET.
53    // For more information, see
54    // https://docs.aws.amazon.com/encryption-sdk/latest/developer-guide/concepts.html#encryption-context
55    let encryption_context = HashMap::from([
56        ("encryption".to_string(), "context".to_string()),
57        ("is not".to_string(), "secret".to_string()),
58        ("but adds".to_string(), "useful metadata".to_string()),
59        (
60            "that can help you".to_string(),
61            "be confident that".to_string(),
62        ),
63        (
64            "the data you are handling".to_string(),
65            "is what you think it is".to_string(),
66        ),
67    ]);
68
69    // 4. Generate a 256-bit AES key to use with your keyring.
70    // In practice, you should get this key from a secure key management system such as an HSM.
71    let aes_key_bytes = generate_aes_key_bytes();
72
73    // 5. Create a Raw AES Keyring
74    let mpl_config = MaterialProvidersConfig::builder().build()?;
75    let mpl = mpl_client::Client::from_conf(mpl_config)?;
76
77    let raw_aes_keyring = mpl
78        .create_raw_aes_keyring()
79        .key_name(key_name)
80        .key_namespace(key_namespace)
81        .wrapping_key(aes_key_bytes)
82        .wrapping_alg(AesWrappingAlg::AlgAes256GcmIv12Tag16)
83        .send()
84        .await?;
85
86    // 6. Encrypt the data with the encryption_context
87    let plaintext = example_data.as_bytes();
88
89    let encryption_response = esdk_client
90        .encrypt()
91        .plaintext(plaintext)
92        .keyring(raw_aes_keyring.clone())
93        .encryption_context(encryption_context.clone())
94        .send()
95        .await?;
96
97    let ciphertext = encryption_response
98        .ciphertext
99        .expect("Unable to unwrap ciphertext from encryption response");
100
101    // 7. Demonstrate that the ciphertext and plaintext are different.
102    // (This is an example for demonstration; you do not need to do this in your own code.)
103    assert_ne!(
104        ciphertext,
105        aws_smithy_types::Blob::new(plaintext),
106        "Ciphertext and plaintext data are the same. Invalid encryption"
107    );
108
109    // 8. Decrypt your encrypted data using the same keyring you used on encrypt.
110    let decryption_response = esdk_client
111        .decrypt()
112        .ciphertext(ciphertext)
113        .keyring(raw_aes_keyring)
114        // Provide the encryption context that was supplied to the encrypt method
115        .encryption_context(encryption_context)
116        .send()
117        .await?;
118
119    let decrypted_plaintext = decryption_response
120        .plaintext
121        .expect("Unable to unwrap plaintext from decryption response");
122
123    // 9. Demonstrate that the decrypted plaintext is identical to the original plaintext.
124    // (This is an example for demonstration; you do not need to do this in your own code.)
125    assert_eq!(
126        decrypted_plaintext,
127        aws_smithy_types::Blob::new(plaintext),
128        "Decrypted plaintext should be identical to the original plaintext. Invalid decryption"
129    );
130
131    println!("Raw AES Keyring Example Completed Successfully");
132
133    Ok(())
134}
examples/set_encryption_algorithm_suite_example.rs (line 92)
51pub async fn encrypt_and_decrypt_with_keyring(example_data: &str) -> Result<(), crate::BoxError> {
52    // 1. Instantiate the encryption SDK client.
53    // This builds the default client with the RequireEncryptRequireDecrypt commitment policy,
54    // which enforces that this client only encrypts using committing algorithm suites and enforces
55    // that this client will only decrypt encrypted messages that were created with a committing
56    // algorithm suite.
57    let esdk_config = AwsEncryptionSdkConfig::builder().build()?;
58    let esdk_client = esdk_client::Client::from_conf(esdk_config)?;
59
60    // 2. The key namespace and key name are defined by you.
61    // and are used by the Raw AES keyring to determine
62    // whether it should attempt to decrypt an encrypted data key.
63    // For more information, see
64    // https://docs.aws.amazon.com/encryption-sdk/latest/developer-guide/use-raw-aes-keyring.html
65    let key_namespace: &str = "my-key-namespace";
66    let key_name: &str = "my-aes-key-name";
67
68    // 3. Create encryption context.
69    // Remember that your encryption context is NOT SECRET.
70    // For more information, see
71    // https://docs.aws.amazon.com/encryption-sdk/latest/developer-guide/concepts.html#encryption-context
72    let encryption_context = HashMap::from([
73        ("encryption".to_string(), "context".to_string()),
74        ("is not".to_string(), "secret".to_string()),
75        ("but adds".to_string(), "useful metadata".to_string()),
76        (
77            "that can help you".to_string(),
78            "be confident that".to_string(),
79        ),
80        (
81            "the data you are handling".to_string(),
82            "is what you think it is".to_string(),
83        ),
84    ]);
85
86    // 4. Generate a 256-bit AES key to use with your keyring.
87    // In practice, you should get this key from a secure key management system such as an HSM.
88    let aes_key_bytes = generate_aes_key_bytes();
89
90    // 5. Create a Raw AES Keyring
91    let mpl_config = MaterialProvidersConfig::builder().build()?;
92    let mpl = mpl_client::Client::from_conf(mpl_config)?;
93
94    // The wrapping algorithm here is NOT the algorithm suite we set in this example.
95    let raw_aes_keyring = mpl
96        .create_raw_aes_keyring()
97        .key_name(key_name)
98        .key_namespace(key_namespace)
99        .wrapping_key(aes_key_bytes)
100        .wrapping_alg(AesWrappingAlg::AlgAes256GcmIv12Tag16)
101        .send()
102        .await?;
103
104    // 6. Encrypt the data with the encryption_context
105    let plaintext = example_data.as_bytes();
106
107    // This is the important step in this example where we specify the algorithm suite
108    // you want to use for encrypting your data
109    let encryption_response = esdk_client
110        .encrypt()
111        .plaintext(plaintext)
112        .keyring(raw_aes_keyring.clone())
113        .encryption_context(encryption_context.clone())
114        .algorithm_suite_id(AlgAes256GcmHkdfSha512CommitKey)
115        .send()
116        .await?;
117
118    let ciphertext = encryption_response
119        .ciphertext
120        .expect("Unable to unwrap ciphertext from encryption response");
121
122    // 7. Demonstrate that the ciphertext and plaintext are different.
123    // (This is an example for demonstration; you do not need to do this in your own code.)
124    assert_ne!(
125        ciphertext,
126        aws_smithy_types::Blob::new(plaintext),
127        "Ciphertext and plaintext data are the same. Invalid encryption"
128    );
129
130    // 8. Decrypt your encrypted data using the same keyring you used on encrypt.
131    let decryption_response = esdk_client
132        .decrypt()
133        .ciphertext(ciphertext)
134        .keyring(raw_aes_keyring)
135        // Provide the encryption context that was supplied to the encrypt method
136        .encryption_context(encryption_context)
137        .send()
138        .await?;
139
140    let decrypted_plaintext = decryption_response
141        .plaintext
142        .expect("Unable to unwrap plaintext from decryption response");
143
144    // 9. Demonstrate that the decrypted plaintext is identical to the original plaintext.
145    // (This is an example for demonstration; you do not need to do this in your own code.)
146    assert_eq!(
147        decrypted_plaintext,
148        aws_smithy_types::Blob::new(plaintext),
149        "Decrypted plaintext should be identical to the original plaintext. Invalid decryption"
150    );
151
152    println!("Set Encryption Algorithm Suite Example Completed Successfully");
153
154    Ok(())
155}
examples/set_commitment_policy_example.rs (line 75)
34pub async fn encrypt_and_decrypt_with_keyring(
35    example_data: &str,
36    kms_key_id: &str,
37) -> Result<(), crate::BoxError> {
38    // 1. Instantiate the encryption SDK client.
39    // This example builds the client with the ForbidEncryptAllowDecrypt commitment policy,
40    // which enforces that this client cannot encrypt with key commitment
41    // and it can decrypt ciphertexts encrypted with or without key commitment.
42    // The default commitment policy if you were to build the client like in
43    // the `keyring/aws_kms_keyring_example.rs` is RequireEncryptRequireDecrypt.
44    // We recommend that AWS Encryption SDK users use the default commitment policy
45    // (RequireEncryptRequireDecrypt) whenever possible.
46    let esdk_config = AwsEncryptionSdkConfig::builder()
47        .commitment_policy(ForbidEncryptAllowDecrypt)
48        .build()?;
49    let esdk_client = esdk_client::Client::from_conf(esdk_config)?;
50
51    // 2. Create a KMS client.
52    let sdk_config = aws_config::load_defaults(aws_config::BehaviorVersion::latest()).await;
53    let kms_client = aws_sdk_kms::Client::new(&sdk_config);
54
55    // 3. Create encryption context.
56    // Remember that your encryption context is NOT SECRET.
57    // For more information, see
58    // https://docs.aws.amazon.com/encryption-sdk/latest/developer-guide/concepts.html#encryption-context
59    let encryption_context = HashMap::from([
60        ("encryption".to_string(), "context".to_string()),
61        ("is not".to_string(), "secret".to_string()),
62        ("but adds".to_string(), "useful metadata".to_string()),
63        (
64            "that can help you".to_string(),
65            "be confident that".to_string(),
66        ),
67        (
68            "the data you are handling".to_string(),
69            "is what you think it is".to_string(),
70        ),
71    ]);
72
73    // 4. Create a KMS keyring
74    let mpl_config = MaterialProvidersConfig::builder().build()?;
75    let mpl = mpl_client::Client::from_conf(mpl_config)?;
76
77    let kms_keyring = mpl
78        .create_aws_kms_keyring()
79        .kms_key_id(kms_key_id)
80        .kms_client(kms_client)
81        .send()
82        .await?;
83
84    // 5. Encrypt the data with the encryption_context. Make sure you use a non-committing algorithm
85    // with the commitment policy ForbidEncryptAllowDecrypt. Otherwise esdk_client.encrypt() will throw
86    // Error: AwsCryptographicMaterialProvidersError
87    //   {
88    //     error: InvalidAlgorithmSuiteInfoOnEncrypt
89    //     {
90    //       message: "Configuration conflict. Commitment policy requires only non-committing algorithm suites"
91    //     }
92    //   }
93    // By default for ForbidEncryptAllowDecrypt, the algorithm used is
94    // AlgAes256GcmIv12Tag16HkdfSha384EcdsaP384 which is a non-committing algorithm.
95    let plaintext = example_data.as_bytes();
96
97    let encryption_response = esdk_client
98        .encrypt()
99        .plaintext(plaintext)
100        .keyring(kms_keyring.clone())
101        .encryption_context(encryption_context.clone())
102        .send()
103        .await?;
104
105    let ciphertext = encryption_response
106        .ciphertext
107        .expect("Unable to unwrap ciphertext from encryption response");
108
109    // 6. Demonstrate that the ciphertext and plaintext are different.
110    // (This is an example for demonstration; you do not need to do this in your own code.)
111    assert_ne!(
112        ciphertext,
113        aws_smithy_types::Blob::new(plaintext),
114        "Ciphertext and plaintext data are the same. Invalid encryption"
115    );
116
117    // 7. Decrypt your encrypted data using the same keyring you used on encrypt.
118    let decryption_response = esdk_client
119        .decrypt()
120        .ciphertext(ciphertext)
121        .keyring(kms_keyring)
122        // Provide the encryption context that was supplied to the encrypt method
123        .encryption_context(encryption_context)
124        .send()
125        .await?;
126
127    let decrypted_plaintext = decryption_response
128        .plaintext
129        .expect("Unable to unwrap plaintext from decryption response");
130
131    // 8. Demonstrate that the decrypted plaintext is identical to the original plaintext.
132    // (This is an example for demonstration; you do not need to do this in your own code.)
133    assert_eq!(
134        decrypted_plaintext,
135        aws_smithy_types::Blob::new(plaintext),
136        "Decrypted plaintext should be identical to the original plaintext. Invalid decryption"
137    );
138
139    println!("Set Commitment Policy Example Completed Successfully");
140
141    Ok(())
142}

Trait Implementations§

Source§

impl Clone for Client

Source§

fn clone(&self) -> Client

Returns a duplicate of the value. Read more
1.0.0 · Source§

fn clone_from(&mut self, source: &Self)

Performs copy-assignment from source. Read more
Source§

impl Debug for Client

Source§

fn fmt(&self, f: &mut Formatter<'_>) -> Result

Formats the value using the given formatter. Read more
Source§

impl PartialEq for Client

Source§

fn eq(&self, other: &Client) -> bool

Tests for self and other values to be equal, and is used by ==.
1.0.0 · Source§

fn ne(&self, other: &Rhs) -> bool

Tests for !=. The default implementation is almost always sufficient, and should not be overridden without very good reason.
Source§

impl StructuralPartialEq for Client

Auto Trait Implementations§

§

impl Freeze for Client

§

impl !RefUnwindSafe for Client

§

impl Send for Client

§

impl Sync for Client

§

impl Unpin for Client

§

impl !UnwindSafe for Client

Blanket Implementations§

Source§

impl<T> Any for T
where T: 'static + ?Sized,

Source§

fn type_id(&self) -> TypeId

Gets the TypeId of self. Read more
Source§

impl<T> AnyRef for T
where T: 'static,

Source§

fn as_any_ref(&self) -> &(dyn Any + 'static)

Source§

impl<T> Borrow<T> for T
where T: ?Sized,

Source§

fn borrow(&self) -> &T

Immutably borrows from an owned value. Read more
Source§

impl<T> BorrowMut<T> for T
where T: ?Sized,

Source§

fn borrow_mut(&mut self) -> &mut T

Mutably borrows from an owned value. Read more
Source§

impl<T> CloneToUninit for T
where T: Clone,

Source§

unsafe fn clone_to_uninit(&self, dest: *mut u8)

🔬This is a nightly-only experimental API. (clone_to_uninit)
Performs copy-assignment from self to dest. Read more
Source§

impl<T> From<T> for T

Source§

fn from(t: T) -> T

Returns the argument unchanged.

Source§

impl<T> Instrument for T

Source§

fn instrument(self, span: Span) -> Instrumented<Self>

Instruments this type with the provided Span, returning an Instrumented wrapper. Read more
Source§

fn in_current_span(self) -> Instrumented<Self>

Instruments this type with the current Span, returning an Instrumented wrapper. Read more
Source§

impl<T, U> Into<U> for T
where U: From<T>,

Source§

fn into(self) -> U

Calls U::from(self).

That is, this conversion is whatever the implementation of From<T> for U chooses to do.

Source§

impl<T> IntoEither for T

Source§

fn into_either(self, into_left: bool) -> Either<Self, Self>

Converts self into a Left variant of Either<Self, Self> if into_left is true. Converts self into a Right variant of Either<Self, Self> otherwise. Read more
Source§

fn into_either_with<F>(self, into_left: F) -> Either<Self, Self>
where F: FnOnce(&Self) -> bool,

Converts self into a Left variant of Either<Self, Self> if into_left(&self) returns true. Converts self into a Right variant of Either<Self, Self> otherwise. Read more
Source§

impl<Unshared, Shared> IntoShared<Shared> for Unshared
where Shared: FromUnshared<Unshared>,

Source§

fn into_shared(self) -> Shared

Creates a shared type from an unshared type.
Source§

impl<T> Same for T

Source§

type Output = T

Should always be Self
Source§

impl<T> ToOwned for T
where T: Clone,

Source§

type Owned = T

The resulting type after obtaining ownership.
Source§

fn to_owned(&self) -> T

Creates owned data from borrowed data, usually by cloning. Read more
Source§

fn clone_into(&self, target: &mut T)

Uses borrowed data to replace owned data, usually by cloning. Read more
Source§

impl<T, U> TryFrom<U> for T
where U: Into<T>,

Source§

type Error = Infallible

The type returned in the event of a conversion error.
Source§

fn try_from(value: U) -> Result<T, <T as TryFrom<U>>::Error>

Performs the conversion.
Source§

impl<T, U> TryInto<U> for T
where U: TryFrom<T>,

Source§

type Error = <U as TryFrom<T>>::Error

The type returned in the event of a conversion error.
Source§

fn try_into(self) -> Result<U, <U as TryFrom<T>>::Error>

Performs the conversion.
Source§

impl<T> Upcast<T> for T
where T: ?Sized,

Source§

fn upcast(&self) -> Ptr<T>

Source§

impl<T> UpcastObject<T> for T
where T: ?Sized,

Source§

fn upcast(&self) -> Object<T>

Source§

impl<V, T> VZip<V> for T
where V: MultiLane<T>,

Source§

fn vzip(self) -> V

Source§

impl<T> WithSubscriber for T

Source§

fn with_subscriber<S>(self, subscriber: S) -> WithDispatch<Self>
where S: Into<Dispatch>,

Attaches the provided Subscriber to this type, returning a WithDispatch wrapper. Read more
Source§

fn with_current_subscriber(self) -> WithDispatch<Self>

Attaches the current default Subscriber to this type, returning a WithDispatch wrapper. Read more