Menu Docs
Página inicial do Docs
/
Manual do MongoDB
/ / / / /

Criptografia explícita

Nesta página

  • Visão geral
  • Usar criptografia explícita
  • Criar uma Instância do ClientEncryption
  • Criptografar campos em operações de leitura e gravação
  • Descriptografia manual
  • Descriptografia automática
  • Exemplo
  • Criar uma instância do MongoClient
  • Criar uma Instância do ClientEncryption
  • Criptografar campos e inserir
  • Recuperar documento e descriptografar campos
  • Aplicação de criptografia em nível de campo no lado do servidor
  • Saiba mais

Saiba como usar o mecanismo de criptografia explícita da CSFLE (Criptografia de Nível de Campo do Lado do Cliente).

A criptografia explícita é um mecanismo no qual você especifica como criptografar e descriptografar campos em seu documento para cada operação executada em seu banco de dados.

A criptografia explícita está disponível nos seguintes produtos MongoDB da versão 4.2 ou posterior:

  • Servidor MongoDB Community

  • MongoDB Enterprise Advanced

  • MongoDB Atlas

Para usar criptografia explícita, você deve executar as seguintes ações em seu aplicativo habilitado para CSFLE:

  • Criar uma Instância do ClientEncryption

  • Criptografar campos em operações de leitura e gravação

  • Descriptografar manualmente ou automaticamente os campos em seus documentos

Para usar a criptografia explícita, crie uma instância do ClientEncryption . ClientEncryption é uma abstração usada entre drivers e mongosh que encapsula Key Vault Collection e operações doKMS envolvidas na criptografia explícita.

Para criar uma instância do ClientEncryption, você deve especificar as seguintes informações:

  • Uma instância do MongoClient com acesso à sua coleção do Key Vault

  • O namespace da sua coleção do Key Vault

  • Um objeto kmsProviders configurado com acesso ao provedor de KMS que hospeda sua chave mestra do cliente

Para mais opções do ClientEncryption, consulte Opções do MongoClient específicas do CSFLE.

Para visualizar trechos de código que mostram como criar uma instância do ClientEncryption, consulte a seção Exemplo deste guia.

Você deve atualizar as operações de leitura e gravação em todo o aplicativo para que ele criptografe os campos antes de executar operações de leitura e gravação.

Para criptografar campos, use o método encrypt de sua instância ClientEncryption.

Para ver trechos de código que mostram como usar o método encrypt, consulte a seção Exemplo deste guia.

Você pode descriptografar seus campos criptografados manualmente ou automaticamente ao usar criptografia explícita.

Para descriptografar seus campos manualmente, use o método decrypt da sua instância do ClientEncryption.

Para ver trechos de código que mostram como usar o método decrypt, consulte a seção Exemplo deste guia.

Para descriptografar seus campos automaticamente, configure sua instância do MongoClient como segue:

  • Especifique sua coleção do Key Vault

  • Especifique um objeto kmsProviders

  • Se você utilizar o servidor da comunidade MongoDB, configure a opção bypassAutoEncryption para True

Observação

A descriptografia automática está disponível no servidor da comunidade MongoDB

Embora a criptografia automática exija o MongoDB Enterprise ou o MongoDB Atlas, a descriptografia automática está disponível nos seguintes produtos do MongoDB:

  • Servidor MongoDB Community

  • MongoDB Enterprise Advanced

  • MongoDB Atlas

Para visualizar um trecho de código que demonstra como ativar a descriptografia automática, selecione a guia correspondente ao seu idioma preferido:

