Skip to content

Commit ebd413f

Browse files
CSHARP-4157: Tests.
1 parent 609e4f8 commit ebd413f

File tree

3 files changed

+67
-112
lines changed

3 files changed

+67
-112
lines changed

src/MongoDB.Driver/Encryption/EncryptOptions.cs

Lines changed: 12 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -19,12 +19,12 @@
1919
namespace MongoDB.Driver.Encryption
2020
{
2121
/// <summary>
22-
/// TODO
22+
/// The QueryType to use for "Indexed" queries.
2323
/// </summary>
2424
public enum QueryType
2525
{
2626
/// <summary>
27-
/// TODO
27+
/// Equality query type.
2828
/// </summary>
2929
Equality = 1
3030
}
@@ -59,7 +59,7 @@ private static string ConvertEnumAlgorithmToString(EncryptionAlgorithm encryptio
5959
/// <param name="alternateKeyName">The alternate key name.</param>
6060
/// <param name="keyId">The key Id.</param>
6161
/// <param name="contentionFactor">The contention factor.</param>
62-
/// <param name="queryType">TODO</param>
62+
/// <param name="queryType">The query type.</param>
6363
public EncryptOptions(
6464
string algorithm,
6565
Optional<string> alternateKeyName = default,
@@ -141,10 +141,10 @@ public EncryptOptions(
141141
public Guid? KeyId => _keyId;
142142

143143
/// <summary>
144-
/// TODO
144+
/// Gets the query type.
145145
/// </summary>
146146
/// <value>
147-
/// TODO
147+
/// The query type.
148148
/// </value>
149149
public QueryType? QueryType => _queryType;
150150

@@ -155,25 +155,30 @@ public EncryptOptions(
155155
/// <param name="alternateKeyName">The alternate key name.</param>
156156
/// <param name="keyId">The keyId.</param>
157157
/// <param name="contentionFactor">The contention factor.</param>
158+
/// <param name="queryType">The query type.</param>
158159
/// <returns>A new EncryptOptions instance.</returns>
159160
public EncryptOptions With(
160161
Optional<string> algorithm = default,
161162
Optional<string> alternateKeyName = default,
162163
Optional<Guid?> keyId = default,
163-
Optional<long?> contentionFactor = default)
164+
Optional<long?> contentionFactor = default,
165+
Optional<QueryType?> queryType = default)
164166
{
165167
return new EncryptOptions(
166168
algorithm: algorithm.WithDefault(_algorithm),
167169
alternateKeyName: alternateKeyName.WithDefault(_alternateKeyName),
168170
keyId: keyId.WithDefault(_keyId),
169-
contentionFactor: contentionFactor.WithDefault(_contentionFactor));
171+
contentionFactor: contentionFactor.WithDefault(_contentionFactor),
172+
queryType: queryType.WithDefault(_queryType));
170173
}
171174

172175
// private methods
173176
private void EnsureThatOptionsAreValid()
174177
{
175178
Ensure.That(!(!_keyId.HasValue && _alternateKeyName == null), "Key Id and AlternateKeyName may not both be null.");
176179
Ensure.That(!(_keyId.HasValue && _alternateKeyName != null), "Key Id and AlternateKeyName may not both be set.");
180+
Ensure.That(!_contentionFactor.HasValue || _algorithm == EncryptionAlgorithm.Indexed.ToString(), "ContentionFactor only applies for Indexed algorithm.");
181+
Ensure.That(!_queryType.HasValue || _algorithm == EncryptionAlgorithm.Indexed.ToString(), "QueryType only applies for Indexed algorithm.");
177182
}
178183
}
179184
}

src/MongoDB.Driver/Encryption/ExplicitEncryptionLibMongoCryptController.cs

Lines changed: 0 additions & 86 deletions
Original file line numberDiff line numberDiff line change
@@ -132,92 +132,6 @@ public async Task<BsonValue> DecryptFieldAsync(BsonBinaryData wrappedBinaryValue
132132
}
133133
}
134134

