Hi, I am looking for an update on this as well.
I have a simple application that requires storing some sensitive data. I opted for a localy managed key to encrypt fields in MongoDB. I am able to encrypt and decrypt data in the DB. But I am having a hard time rotating 'local’s keys. I am using .NET driver v 2.27.0. Is this feature available in this version?
In my test application, when I try re-wrapping using new ‘local’ key I get an error
Found existing DEK for <DBName>.<Entity>
fail: Microsoft.AspNetCore.Diagnostics.DeveloperExceptionPageMiddleware[1]
An unhandled exception has occurred while executing the request.
MongoDB.Driver.Encryption.MongoEncryptionException: Encryption related exception: Unexpected field: 'key'.
---> MongoDB.Libmongocrypt.CryptException: Unexpected field: 'key'
at MongoDB.Libmongocrypt.Status.ThrowExceptionIfNeeded()
at MongoDB.Libmongocrypt.ContextSafeHandle.Check(Status status, Boolean success)
at MongoDB.Libmongocrypt.PinnedBinary.RunAsPinnedBinary[THandle](THandle handle, Byte[] bytes, Status status, Func`3 handleFunc)
at MongoDB.Libmongocrypt.KmsKeyId.SetCredentials(ContextSafeHandle context, Status status)
at MongoDB.Libmongocrypt.CryptClient.StartRewrapMultipleDataKeysContext(KmsKeyId kmsKey, Byte[] filter)
at MongoDB.Driver.Encryption.ExplicitEncryptionLibMongoCryptController.RewrapManyDataKey(FilterDefinition`1 filter, RewrapManyDataKeyOptions options, CancellationToken cancellationToken).
Here is the function I am calling to rewrap keys
{
var client = CreateClient();
var result = "";
//kms provider: local
var kmsProviders = new KmsProviders(_secureConnectionSettings.EncryptionMasterKey); //new key
var keyVaultNamespace = CollectionNamespace.FromFullName(
$"{_secureConnectionSettings.EncryptionDatabaseName}.__{_secureConnectionSettings.EncryptionKeyVaultCollection}");
// Get the key vault collection
var keyVaultCollection = client.GetDatabase(_secureConnectionSettings.EncryptionDatabaseName)
.GetCollection<BsonDocument>("__KeyVault");
// Rewrap all keys in the key vault collection
var encryptionOptions = new ClientEncryptionOptions(client, keyVaultNamespace, kmsProviders.Providers);
using (var clientEncryption = new ClientEncryption(encryptionOptions))
{
var filter = Builders<BsonDocument>.Filter.Empty; // To rewrap all keys, use an empty filter
var updateOptions = new RewrapManyDataKeyOptions("local", new BsonDocument
{
{
"key",
"<new key>"
} // New CMK ARN for local
});
// Rewrap the keys
var rewrapResult = clientEncryption.RewrapManyDataKey(filter, updateOptions);
result = $"Rewrapped {rewrapResult.BulkWriteResult.ModifiedCount} keys.";
}
}
I found an example of the above on the web but I am not sure if the usage is correct. For one the line is calling the new master key,
var kmsProviders = new KmsProviders(_secureConnectionSettings.EncryptionMasterKey);
and the kmsProvider is used as a parameter in
var encryptionOptions = new ClientEncryptionOptions(client, keyVaultNamespace, kmsProviders.Providers);
should it be the old masterkey or the new key. Another point I wanted to check is KMSProvider is Dictionary<string, IReadOnlyDictionary<string, object>>(). When I add the new masterkey I am replacing the the old key with the new key before rotation. I am not certain if that was intended.