Skip to content

Commit ffe0270

Browse files
committed
updated mpl examples in README
1 parent 9f12c96 commit ffe0270

File tree

1 file changed

+204
-25
lines changed

1 file changed

+204
-25
lines changed

README.rst

Lines changed: 204 additions & 25 deletions
Original file line numberDiff line numberDiff line change
@@ -101,7 +101,6 @@ Please avoid using these and instead use components in the MPL.
101101
Master Key Providers
102102
--------------------
103103
Master key providers are resources that provide master keys.
104-
An example of a master key provider is `AWS KMS`_.
105104

106105
To encrypt data in this client, a ``MasterKeyProvider`` object must contain at least one ``MasterKey`` object.
107106

@@ -115,7 +114,7 @@ Please install this library and migrate master key providers to keyring interfac
115114
Master Keys
116115
-----------
117116
Master keys generate, encrypt, and decrypt data keys.
118-
An example of a master key is a `KMS customer master key (CMK)`_.
117+
An example of a master key is an `AWS KMS key`_.
119118

120119
NOTE: Master keys are deprecated
121120
and have been superseded by keyrings
@@ -154,13 +153,13 @@ Note: You must also install the `AWS Cryptographic Material Providers Library (M
154153

155154
AwsKmsKeyring
156155
=============================
157-
A ``AwsKmsKeyring`` is configured with an AWS KMS key ARN whose AWS KMS key
156+
An ``AwsKmsKeyring`` is configured with an AWS KMS key ARN whose AWS KMS key
158157
will be used to generate, encrypt, and decrypt data keys.
159158
On encryption, it encrypts the plaintext with the data key.
160159
On decryption, it decrypts an encrypted version of the data key,
161160
then uses the decrypted data key to decrypt the ciphertext.
162161

163-
To create a ``AwsKmsKeyring`` you must provide a AWS KMS key ARN.
162+
To create an ``AwsKmsKeyring`` you must provide a AWS KMS key ARN.
164163
For keyrings that will only be used for encryption,
165164
you can use any valid `KMS key identifier`_.
166165
For providers that will be used for decryption,
@@ -174,46 +173,209 @@ pre-existing instance of a ``botocore session`` to the ``AwsKmsKeyring``.
174173
This latter option can be useful if you have an alternate way to store your AWS credentials or
175174
you want to reuse an existing instance of a botocore session in order to decrease startup costs.
176175

177-
TODO-MPL: Code example
176+
.. code:: python
177+
178+
import boto3
179+
from aws_cryptographic_materialproviders.mpl import AwsCryptographicMaterialProviders
180+
from aws_cryptographic_materialproviders.mpl.config import MaterialProvidersConfig
181+
from aws_cryptographic_materialproviders.mpl.models import CreateAwsKmsKeyringInput
182+
from aws_cryptographic_materialproviders.mpl.references import IKeyring
183+
184+
import aws_encryption_sdk
185+
from aws_encryption_sdk import CommitmentPolicy
186+
187+
# Instantiate the encryption SDK client.
188+
client = aws_encryption_sdk.EncryptionSDKClient(
189+
commitment_policy=CommitmentPolicy.REQUIRE_ENCRYPT_REQUIRE_DECRYPT
190+
)
191+
192+
# Create a KMS keyring.
193+
mat_prov: AwsCryptographicMaterialProviders = AwsCryptographicMaterialProviders(
194+
config=MaterialProvidersConfig()
195+
)
196+
197+
keyring_input: CreateAwsKmsKeyringInput = CreateAwsKmsKeyringInput(
198+
kms_key_id='arn:aws:kms:us-east-1:2222222222222:key/22222222-2222-2222-2222-222222222222',
199+
kms_client=boto3.client('kms', region_name="us-east-1")
200+
)
201+
202+
kms_keyring: IKeyring = mat_prov.create_aws_kms_keyring(
203+
input=keyring_input
204+
)
205+
178206
179207
If you want to configure a keyring with multiple AWS KMS keys, see the multi-keyring.
180208

181209
MultiKeyring
182210
============
183211

184-
A ``MultiKeyring`` is configured with an optional generator keyring and a list of child keyrings.
212+
A ``MultiKeyring`` is configured with an optional generator keyring and a list of
213+
child keyrings of the same or a different type.
214+
215+
The effect is like using several keyrings in a series. When you use a multi-keyring to
216+
encrypt data, any of the wrapping keys in any of its keyrings can decrypt that data.
185217

186-
TODO-MPL: More words
218+
.. code:: python
219+
220+
import boto3
221+
from aws_cryptographic_materialproviders.mpl import AwsCryptographicMaterialProviders
222+
from aws_cryptographic_materialproviders.mpl.config import MaterialProvidersConfig
223+
from aws_cryptographic_materialproviders.mpl.models import CreateAwsKmsMultiKeyringInput
224+
from aws_cryptographic_materialproviders.mpl.references import IKeyring
225+
226+
import aws_encryption_sdk
227+
from aws_encryption_sdk import CommitmentPolicy
228+
229+
# Instantiate the encryption SDK client.
230+
client = aws_encryption_sdk.EncryptionSDKClient(
231+
commitment_policy=CommitmentPolicy.REQUIRE_ENCRYPT_REQUIRE_DECRYPT
232+
)
233+
234+
# Create an AwsKmsMultiKeyring that protects your data under two different KMS Keys.
235+
# Either KMS Key individually is capable of decrypting data encrypted under this Multi Keyring.
236+
mat_prov: AwsCryptographicMaterialProviders = AwsCryptographicMaterialProviders(
237+
config=MaterialProvidersConfig()
238+
)
239+
240+
kms_multi_keyring_input: CreateAwsKmsMultiKeyringInput = CreateAwsKmsMultiKeyringInput(
241+
generator='arn:aws:kms:us-east-1:2222222222222:key/22222222-2222-2222-2222-222222222222',
242+
kms_key_ids=['arn:aws:kms:us-east-1:3333333333333:key/33333333-3333-3333-3333-333333333333']
243+
)
244+
245+
kms_multi_keyring: IKeyring = mat_prov.create_aws_kms_multi_keyring(
246+
input=kms_multi_keyring_input
247+
)
187248
188-
TODO-MPL: Code example
189249
190250
AwsKmsDiscoveryKeyring
191251
======================
192252
We recommend using an ``AwsKmsKeyring`` in order to ensure that you can only
193253
encrypt and decrypt data using the AWS KMS key ARN you expect,
194254
or a ``MultiKeyring`` if you are using multiple keys. However, if you are unable to
195255
explicitly identify the AWS KMS key ARNs that should be used for decryption, you can instead
196-
use a ``AwsKmsDiscoveryKeyring`` for decryption operations. This provider
256+
use an ``AwsKmsDiscoveryKeyring`` for decryption operations. This provider
197257
attempts decryption of any ciphertexts as long as they match a ``DiscoveryFilter`` that
198258
you configure. A ``DiscoveryFilter`` consists of a list of AWS account ids and an AWS
199259
partition.
200260

201-
TODO-MPL: Code example
261+
.. code:: python
262+
263+
import boto3
264+
from aws_cryptographic_materialproviders.mpl import AwsCryptographicMaterialProviders
265+
from aws_cryptographic_materialproviders.mpl.config import MaterialProvidersConfig
266+
ffrom aws_cryptographic_materialproviders.mpl.models import (
267+
CreateAwsKmsDiscoveryKeyringInput,
268+
DiscoveryFilter,
269+
)
270+
from aws_cryptographic_materialproviders.mpl.references import IKeyring
271+
272+
import aws_encryption_sdk
273+
from aws_encryption_sdk import CommitmentPolicy
274+
275+
# Instantiate the encryption SDK client.
276+
client = aws_encryption_sdk.EncryptionSDKClient(
277+
commitment_policy=CommitmentPolicy.REQUIRE_ENCRYPT_REQUIRE_DECRYPT
278+
)
279+
280+
# Create a Discovery keyring to use for decryption
281+
mat_prov: AwsCryptographicMaterialProviders = AwsCryptographicMaterialProviders(
282+
config=MaterialProvidersConfig()
283+
)
284+
285+
discovery_keyring_input: CreateAwsKmsDiscoveryKeyringInput = CreateAwsKmsDiscoveryKeyringInput(
286+
kms_client=boto3.client('kms', region_name="us-east-1"),
287+
discovery_filter=DiscoveryFilter(
288+
account_ids=["2222222222222"],
289+
partition="aws"
290+
)
291+
)
292+
293+
discovery_keyring: IKeyring = mat_prov.create_aws_kms_discovery_keyring(
294+
input=discovery_keyring_input
295+
)
296+
202297
203298
If you do not want to filter the set of allowed accounts, you can also omit the ``discovery_filter`` argument.
204299

205-
Note that a ``AwsKmsDiscoveryKeyring`` cannot be used for encryption operations.
300+
Note that an ``AwsKmsDiscoveryKeyring`` cannot be used for encryption operations.
206301

207302
Encryption and Decryption
208303
=========================
209304
After you create an instance of an ``EncryptionSDKClient`` and a ``Keyring``, you can use either of
210305
the client's two ``encrypt``/``decrypt`` functions to encrypt and decrypt your data.
211306

212-
TODO-MPL: Code example; basic example with keyring
307+
Here's an example for using a KMS keyring for encryption and decryption:
308+
309+
.. code:: python
310+
311+
# Encrypt the data.
312+
my_ciphertext, enc_header = client.encrypt(
313+
source=my_plaintext,
314+
keyring=kms_keyring
315+
)
316+
317+
# Decrypt your encrypted data.
318+
my_decrypted_plaintext, dec_header = client.decrypt(
319+
source=my_ciphertext,
320+
keyring=kms_keyring
321+
)
213322
214323
You can provide an `encryption context`_: a form of additional authenticating information.
215324

216-
TODO-MPL: Code example with encryption context
325+
Here's an example for using KMS keyring with an encryption context:
326+
327+
.. code:: python
328+
329+
import boto3
330+
from aws_cryptographic_materialproviders.mpl import AwsCryptographicMaterialProviders
331+
from aws_cryptographic_materialproviders.mpl.config import MaterialProvidersConfig
332+
from aws_cryptographic_materialproviders.mpl.models import CreateAwsKmsKeyringInput
333+
from aws_cryptographic_materialproviders.mpl.references import IKeyring
334+
335+
import aws_encryption_sdk
336+
from aws_encryption_sdk import CommitmentPolicy
337+
338+
# Instantiate the encryption SDK client.
339+
client = aws_encryption_sdk.EncryptionSDKClient(
340+
commitment_policy=CommitmentPolicy.REQUIRE_ENCRYPT_REQUIRE_DECRYPT
341+
)
342+
343+
# Create an encryption context
344+
encryption_context: Dict[str, str] = {
345+
"encryption": "context",
346+
"is not": "secret",
347+
"but adds": "useful metadata",
348+
"that can help you": "be confident that",
349+
"the data you are handling": "is what you think it is",
350+
}
351+
352+
# Create a KMS keyring.
353+
mat_prov: AwsCryptographicMaterialProviders = AwsCryptographicMaterialProviders(
354+
config=MaterialProvidersConfig()
355+
)
356+
357+
keyring_input: CreateAwsKmsKeyringInput = CreateAwsKmsKeyringInput(
358+
kms_key_id='arn:aws:kms:us-east-1:2222222222222:key/22222222-2222-2222-2222-222222222222',
359+
kms_client=boto3.client('kms', region_name="us-east-1")
360+
)
361+
362+
kms_keyring: IKeyring = mat_prov.create_aws_kms_keyring(
363+
input=keyring_input
364+
)
365+
366+
# Encrypt the data with the encryptionContext.
367+
my_ciphertext, enc_header = client.encrypt(
368+
source=my_plaintext,
369+
keyring=kms_keyring,
370+
encryption_context=encryption_context
371+
)
372+
373+
# Decrypt your encrypted data.
374+
my_decrypted_plaintext, dec_header = client.decrypt(
375+
source=my_ciphertext,
376+
keyring=kms_keyring
377+
)
378+
217379
218380
Streaming
219381
=========
@@ -222,50 +384,67 @@ memory at once, you can use this library's streaming clients directly. The strea
222384
file-like objects, and behave exactly as you would expect a Python file object to behave,
223385
offering context manager and iteration support.
224386

225-
TODO-MPL: Update code example to use a keyring
226-
227387
.. code:: python
228388
389+
import boto3
390+
from aws_cryptographic_materialproviders.mpl import AwsCryptographicMaterialProviders
391+
from aws_cryptographic_materialproviders.mpl.config import MaterialProvidersConfig
392+
from aws_cryptographic_materialproviders.mpl.models import CreateAwsKmsKeyringInput
393+
from aws_cryptographic_materialproviders.mpl.references import IKeyring
394+
229395
import aws_encryption_sdk
230-
from aws_encryption_sdk.identifiers import CommitmentPolicy
231-
import filecmp
396+
from aws_encryption_sdk import CommitmentPolicy
232397
398+
# Instantiate the encryption SDK client.
233399
client = aws_encryption_sdk.EncryptionSDKClient(
234-
commitment_policy=CommitmentPolicy.FORBID_ENCRYPT_ALLOW_DECRYPT
400+
commitment_policy=CommitmentPolicy.REQUIRE_ENCRYPT_ALLOW_DECRYPT
401+
)
402+
403+
# Create a keyring.
404+
mat_prov: AwsCryptographicMaterialProviders = AwsCryptographicMaterialProviders(
405+
config=MaterialProvidersConfig()
406+
)
407+
408+
keyring_input: CreateAwsKmsKeyringInput = CreateAwsKmsKeyringInput(
409+
kms_key_id='arn:aws:kms:us-east-1:2222222222222:key/22222222-2222-2222-2222-222222222222',
410+
kms_client=boto3.client('kms', region_name="us-east-1")
411+
)
412+
413+
kms_keyring: IKeyring = mat_prov.create_aws_kms_keyring(
414+
input=keyring_input
235415
)
236416
237-
# TODO-MPL: create a keyring
238417
plaintext_filename = 'my-secret-data.dat'
239418
ciphertext_filename = 'my-encrypted-data.ct'
240419
420+
# Encrypt the data stream.
241421
with open(plaintext_filename, 'rb') as pt_file, open(ciphertext_filename, 'wb') as ct_file:
242422
with client.stream(
243423
mode='e',
244424
source=pt_file,
245-
keyring = # TODO-MPL: provide keyring
425+
keyring=kms_keyring
246426
) as encryptor:
247427
for chunk in encryptor:
248428
ct_file.write(chunk)
249429
250430
decrypted_filename = 'my-decrypted-data.dat'
251431
432+
# Decrypt your encrypted data stream.
252433
with open(ciphertext_filename, 'rb') as ct_file, open(decrypted_filename, 'wb') as pt_file:
253434
with client.stream(
254435
mode='d',
255436
source=ct_file,
256-
keyring = # TODO-MPL: provide keyring
437+
keyring=kms_keyring
257438
) as decryptor:
258439
for chunk in decryptor:
259440
pt_file.write(chunk)
260441
261-
assert filecmp.cmp(plaintext_filename, decrypted_filename)
262-
assert encryptor.header.encryption_context == decryptor.header.encryption_context
263442
264443
Performance Considerations
265444
==========================
266445
Adjusting the frame size can significantly improve the performance of encrypt/decrypt operations with this library.
267446

268-
Processing each frame in a framed message involves a certain amount of overhead. If you are encrypting a large file,
447+
Processing each frame in a framed message involves a certain amount of overhead. If you are encrypting a large file,
269448
increasing the frame size can offer potentially significant performance gains. We recommend that you tune these values
270449
to your use-case in order to obtain peak performance.
271450

@@ -297,7 +476,7 @@ sharing entries in that cache across threads needs to be done carefully
297476
.. _Read the Docs: http://aws-encryption-sdk-python.readthedocs.io/en/latest/
298477
.. _GitHub: https://github.com/aws/aws-encryption-sdk-python/
299478
.. _AWS KMS: https://docs.aws.amazon.com/kms/latest/developerguide/overview.html
300-
.. _KMS customer master key (CMK): https://docs.aws.amazon.com/kms/latest/developerguide/concepts.html#master_keys
479+
.. _AWS KMS key: https://docs.aws.amazon.com/kms/latest/developerguide/concepts.html#master_keys
301480
.. _KMS key identifier: https://docs.aws.amazon.com/kms/latest/developerguide/concepts.html#key-id
302481
.. _boto3 SDK: https://boto3.readthedocs.io/en/latest/
303482
.. _standard means by which boto3 locates credentials: https://boto3.readthedocs.io/en/latest/guide/configuration.html

0 commit comments

Comments
 (0)