This topic describes how to encrypt data locally and upload it to Cloud Storage with Tink and Cloud Key Management Service (Cloud KMS). Tink is an open source cryptography library written by cryptographers and security engineers at Google.
Overview
Client-side encryption is any encryption performed prior to sending your data to the cloud. When using client-side encryption, you're responsible for creating and managing your encryption keys and encrypting your data before sending it to the cloud.
In this topic, you implement client-side envelope encryption with Tink using an encryption key in Cloud KMS.
You can find a Terraform-based blueprint version of this tutorial in the kms-solutions GitHub repository.
Before you begin
- Create a symmetric Cloud KMS encryption key for encryption. Take note of the URI of the key. You need it later.
- Install Tink for use with Cloud KMS.
- Create a bucket in Cloud Storage to upload your encrypted data.
Required roles
To ensure that your service account has the necessary
permissions to use Cloud KMS keys with Tink,
ask your administrator to grant your service account the
Cloud KMS CryptoKey Encrypter/Decrypter (roles/cloudkms.cryptoKeyEncrypterDecrypter
) IAM role on your key.
For more information about granting roles, see Manage access to projects, folders, and organizations.
Your administrator might also be able to give your service account the required permissions through custom roles or other predefined roles.
Envelope encryption with Tink
In envelope encryption, the Cloud KMS key acts as a key encryption key (KEK). That is, it's used to encrypt data encryption keys (DEK) which in turn are used to encrypt actual data.
After creating a KEK in Cloud KMS, to encrypt each message you must:
- Generate a data encryption key (DEK) locally.
- Use the DEK locally to encrypt the message.
- Use Cloud KMS to encrypt (wrap) the DEK with the KEK.
- Store the encrypted data and the wrapped DEK.
You don't need to implement this envelope encryption process from scratch when you use Tink.
To use Tink for envelope encryption, you provide Tink with a key URI and credentials. The key URI points to your KEK in Cloud KMS, and the credentials let Tink use the KEK. Tink generates the DEK, encrypts the data, wraps the DEK, and then returns a single ciphertext with the encrypted data and wrapped DEK.
Tink supports envelope encryption in Python, Java, C++, and Go using the Authenticated Encryption with Associated Data (AEAD) primitive.
Connect Tink and Cloud KMS
To encrypt the DEKs generated by Tink with your KEK in Cloud KMS, you need to get the URI of your KEK. In Cloud KMS, the KEK URI has the following format:
gcp-kms://projects/PROJECT_ID/locations/LOCATION/keyRings/KEY_RING/cryptoKeys/KEY_NAME/cryptoKeyVersions/KEY_VERSION
See Getting a Cloud KMS resource ID for details on how to get the path to your key.
Initialize Tink and encrypt data
Tink uses primitives—cryptographic building blocks that manage the details of their underlying algorithms—so you can perform tasks safely. Each primitive offers an API that handles a specific task. Here, we're using AEAD, so we use the Tink AEAD primitive.
Python
To learn how to install and use the client library for Cloud KMS, see
Cloud KMS client libraries.
To authenticate to Cloud KMS, set up Application Default Credentials.
For more information, see
Set up authentication for a local development environment.
Python
Java
To learn how to install and use the client library for Cloud KMS, see
Cloud KMS client libraries.
To authenticate to Cloud KMS, set up Application Default Credentials.
For more information, see
Set up authentication for a local development environment.
Java
For more information about the primitives and interfaces supported by Tink, see the Get started page for Tink.
What's next?
- Learn more about Tink.
- Learn how to use client-side encryption with Cloud SQL.