var autoEncryptionOpts = {
keyVaultNamespace: keyVaultNamespace,
kmsProviders: kmsProviders,
bypassAutoEncryption: true,
};
var encryptedClient = Mongo(
connectionString,
autoEncryptionOpts
);
var clientSettings = MongoClientSettings.FromConnectionString(connectionString);
var autoEncryptionOptions = new AutoEncryptionOptions(
keyVaultNamespace: keyVaultNamespace,
kmsProviders: kmsProviders,
bypassAutoEncryption: true);
clientSettings.AutoEncryptionOptions = autoEncryptionOptions;
var client = new MongoClient(clientSettings);
autoEncryptionOpts := options.AutoEncryption().
SetKmsProviders(kmsProviders).
SetKeyVaultNamespace(KeyVaultNamespace).
SetBypassAutoEncryption(true)
client, err := mongo.Connect(context.TODO(), options.Client().ApplyURI(URI).SetAutoEncryptionOptions(autoEncryptionOpts))
if err != nil {
return fmt.Errorf("Connect error for encrypted client: %v", err)
}
defer func() {
_ = client.Disconnect(context.TODO())
}()
MongoClientSettings clientSettings = MongoClientSettings.builder()
.applyConnectionString(new ConnectionString(connectionString))
.autoEncryptionSettings(AutoEncryptionSettings.builder()
.keyVaultNamespace(keyVaultNamespace)
.kmsProviders(kmsProviders).bypassAutoEncryption(true)
.build())
.build();
MongoClient mongoClient = MongoClients.create(clientSettings);
const client = new MongoClient(connectionString, {
useNewUrlParser: true,
useUnifiedTopology: true,
monitorCommands: true,
autoEncryption: {
keyVaultNamespace,
kmsProviders,
bypassAutoEncryption: true,
},
});
auto_encryption_opts = AutoEncryptionOpts(
kms_providers=kms_providers,
key_vault_namespace=key_vault_namespace,
bypass_auto_encryption=True,
)
client = MongoClient(auto_encryption_opts=auto_encryption_opts)

Suponha que você deseja inserir documentos com a seguinte estrutura em sua instância MongoDB:

{
"name": "<name of person>",
"age": <age of person>,
"favorite-foods": ["<array of foods>"]
}
1

Neste exemplo, você usa a mesma instância do MongoClient para acessar sua coleção do Key Vault e ler e gravar dados criptografados.

Os trechos de código a seguir mostram como criar uma instância MongoClient:

const autoEncryptionOpts = {
keyVaultNamespace: keyVaultNamespace,
kmsProviders: kmsProviders,
};
const encryptedClient = Mongo(connectionString, autoEncryptionOpts);
var client = new MongoClient(connectionString);
client, err := mongo.Connect(context.TODO(), options.Client().ApplyURI(URI))
if err != nil {
panic(fmt.Errorf("Client connect error %v", err))
}
MongoClient client = MongoClients.create(connectionString);
const client = new MongoClient(connectionString, {
useNewUrlParser: true,
useUnifiedTopology: true,
});
client = MongoClient(your_connection_uri)
2

Os trechos de código a seguir mostram como criar uma instância ClientEncryption:

const clientEncryption = encryptedClient.getClientEncryption();
var collection = client.GetDatabase(db).GetCollection<BsonDocument>(coll);
var clientEncryptionOptions = new ClientEncryptionOptions(
keyVaultClient: client,
keyVaultNamespace: keyVaultNamespace,
kmsProviders: kmsProviders);
var clientEncryption = new ClientEncryption(clientEncryptionOptions);
coll := client.Database(DbName).Collection(CollName)
clientEncryptionOpts := options.ClientEncryption().SetKeyVaultNamespace(KeyVaultNamespace).SetKmsProviders(kmsProviders)
clientEnc, err := mongo.NewClientEncryption(client, clientEncryptionOpts)
if err != nil {
panic(fmt.Errorf("NewClientEncryption error %v", err))
}
defer func() {
_ = clientEnc.Close(context.TODO())
}()
MongoCollection<Document> collection = client.getDatabase(db).getCollection(coll);
ClientEncryptionSettings clientEncryptionSettings = ClientEncryptionSettings.builder()
.keyVaultMongoClientSettings(MongoClientSettings.builder()
.applyConnectionString(new ConnectionString(connectionString))
.build())
.keyVaultNamespace(keyVaultNamespace)
.kmsProviders(kmsProviders)
.build();
ClientEncryption clientEncryption = ClientEncryptions.create(clientEncryptionSettings);
const collection = client.db(db).collection(coll);
const encryption = new ClientEncryption(client, {
keyVaultNamespace,
kmsProviders,
});
coll = client.employees.foods
client_encryption = ClientEncryption(
kms_providers,
"encryption.___keyVault",
client,
coll.codec_options,
)

