39
39
import org .springframework .util .ObjectUtils ;
40
40
41
41
/**
42
+ * Default implementation of {@link EncryptingConverter}. Properties used with this converter must be annotated with
43
+ * {@link Encrypted @Encrypted} to provide key and algorithm metadata.
44
+ *
42
45
* @author Christoph Strobl
43
46
* @since 4.1
44
47
*/
45
48
public class MongoEncryptionConverter implements EncryptingConverter <Object , Object > {
46
49
47
50
private static final Log LOGGER = LogFactory .getLog (MongoEncryptionConverter .class );
48
51
49
- private Encryption <BsonValue , BsonBinary > encryption ;
52
+ private final Encryption <BsonValue , BsonBinary > encryption ;
50
53
private final EncryptionKeyResolver keyResolver ;
51
54
52
55
public MongoEncryptionConverter (Encryption <BsonValue , BsonBinary > encryption , EncryptionKeyResolver keyResolver ) {
@@ -70,7 +73,7 @@ public Object decrypt(Object encryptedValue, EncryptionContext context) {
70
73
if (encryptedValue instanceof Binary || encryptedValue instanceof BsonBinary ) {
71
74
72
75
if (LOGGER .isDebugEnabled ()) {
73
- LOGGER .debug (String .format ("Decrypting %s.%s." , getProperty (context ).getOwner ().getName (),
76
+ LOGGER .debug (String .format ("Decrypting %s.%s." , getProperty (context ).getOwner ().getName (),
74
77
getProperty (context ).getName ()));
75
78
}
76
79
@@ -83,18 +86,20 @@ public Object decrypt(Object encryptedValue, EncryptionContext context) {
83
86
}
84
87
}
85
88
86
- MongoPersistentProperty persistentProperty = getProperty (context );
89
+ MongoPersistentProperty persistentProperty = getProperty (context );
87
90
88
91
if (getProperty (context ).isCollectionLike () && decryptedValue instanceof Iterable <?> iterable ) {
92
+
93
+ int size = iterable instanceof Collection <?> c ? c .size () : 10 ;
94
+
89
95
if (!persistentProperty .isEntity ()) {
90
- Collection <Object > collection = CollectionFactory .createCollection (persistentProperty .getType (), 10 );
96
+ Collection <Object > collection = CollectionFactory .createCollection (persistentProperty .getType (), size );
91
97
iterable .forEach (it -> collection .add (BsonUtils .toJavaType ((BsonValue ) it )));
92
98
return collection ;
93
99
} else {
94
- Collection <Object > collection = CollectionFactory .createCollection (persistentProperty .getType (), 10 );
100
+ Collection <Object > collection = CollectionFactory .createCollection (persistentProperty .getType (), size );
95
101
iterable .forEach (it -> {
96
- collection .add (context .read (BsonUtils .toJavaType ((BsonValue ) it ),
97
- persistentProperty .getActualType ()));
102
+ collection .add (context .read (BsonUtils .toJavaType ((BsonValue ) it ), persistentProperty .getActualType ()));
98
103
});
99
104
return collection ;
100
105
}
@@ -109,17 +114,12 @@ public Object decrypt(Object encryptedValue, EncryptionContext context) {
109
114
}
110
115
111
116
if (persistentProperty .isEntity () && decryptedValue instanceof BsonDocument bsonDocument ) {
112
- return context .read (BsonUtils .toJavaType (bsonDocument ),
113
- persistentProperty .getTypeInformation ().getType ());
117
+ return context .read (BsonUtils .toJavaType (bsonDocument ), persistentProperty .getTypeInformation ().getType ());
114
118
}
115
119
116
120
return decryptedValue ;
117
121
}
118
122
119
- private MongoPersistentProperty getProperty (EncryptionContext context ) {
120
- return context .getProperty ();
121
- }
122
-
123
123
@ Override
124
124
public Object encrypt (Object value , EncryptionContext context ) {
125
125
@@ -128,15 +128,19 @@ public Object encrypt(Object value, EncryptionContext context) {
128
128
getProperty (context ).getName ()));
129
129
}
130
130
131
- MongoPersistentProperty persistentProperty = getProperty (context );
131
+ MongoPersistentProperty persistentProperty = getProperty (context );
132
132
133
133
Encrypted annotation = persistentProperty .findAnnotation (Encrypted .class );
134
- if (annotation == null ) {
134
+ if (annotation == null ) {
135
135
annotation = persistentProperty .getOwner ().findAnnotation (Encrypted .class );
136
136
}
137
137
138
- EncryptionOptions encryptionOptions = new EncryptionOptions (annotation .algorithm ());
139
- encryptionOptions .setKey (keyResolver .getKey (context ));
138
+ if (annotation == null ) {
139
+ throw new IllegalStateException (String .format ("Property %s.%s is not annotated with @Encrypted" ,
140
+ getProperty (context ).getOwner ().getName (), getProperty (context ).getName ()));
141
+ }
142
+
143
+ EncryptionOptions encryptionOptions = new EncryptionOptions (annotation .algorithm (), keyResolver .getKey (context ));
140
144
141
145
if (!persistentProperty .isEntity ()) {
142
146
@@ -162,36 +166,44 @@ public Object encrypt(Object value, EncryptionContext context) {
162
166
return encryption .encrypt (BsonUtils .simpleToBsonValue (write ), encryptionOptions );
163
167
}
164
168
165
- public BsonValue collectionLikeToBsonValue (Object value , MongoPersistentProperty property ,
169
+ private BsonValue collectionLikeToBsonValue (Object value , MongoPersistentProperty property ,
166
170
EncryptionContext context ) {
167
171
168
172
BsonArray bsonArray = new BsonArray ();
169
- if (!property .isEntity ()) {
170
- if (value instanceof Collection values ) {
171
- values .forEach (it -> bsonArray .add (BsonUtils .simpleToBsonValue (it )));
172
- } else if (ObjectUtils .isArray (value )) {
173
- for (Object o : ObjectUtils .toObjectArray (value )) {
174
- bsonArray .add (BsonUtils .simpleToBsonValue (o ));
173
+ boolean isEntity = property .isEntity ();
174
+
175
+ if (value instanceof Collection <?> values ) {
176
+ values .forEach (it -> {
177
+
178
+ if (isEntity ) {
179
+ Document document = (Document ) context .write (it , property .getTypeInformation ());
180
+ bsonArray .add (document == null ? null : document .toBsonDocument ());
181
+ } else {
182
+ bsonArray .add (BsonUtils .simpleToBsonValue (it ));
175
183
}
176
- }
177
- return bsonArray ;
178
- } else {
179
- if (value instanceof Collection values ) {
180
- values .forEach (it -> {
181
- Document write = (Document ) context .write (it , property .getTypeInformation ());
182
- bsonArray .add (write .toBsonDocument ());
183
- });
184
- } else if (ObjectUtils .isArray (value )) {
185
- for (Object o : ObjectUtils .toObjectArray (value )) {
186
- Document write = (Document ) context .write (o , property .getTypeInformation ());
187
- bsonArray .add (write .toBsonDocument ());
184
+ });
185
+ } else if (ObjectUtils .isArray (value )) {
186
+
187
+ for (Object o : ObjectUtils .toObjectArray (value )) {
188
+
189
+ if (isEntity ) {
190
+ Document document = (Document ) context .write (o , property .getTypeInformation ());
191
+ bsonArray .add (document == null ? null : document .toBsonDocument ());
192
+ } else {
193
+ bsonArray .add (BsonUtils .simpleToBsonValue (o ));
188
194
}
189
195
}
190
- return bsonArray ;
191
196
}
197
+
198
+ return bsonArray ;
192
199
}
193
200
201
+ @ Override
194
202
public EncryptionContext buildEncryptionContext (MongoConversionContext context ) {
195
203
return new ExplicitEncryptionContext (context );
196
204
}
205
+
206
+ protected MongoPersistentProperty getProperty (EncryptionContext context ) {
207
+ return context .getProperty ();
208
+ }
197
209
}
0 commit comments