135-
public BsonBinaryData EncryptField(
136-
BsonValue value,
137-
Guid? keyId,
138-
string alternateKeyName,
139-
string encryptionAlgorithm,
140-
CancellationToken cancellationToken)
141-
{
142-
try
143-
{
144-
var wrappedValueBytes = GetWrappedValueBytes(value);
145-
146-
CryptContext context;
147-
if (keyId.HasValue && alternateKeyName != null)
148-
{
149-
throw new ArgumentException("keyId and alternateKeyName cannot both be provided.");
150-
}
151-
else if (keyId.HasValue)
152-
{
153-
var keyBytes = GuidConverter.ToBytes(keyId.Value, GuidRepresentation.Standard);
154-
context = _cryptClient.StartExplicitEncryptionContextWithKeyId(keyBytes, encryptionAlgorithm, wrappedValueBytes);
155-
}
156-
else if (alternateKeyName != null)
157-
{
158-
var wrappedAlternateKeyNameBytes = GetWrappedAlternateKeyNameBytes(alternateKeyName);
159-
context = _cryptClient.StartExplicitEncryptionContextWithKeyAltName(wrappedAlternateKeyNameBytes, encryptionAlgorithm, wrappedValueBytes);
160-
}
161-
else
162-
{
163-
throw new ArgumentException("Either keyId or alternateKeyName must be provided.");
164-
}
165-
166-
using (context)
167-
{
168-
var wrappedBytes = ProcessStates(context, databaseName: null, cancellationToken);
169-
return UnwrapEncryptedValue(wrappedBytes);
170-
}
171-
}
172-
catch (Exception ex)
173-
{
174-
throw new MongoEncryptionException(ex);
175-
}
176-
}
177-
178-
public async Task<BsonBinaryData> EncryptFieldAsync(
179-
BsonValue value,
180-
Guid? keyId,
181-
string alternateKeyName,
182-
string encryptionAlgorithm,
183-
CancellationToken cancellationToken)
184-
{
185-
try
186-
{
187-
var wrappedValueBytes = GetWrappedValueBytes(value);
188-
189-
CryptContext context;
190-
if (keyId.HasValue && alternateKeyName != null)
191-
{
192-
throw new ArgumentException("keyId and alternateKeyName cannot both be provided.");
193-
}
194-
else if (keyId.HasValue)
195-
{
196-
var bytes = GuidConverter.ToBytes(keyId.Value, GuidRepresentation.Standard);
197-
context = _cryptClient.StartExplicitEncryptionContextWithKeyId(bytes, encryptionAlgorithm, wrappedValueBytes);
198-
}
199-
else if (alternateKeyName != null)
200-
{
201-
var wrappedAlternateKeyNameBytes = GetWrappedAlternateKeyNameBytes(alternateKeyName);
202-
context = _cryptClient.StartExplicitEncryptionContextWithKeyAltName(wrappedAlternateKeyNameBytes, encryptionAlgorithm, wrappedValueBytes);
203-
}
204-
else
205-
{
206-
throw new ArgumentException("Either keyId or alternateKeyName must be provided.");
207-
}
208-
209-
using (context)
210-
{
211-
var wrappedBytes = await ProcessStatesAsync(context, databaseName: null, cancellationToken).ConfigureAwait(false);
212-
return UnwrapEncryptedValue(wrappedBytes);
213-
}
214-
}
215-
catch (Exception ex)
216-
{
217-
throw new MongoEncryptionException(ex);
218-
}
219-
}
220-
221135
public BsonBinaryData EncryptField(
222136
BsonValue value,
223137
EncryptOptions encryptOptions,

tests/MongoDB.Driver.Tests/EncryptOptionsTests.cs

Lines changed: 55 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -29,6 +29,14 @@ public void Constructor_should_fail_when_algorithm_is_null()
2929
exception.Should().BeOfType<ArgumentNullException>();
3030
}
3131

32+
[Fact]
33+
public void Constructor_should_fail_when_contentionFactor_and_algorithm_is_not_indexed()
34+
{
35+
var exception = Record.Exception(() => new EncryptOptions(algorithm: "test", contentionFactor: 1, keyId: Guid.NewGuid()));
36+
var e = exception.Should().BeOfType<ArgumentException>().Subject;
37+
e.Message.Should().Be("ContentionFactor only applies for Indexed algorithm.");
38+
}
39+
3240
[Fact]
3341
public void Constructor_should_fail_when_keyId_and_alternateKeyName_are_both_empty()
3442
{
@@ -45,6 +53,14 @@ public void Constructor_should_fail_when_keyId_and_alternateKeyName_are_both_spe
4553
e.Message.Should().Be("Key Id and AlternateKeyName may not both be set.");
4654
}
4755