Observação

CodecOptions

O driver Python para MongoDB requer que você indique o CodecOptions usado para criptografar e descriptografar seus documentos.

Especifique o CodecOptions que você configurou no MongoClient, Database ou Collection com o qual está gravando dados criptografados e descriptografados do aplicativo no MongoDB.

3

Você deseja criptografar os campos do documento usando os seguintes algoritmos:

Nome do campo
Algoritmo de criptografia
Tipo de campo BSON
name
Determinístico(a)
String
age
Sem criptografia
Int
favorite-foods
Aleatório
Array

Os seguintes trechos de código mostram como criptografar manualmente os campos em seu documento e inserir seu documento no MongoDB:

Observação

A variável dataKeyId nos exemplos abaixo refere-se a uma chave de encriptação de dados (DEK). Para saber como gerar uma DEK com seu fornecedor de chave local, consulte o Início rápido. Para saber como criar uma DEK com um sistema de gerenciamento de chaves específico, consulte Tutoriais.

const encName = clientEncryption.encrypt(
dataKeyId,
"Greg",
"AEAD_AES_256_CBC_HMAC_SHA_512-Deterministic"
);
const encFoods = clientEncryption.encrypt(
dataKeyId,
["Cheese", "Grapes"],
"AEAD_AES_256_CBC_HMAC_SHA_512-Random"
);
db.getSiblingDB(database).getCollection(collection).insertOne({
name: encName,
foods: encFoods,
});

Observação

A variável dataKeyId nos exemplos abaixo refere-se a uma chave de encriptação de dados (DEK). Para saber como gerar uma DEK com seu fornecedor de chave local, consulte o Início rápido. Para saber como criar uma DEK com um sistema de gerenciamento de chaves específico, consulte Tutoriais.

var encryptedName = clientEncryption.Encrypt(
"Greg",
new EncryptOptions(algorithm: "AEAD_AES_256_CBC_HMAC_SHA_512-Deterministic", keyId: dataKeyId),
CancellationToken.None);
var encryptedFoods = clientEncryption.Encrypt(
new BsonArray { "Cheese", "Grapes" },
new EncryptOptions(algorithm: "AEAD_AES_256_CBC_HMAC_SHA_512-Random", keyId: dataKeyId),
CancellationToken.None);
collection.InsertOne(new BsonDocument { { "name", encryptedName }, { "age", 83 }, { "foods", encryptedFoods } });

Observação

A variável dataKeyId nos exemplos abaixo refere-se a uma chave de encriptação de dados (DEK). Para saber como gerar uma DEK com seu fornecedor de chave local, consulte o Início rápido. Para saber como criar uma DEK com um sistema de gerenciamento de chaves específico, consulte Tutoriais.

nameRawValueType, nameRawValueData, err := bson.MarshalValue("Greg")
if err != nil {
panic(err)
}
nameRawValue := bson.RawValue{Type: nameRawValueType, Value: nameRawValueData}
nameEncryptionOpts := options.Encrypt().
SetAlgorithm("AEAD_AES_256_CBC_HMAC_SHA_512-Deterministic").
SetKeyID(dataKeyId)
nameEncryptedField, err := clientEnc.Encrypt(
context.TODO(),
nameRawValue,
nameEncryptionOpts)
if err != nil {
panic(err)
}
foodsRawValueType, foodsRawValueData, err := bson.MarshalValue(bson.A{"Grapes", "Cheese"})
if err != nil {
panic(err)
}
foodsRawValue := bson.RawValue{Type: foodsRawValueType, Value: foodsRawValueData}
encryptionOpts := options.Encrypt().
SetAlgorithm("AEAD_AES_256_CBC_HMAC_SHA_512-Random").
SetKeyID(dataKeyId)
foodsEncryptedField, err := clientEnc.Encrypt(
context.TODO(),
foodsRawValue,
encryptionOpts)
if err != nil {
panic(err)
}
_, err = coll.InsertOne(
context.TODO(),
bson.D{{"name", nameEncryptedField}, {"foods", foodsEncryptedField}, {"age", 83}})
if err != nil {
panic(err)
}

