Skip to content

Commit d49b1c3

Browse files
committed
DATAMONGO-2306 - Polishing.
Add Nullable annotation to nullable method args. Remove IV from JSON Schema as it is not listed in Mongo specs. Tweak wording in docs. Parse encryption-settings-ref for MongoClientOptions. Add support for KeyId's in encrypted JSON schema properties. Original pull request: #766.
1 parent da0cb6d commit d49b1c3

File tree

5 files changed

+44
-14
lines changed

5 files changed

+44
-14
lines changed

spring-data-mongodb/src/main/java/org/springframework/data/mongodb/config/MongoParsingUtils.java

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -35,6 +35,7 @@
3535
* @author Oliver Gierke
3636
* @author Thomas Darimont
3737
* @author Christoph Strobl
38+
* @author Mark Paluch
3839
*/
3940
@SuppressWarnings("deprecation")
4041
abstract class MongoParsingUtils {
@@ -92,6 +93,7 @@ public static boolean parseMongoClientOptions(Element element, BeanDefinitionBui
9293
setPropertyValue(clientOptionsDefBuilder, optionsElement, "heartbeat-socket-timeout", "heartbeatSocketTimeout");
9394
setPropertyValue(clientOptionsDefBuilder, optionsElement, "ssl", "ssl");
9495
setPropertyReference(clientOptionsDefBuilder, optionsElement, "ssl-socket-factory-ref", "sslSocketFactory");
96+
setPropertyReference(clientOptionsDefBuilder, optionsElement, "encryption-settings-ref", "autoEncryptionSettings");
9597
setPropertyValue(clientOptionsDefBuilder, optionsElement, "server-selection-timeout", "serverSelectionTimeout");
9698

9799
mongoClientBuilder.addPropertyValue("mongoClientOptions", clientOptionsDefBuilder.getBeanDefinition());

spring-data-mongodb/src/main/java/org/springframework/data/mongodb/core/MongoEncryptionSettingsFactoryBean.java

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,7 @@
2020

2121
import org.bson.BsonDocument;
2222
import org.springframework.beans.factory.FactoryBean;
23+
import org.springframework.lang.Nullable;
2324

2425
import com.mongodb.AutoEncryptionSettings;
2526
import com.mongodb.MongoClientSettings;
@@ -104,7 +105,7 @@ public AutoEncryptionSettings getObject() {
104105
.build();
105106
}
106107

107-
private <K, V> Map<K, V> orEmpty(Map<K, V> source) {
108+
private <K, V> Map<K, V> orEmpty(@Nullable Map<K, V> source) {
108109
return source != null ? source : Collections.emptyMap();
109110
}
110111

spring-data-mongodb/src/main/java/org/springframework/data/mongodb/core/schema/IdentifiableJsonSchemaProperty.java

Lines changed: 20 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -18,9 +18,12 @@
1818
import java.util.Arrays;
1919
import java.util.Collection;
2020
import java.util.LinkedHashSet;
21+
import java.util.List;
2122
import java.util.Set;
23+
import java.util.UUID;
2224

2325
import org.bson.Document;
26+
2427
import org.springframework.data.domain.Range;
2528
import org.springframework.data.mongodb.core.schema.TypedJsonSchemaObject.ArrayJsonSchemaObject;
2629
import org.springframework.data.mongodb.core.schema.TypedJsonSchemaObject.BooleanJsonSchemaObject;
@@ -1057,8 +1060,8 @@ public static class EncryptedJsonSchemaProperty implements JsonSchemaProperty {
10571060

10581061
private final JsonSchemaProperty targetProperty;
10591062
private final @Nullable String algorithm;
1060-
private final @Nullable char[] keyId;
1061-
private final @Nullable char[] iv;
1063+
private final @Nullable String keyId;
1064+
private final @Nullable List<UUID> keyIds;
10621065

10631066
/**
10641067
* Create new instance of {@link EncryptedJsonSchemaProperty} wrapping the given {@link JsonSchemaProperty target}.
@@ -1069,14 +1072,14 @@ public EncryptedJsonSchemaProperty(JsonSchemaProperty target) {
10691072
this(target, null, null, null);
10701073
}
10711074

1072-
private EncryptedJsonSchemaProperty(JsonSchemaProperty target, @Nullable String algorithm, @Nullable char[] keyId,
1073-
@Nullable char[] iv) {
1075+
private EncryptedJsonSchemaProperty(JsonSchemaProperty target, @Nullable String algorithm, @Nullable String keyId,
1076+
@Nullable List<UUID> keyIds) {
10741077

10751078
Assert.notNull(target, "Target must not be null!");
10761079
this.targetProperty = target;
10771080
this.algorithm = algorithm;
10781081
this.keyId = keyId;
1079-
this.iv = iv;
1082+
this.keyIds = keyIds;
10801083
}
10811084

10821085
/**
@@ -1113,19 +1116,23 @@ public EncryptedJsonSchemaProperty aead_aes_256_cbc_hmac_sha_512_deterministic()
11131116
* @return new instance of {@link EncryptedJsonSchemaProperty}.
11141117
*/
11151118
public EncryptedJsonSchemaProperty algorithm(String algorithm) {
1116-
return new EncryptedJsonSchemaProperty(targetProperty, algorithm, keyId, iv);
1119+
return new EncryptedJsonSchemaProperty(targetProperty, algorithm, keyId, keyIds);
11171120
}
11181121

11191122
/**
11201123
* @param key
11211124
* @return
11221125
*/
1123-
public EncryptedJsonSchemaProperty keyId(char[] key) {
1124-
return new EncryptedJsonSchemaProperty(targetProperty, algorithm, key, iv);
1126+
public EncryptedJsonSchemaProperty keyId(String keyId) {
1127+
return new EncryptedJsonSchemaProperty(targetProperty, algorithm, keyId, null);
11251128
}
11261129

1127-
public EncryptedJsonSchemaProperty keyId(String key) {
1128-
return keyId(key.toCharArray());
1130+
/**
1131+
* @param keyId
1132+
* @return
1133+
*/
1134+
public EncryptedJsonSchemaProperty keys(UUID... keyId) {
1135+
return new EncryptedJsonSchemaProperty(targetProperty, algorithm, null, Arrays.asList(keyId));
11291136
}
11301137

11311138
/*
@@ -1141,7 +1148,9 @@ public Document toDocument() {
11411148
Document enc = new Document();
11421149

11431150
if (!ObjectUtils.isEmpty(keyId)) {
1144-
enc.append("keyId", new String(keyId));
1151+
enc.append("keyId", keyId);
1152+
} else if (!ObjectUtils.isEmpty(keyIds)) {
1153+
enc.append("keyId", keyIds);
11451154
}
11461155

11471156
Type type = extractPropertyType(propertySpecification);

spring-data-mongodb/src/test/java/org/springframework/data/mongodb/core/schema/MongoJsonSchemaUnitTests.java

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,8 @@
1919
import static org.springframework.data.mongodb.test.util.Assertions.*;
2020

2121
import java.util.Arrays;
22+
import java.util.Collections;
23+
import java.util.UUID;
2224

2325
import org.bson.Document;
2426
import org.junit.Test;
@@ -87,6 +89,22 @@ public void rendersEncryptedPropertyCorrectly() {
8789
.append("algorithm", "AEAD_AES_256_CBC_HMAC_SHA_512-Deterministic").append("bsonType", "string"))))));
8890
}
8991

92+
@Test // DATAMONGO-2306
93+
public void rendersEncryptedPropertyWithKeyIdCorrectly() {
94+
95+
UUID uuid = UUID.randomUUID();
96+
MongoJsonSchema schema = MongoJsonSchema.builder().properties( //
97+
encrypted(string("ssn")) //
98+
.aead_aes_256_cbc_hmac_sha_512_deterministic() //
99+
.keys(uuid) //
100+
).build();
101+
102+
assertThat(schema.toDocument()).isEqualTo(new Document("$jsonSchema",
103+
new Document("type", "object").append("properties",
104+
new Document("ssn", new Document("encrypt", new Document("keyId", Collections.singletonList(uuid))
105+
.append("algorithm", "AEAD_AES_256_CBC_HMAC_SHA_512-Deterministic").append("bsonType", "string"))))));
106+
}
107+
90108
@Test // DATAMONGO-1835
91109
public void throwsExceptionOnNullRoot() {
92110
assertThatIllegalArgumentException().isThrownBy(() -> MongoJsonSchema.of((JsonSchemaObject) null));

src/main/asciidoc/reference/mongo-json-schema.adoc

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -208,7 +208,7 @@ template.find(query(matchingDocumentStructure(schema)), Person.class);
208208
[[mongo.jsonSchema.encrypted-fields]]
209209
==== Encrypted Fields
210210

211-
MongoDB 4.2 https://docs.mongodb.com/master/core/security-client-side-encryption/[Field Level Encryption] allows to directly secure certain properties.
211+
MongoDB 4.2 https://docs.mongodb.com/master/core/security-client-side-encryption/[Field Level Encryption] allows to directly encrypt individual properties.
212212

213213
Properties can be wrapped within an encrypted property when setting up the JSON Schema as shown in the example below.
214214

@@ -225,7 +225,7 @@ MongoJsonSchema schema = MongoJsonSchema.builder()
225225
----
226226
====
227227

228-
NOTE: Make sure to set the drivers `com.mongodb.AutoEncryptionSettings` to use client side encryption.
228+
NOTE: Make sure to set the drivers `com.mongodb.AutoEncryptionSettings` to use client-side encryption. MongoDB does not support encryption for all field types. Specific data types require deterministic encryption to preserve equality comparison functionality.
229229

230230
[[mongo.jsonSchema.types]]
231231
==== JSON Schema Types

0 commit comments

Comments
 (0)