56+
[Fact]
57+
public void Constructor_should_fail_when_queryType_and_algorithm_is_not_indexed()
58+
{
59+
var exception = Record.Exception(() => new EncryptOptions(algorithm: "test", queryType: QueryType.Equality, keyId: Guid.NewGuid()));
60+
var e = exception.Should().BeOfType<ArgumentException>().Subject;
61+
e.Message.Should().Be("QueryType only applies for Indexed algorithm.");
62+
}
63+
4864
[Theory]
4965
[InlineData(EncryptionAlgorithm.AEAD_AES_256_CBC_HMAC_SHA_512_Deterministic, "AEAD_AES_256_CBC_HMAC_SHA_512-Deterministic")]
5066
[InlineData(EncryptionAlgorithm.AEAD_AES_256_CBC_HMAC_SHA_512_Random, "AEAD_AES_256_CBC_HMAC_SHA_512-Random")]
@@ -59,6 +75,10 @@ public void Constructor_should_fail_when_keyId_and_alternateKeyName_are_both_spe
5975
[InlineData("TEST_random", "TEST_random")]
6076
// just a random value in enum form
6177
[InlineData((EncryptionAlgorithm)99, "99")]
78+
[InlineData(EncryptionAlgorithm.Indexed, "Indexed")]
79+
[InlineData("Indexed", "Indexed")]
80+
[InlineData(EncryptionAlgorithm.Unindexed, "Unindexed")]
81+
[InlineData("Unindexed", "Unindexed")]
6282
public void Constructor_should_support_different_algorithm_representations(object algorithm, string expectedAlgorithmRepresentation)
6383
{
6484
var alternateKeyName = "test";
@@ -81,44 +101,60 @@ public void Constructor_should_support_different_algorithm_representations(objec
81101
[Fact]
82102
public void With_should_set_correct_values()
83103
{
84-
var originalAlgorithm = "originalAlgorithm";
104+
var originalAlgorithm = EncryptionAlgorithm.Indexed.ToString();
85105
var newAlgorithm = "newAlgorithm";
86106
var originalKeyId = Guid.Empty;
87107
var newKeyId = Guid.NewGuid();
88108
var originalAlternateKeyName = "test";
89109
var newAlternateKeyName = "new";
110+
long? originalContention = null;
111+
var newContention = 2;
112+
QueryType? originalQueryType = null;
113+
var newQueryType = QueryType.Equality;
90114

91-
var subject = CreateConfiguredSubject(withKeyId: true);
92-
AssertValues(subject, originalAlgorithm, originalKeyId, null);
115+
var fle1WithKeyIdState = 0;
116+
var subject = CreateConfiguredSubject(state: fle1WithKeyIdState);
117+
AssertValues(subject, originalAlgorithm, expectedKeyId: originalKeyId);
93118

94119
subject = subject.With(algorithm: newAlgorithm);
95-
AssertValues(subject, newAlgorithm, originalKeyId, null);
120+
AssertValues(subject, newAlgorithm, expectedKeyId: originalKeyId);
96121

97122
subject = subject.With(keyId: newKeyId);
98-
AssertValues(subject, newAlgorithm, newKeyId, null);
123+
AssertValues(subject, newAlgorithm, expectedKeyId: newKeyId);
99124

100-
subject = CreateConfiguredSubject(withKeyId: false);
101-
AssertValues(subject, originalAlgorithm, null, originalAlternateKeyName);
125+
var fle1WithAlternateKeyNameState = 1;
126+
subject = CreateConfiguredSubject(state: fle1WithAlternateKeyNameState);
127+
AssertValues(subject, originalAlgorithm, expectedAlternateKeyName: originalAlternateKeyName);
102128

103129
subject = subject.With(alternateKeyName: newAlternateKeyName);
104-
AssertValues(subject, originalAlgorithm, null, newAlternateKeyName);
130+
AssertValues(subject, originalAlgorithm, expectedAlternateKeyName: newAlternateKeyName);
131+
132+
var fle2State = 2;
133+
subject = CreateConfiguredSubject(state: fle2State);
134+
subject = subject.With(contentionFactor: newContention);
135+
AssertValues(subject, EncryptionAlgorithm.Indexed.ToString(), expectedKeyId: originalKeyId, expectedContentionFactor: newContention);
105136

106-
static void AssertValues(EncryptOptions subject, string algorithm, Guid? keyId, string alternateKeyName)
137+
subject = CreateConfiguredSubject(state: fle2State);
138+
subject = subject.With(queryType: newQueryType);
139+
AssertValues(subject, EncryptionAlgorithm.Indexed.ToString(), expectedKeyId: originalKeyId, expectedQueryType: newQueryType);
140+
141+
static void AssertValues(EncryptOptions subject, string expectedAlgorithm, Guid? expectedKeyId = null, string expectedAlternateKeyName = null, QueryType? expectedQueryType = null, long? expectedContentionFactor = null)
107142
{
108-
subject.Algorithm.Should().Be(algorithm);
109-
subject.KeyId.Should().Be(keyId);
110-
subject.AlternateKeyName.Should().Be(alternateKeyName);
143+
subject.Algorithm.Should().Be(expectedAlgorithm);
144+
subject.KeyId.Should().Be(expectedKeyId);
145+
subject.AlternateKeyName.Should().Be(expectedAlternateKeyName);
146+
subject.QueryType.Should().Be(expectedQueryType);
147+
subject.ContentionFactor.Should().Be(expectedContentionFactor);
111148
}
112149

113-
EncryptOptions CreateConfiguredSubject(bool withKeyId)
150+
EncryptOptions CreateConfiguredSubject(int state)
114151
{
115-
if (withKeyId)
116-
{
117-
return new EncryptOptions(algorithm: originalAlgorithm, keyId: originalKeyId);
118-
}
119-
else
152+
switch (state)
120153
{
121-
return new EncryptOptions(algorithm: originalAlgorithm, alternateKeyName: originalAlternateKeyName);
154+
case 0: return new EncryptOptions(algorithm: originalAlgorithm, keyId: originalKeyId);
155+
case 1: return new EncryptOptions(algorithm: originalAlgorithm, alternateKeyName: originalAlternateKeyName);
156+
case 2: return new EncryptOptions(algorithm: originalAlgorithm, keyId: originalKeyId, contentionFactor: originalContention, queryType: originalQueryType);
157+
default: throw new Exception($"Unexpected state: {state}.");
122158
}
123159
}
124160
}

0 commit comments

Comments
 (0)