Observação

A variável dataKeyId nos exemplos abaixo refere-se a uma chave de encriptação de dados (DEK). Para saber como gerar uma DEK com seu fornecedor de chave local, consulte o Início rápido. Para saber como criar uma DEK com um sistema de gerenciamento de chaves específico, consulte Tutoriais.

BsonBinary encryptedName = clientEncryption.encrypt(new BsonString("Greg"), new EncryptOptions("AEAD_AES_256_CBC_HMAC_SHA_512-Deterministic").keyId(dataKeyId));
BsonBinary encryptedFoods = clientEncryption.encrypt(new BsonArray().parse("[\"Grapes\", \"Foods\"]"), new EncryptOptions("AEAD_AES_256_CBC_HMAC_SHA_512-Random").keyId(dataKeyId));
collection.insertOne(new Document("name", encryptedName).append("foods", encryptedFoods).append("age", 83));

Observação

A variável dataKeyId nos exemplos abaixo refere-se a uma chave de encriptação de dados (DEK). Para saber como gerar uma DEK com seu fornecedor de chave local, consulte o Início rápido. Para saber como criar uma DEK com um sistema de gerenciamento de chaves específico, consulte Tutoriais.

encryptedName = await encryption.encrypt("Greg", {
algorithm: "AEAD_AES_256_CBC_HMAC_SHA_512-Deterministic",
keyId: dataKeyId,
});
encryptedFoods = await encryption.encrypt(["Cheese", "Grapes"], {
algorithm: "AEAD_AES_256_CBC_HMAC_SHA_512-Random",
keyId: dataKeyId,
});
await collection.insertOne({
name: encryptedName,
age: 83,
foods: encryptedFoods,
});

Observação

A variável data_key_id nos exemplos abaixo refere-se a uma chave de encriptação de dados (DEK). Para saber como gerar uma DEK com seu fornecedor de chave local, consulte o Início rápido. Para saber como criar uma DEK com um sistema de gerenciamento de chaves específico, consulte Tutoriais.

encrypted_name = client_encryption.encrypt(
"Greg",
Algorithm.AEAD_AES_256_CBC_HMAC_SHA_512_Deterministic,
key_id=data_key_id,
)
encrypted_foods = client_encryption.encrypt(
["Cheese", "Grapes"],
Algorithm.AEAD_AES_256_CBC_HMAC_SHA_512_Random,
key_id=data_key_id,
)
coll.insert_one({"name": encrypted_name, "age": 83, "foods": encrypted_foods})
4

Os seguintes trechos de código mostram como recuperar seu documento inserido e descriptografar manualmente os campos criptografados:

const encNameQuery = clientEncryption.encrypt(
dataKeyId,
"Greg",
"AEAD_AES_256_CBC_HMAC_SHA_512-Deterministic"
);
let doc = db.getSiblingDB(database).getCollection(collection).findOne({
name: encNameQuery,
});
console.log(doc);
doc.name = clientEncryption.decrypt(doc.name);
doc.foods = clientEncryption.decrypt(doc.foods);
console.log(doc);
var nameToQuery = "Greg";
var encryptedNameToQuery = clientEncryption.Encrypt(
nameToQuery,
new EncryptOptions(algorithm: "AEAD_AES_256_CBC_HMAC_SHA_512-Deterministic", keyId: dataKeyId),
CancellationToken.None);
var doc = collection.Find(new BsonDocument { { "name", encryptedNameToQuery } }).Single();
Console.WriteLine($"Encrypted document: {doc}");
doc["name"] = clientEncryption.Decrypt(doc["name"].AsBsonBinaryData, CancellationToken.None);
doc["foods"] = clientEncryption.Decrypt(doc["foods"].AsBsonBinaryData, CancellationToken.None);
Console.WriteLine($"Decrypted field: {doc}");
nameQueryRawValueType, nameQueryRawValueData, err := bson.MarshalValue("Greg")
if err != nil {
panic(err)
}
nameQueryRawValue := bson.RawValue{Type: nameQueryRawValueType, Value: nameQueryRawValueData}
nameQueryEncryptionOpts := options.Encrypt().
SetAlgorithm("AEAD_AES_256_CBC_HMAC_SHA_512-Deterministic").
SetKeyID(dataKeyId)
nameQueryEncryptedField, err := clientEnc.Encrypt(
context.TODO(),
nameQueryRawValue,
nameQueryEncryptionOpts)
if err != nil {
panic(err)
}
var result bson.M
err = coll.FindOne(
context.TODO(),
bson.D{{"name", nameQueryEncryptedField}}).Decode(&result)
if err != nil {
if err == mongo.ErrNoDocuments {
return
}
panic(err)
}
fmt.Printf("Encrypted Document: %s\n", result)
nameDecrypted, err := clientEnc.Decrypt(
context.TODO(),
result["name"].(primitive.Binary))
foodsDecrypted, err := clientEnc.Decrypt(
context.TODO(),
result["foods"].(primitive.Binary))
result["foods"] = foodsDecrypted
result["name"] = nameDecrypted
fmt.Printf("Decrypted Document: %s\n", result)
BsonBinary encryptedNameQuery = clientEncryption.encrypt(new BsonString("Greg"), new EncryptOptions("AEAD_AES_256_CBC_HMAC_SHA_512-Deterministic").keyId(dataKeyId));
Document result = collection.find(eq("name", encryptedNameQuery)).first();
System.out.println("Encrypted Document: " + result.toJson());
result.replace("name", clientEncryption.decrypt(new BsonBinary(result.get("name", Binary.class).getData())));
result.replace("foods", clientEncryption.decrypt(new BsonBinary(result.get("foods", Binary.class).getData())));
System.out.println("Decrypted Document: " + result.toJson());
queryEncryptedName = await encryption.encrypt("Greg", {
algorithm: "AEAD_AES_256_CBC_HMAC_SHA_512-Deterministic",
keyId: dataKeyId,
});
let doc = await collection.findOne({ name: queryEncryptedName });
console.log("Encrypted Document: ", doc);
doc.name = encryption.decrypt(doc.name);
doc.foods = encryption.decrypt(doc.foods);
console.log("Decrypted document: ", doc);
name_to_query = "Greg"
encrypted_name_to_query = client_encryption.encrypt(
name_to_query,
Algorithm.AEAD_AES_256_CBC_HMAC_SHA_512_Deterministic,
key_id=data_key_id,
)
doc = client.employees.foods.find_one({"name": encrypted_name_to_query})
print("Encrypted document: %s" % (doc,))
doc["name"] = client_encryption.decrypt(doc["name"])
doc["foods"] = client_encryption.decrypt(doc["foods"])
print("Decrypted document: %s" % (doc,))

O MongoDB suporta o uso da validação de esquema para impor a criptografia de campos específicos em uma coleção.

Um cliente que executa a criptografia de nível de campo do lado do cliente com o mecanismo de criptografia explícito em uma instância do MongoDB configurada para impor a criptografia de determinados campos deve criptografar esses campos conforme especificado na instância do MongoDB.

Para saber como configurar a imposição de CSFLE no lado do servidor, consulte Aplicação do esquema CSFLE no lado do servidor.

Para saber mais sobre coleções de Key Vault, chaves de criptografia de dados e chaves mestras de clientes, consulte Chaves e Key Vaults.

Para saber mais sobre os provedores KMS e os objetos kmsProviders, consulte Provedores CSFLE KMS.

Voltar

Criptografia automática