2222
2323import org .bson .BsonNull ;
2424import org .bson .Document ;
25-
2625import org .springframework .data .domain .Range ;
2726import org .springframework .data .domain .Range .Bound ;
28- import org .springframework .data .util .Streamable ;
2927import org .springframework .lang .Nullable ;
3028
3129/**
30+ * Encapsulation of individual {@link QueryCharacteristic query characteristics} used to define queries that can be
31+ * executed when using queryable encryption.
32+ *
3233 * @author Christoph Strobl
3334 * @since 4.5
3435 */
35- public class QueryCharacteristics implements Streamable <QueryCharacteristic > {
36+ public class QueryCharacteristics implements Iterable <QueryCharacteristic > {
3637
38+ /**
39+ * instance indicating none
40+ */
3741 private static final QueryCharacteristics NONE = new QueryCharacteristics (Collections .emptyList ());
3842
3943 private final List <QueryCharacteristic > characteristics ;
@@ -42,18 +46,36 @@ public class QueryCharacteristics implements Streamable<QueryCharacteristic> {
4246 this .characteristics = characteristics ;
4347 }
4448
49+ /**
50+ * @return marker instance indicating no characteristics have been defined.
51+ */
4552 public static QueryCharacteristics none () {
4653 return NONE ;
4754 }
4855
56+ /**
57+ * Create new {@link QueryCharacteristics} from given list of {@link QueryCharacteristic characteristics}.
58+ *
59+ * @param characteristics must not be {@literal null}.
60+ * @return new instance of {@link QueryCharacteristics}.
61+ */
4962 public static QueryCharacteristics of (List <QueryCharacteristic > characteristics ) {
5063 return new QueryCharacteristics (List .copyOf (characteristics ));
5164 }
5265
66+ /**
67+ * Create new {@link QueryCharacteristics} from given {@link QueryCharacteristic characteristics}.
68+ *
69+ * @param characteristics must not be {@literal null}.
70+ * @return new instance of {@link QueryCharacteristics}.
71+ */
5372 public static QueryCharacteristics of (QueryCharacteristic ... characteristics ) {
5473 return new QueryCharacteristics (Arrays .asList (characteristics ));
5574 }
5675
76+ /**
77+ * @return the list of {@link QueryCharacteristic characteristics}.
78+ */
5779 public List <QueryCharacteristic > getCharacteristics () {
5880 return characteristics ;
5981 }
@@ -63,22 +85,50 @@ public Iterator<QueryCharacteristic> iterator() {
6385 return this .characteristics .iterator ();
6486 }
6587
88+ /**
89+ * Create a new {@link RangeQuery range query characteristic} used to define range queries against an encrypted field.
90+ *
91+ * @param <T> targeted field type
92+ * @return new instance of {@link RangeQuery}.
93+ */
6694 public static <T > RangeQuery <T > range () {
6795 return new RangeQuery <>();
6896 }
6997
98+ /**
99+ * Create a new {@link EqualityQuery equality query characteristic} used to define equality queries against an
100+ * encrypted field.
101+ *
102+ * @param <T> targeted field type
103+ * @return new instance of {@link EqualityQuery}.
104+ */
70105 public static <T > EqualityQuery <T > equality () {
71106 return new EqualityQuery <>(null );
72107 }
73108
109+ /**
110+ * {@link QueryCharacteristic} for equality comparison.
111+ *
112+ * @param <T>
113+ * @since 4.5
114+ */
74115 public static class EqualityQuery <T > implements QueryCharacteristic {
75116
76117 private final @ Nullable Long contention ;
77118
119+ /**
120+ * Create new instance of {@link EqualityQuery}.
121+ *
122+ * @param contention can be {@literal null}.
123+ */
78124 public EqualityQuery (@ Nullable Long contention ) {
79125 this .contention = contention ;
80126 }
81127
128+ /**
129+ * @param contention concurrent counter partition factor.
130+ * @return new instance of {@link EqualityQuery}.
131+ */
82132 public EqualityQuery <T > contention (long contention ) {
83133 return new EqualityQuery <>(contention );
84134 }
@@ -94,64 +144,120 @@ public Document toDocument() {
94144 }
95145 }
96146
147+ /**
148+ * {@link QueryCharacteristic} for range comparison.
149+ *
150+ * @param <T>
151+ * @since 4.5
152+ */
97153 public static class RangeQuery <T > implements QueryCharacteristic {
98154
99155 private final @ Nullable Range <T > valueRange ;
100156 private final @ Nullable Integer trimFactor ;
101157 private final @ Nullable Long sparsity ;
158+ private final @ Nullable Long precision ;
102159 private final @ Nullable Long contention ;
103160
104161 private RangeQuery () {
105- this (Range .unbounded (), null , null , null );
162+ this (Range .unbounded (), null , null , null , null );
106163 }
107164
165+ /**
166+ * Create new instance of {@link RangeQuery}.
167+ *
168+ * @param valueRange
169+ * @param trimFactor
170+ * @param sparsity
171+ * @param contention
172+ */
108173 public RangeQuery (@ Nullable Range <T > valueRange , @ Nullable Integer trimFactor , @ Nullable Long sparsity ,
109- @ Nullable Long contention ) {
174+ @ Nullable Long precision , @ Nullable Long contention ) {
110175 this .valueRange = valueRange ;
111176 this .trimFactor = trimFactor ;
112177 this .sparsity = sparsity ;
178+ this .precision = precision ;
113179 this .contention = contention ;
114180 }
115181
116- @ Override
117- public String queryType () {
118- return "range" ;
119- }
120-
182+ /**
183+ * @param lower the lower value range boundary for the queryable field.
184+ * @return new instance of {@link RangeQuery}.
185+ */
121186 public RangeQuery <T > min (T lower ) {
122187
123188 Range <T > range = Range .of (Bound .inclusive (lower ),
124189 valueRange != null ? valueRange .getUpperBound () : Bound .unbounded ());
125- return new RangeQuery <>(range , trimFactor , sparsity , contention );
190+ return new RangeQuery <>(range , trimFactor , sparsity , precision , contention );
126191 }
127192
193+ /**
194+ * @param upper the upper value range boundary for the queryable field.
195+ * @return new instance of {@link RangeQuery}.
196+ */
128197 public RangeQuery <T > max (T upper ) {
129198
130199 Range <T > range = Range .of (valueRange != null ? valueRange .getLowerBound () : Bound .unbounded (),
131200 Bound .inclusive (upper ));
132- return new RangeQuery <>(range , trimFactor , sparsity , contention );
201+ return new RangeQuery <>(range , trimFactor , sparsity , precision , contention );
133202 }
134203
204+ /**
205+ * @param trimFactor value to control the throughput of concurrent inserts and updates.
206+ * @return new instance of {@link RangeQuery}.
207+ */
135208 public RangeQuery <T > trimFactor (int trimFactor ) {
136- return new RangeQuery <>(valueRange , trimFactor , sparsity , contention );
209+ return new RangeQuery <>(valueRange , trimFactor , sparsity , precision , contention );
137210 }
138211
212+ /**
213+ * @param sparsity value to control the value density within the index.
214+ * @return new instance of {@link RangeQuery}.
215+ */
139216 public RangeQuery <T > sparsity (long sparsity ) {
140- return new RangeQuery <>(valueRange , trimFactor , sparsity , contention );
217+ return new RangeQuery <>(valueRange , trimFactor , sparsity , precision , contention );
141218 }
142219
220+ /**
221+ * @param contention concurrent counter partition factor.
222+ * @return new instance of {@link RangeQuery}.
223+ */
143224 public RangeQuery <T > contention (long contention ) {
144- return new RangeQuery <>(valueRange , trimFactor , sparsity , contention );
225+ return new RangeQuery <>(valueRange , trimFactor , sparsity , precision , contention );
226+ }
227+
228+ /**
229+ * @param precision digits considered comparing floating point numbers.
230+ * @return new instance of {@link RangeQuery}.
231+ */
232+ public RangeQuery <T > precision (long precision ) {
233+ return new RangeQuery <>(valueRange , trimFactor , sparsity , precision , contention );
234+ }
235+
236+ @ Override
237+ public String queryType () {
238+ return "range" ;
145239 }
146240
147241 @ Override
148242 @ SuppressWarnings ("unchecked" )
149243 public Document toDocument () {
150244
151- return QueryCharacteristic .super .toDocument ().append ("contention" , contention ).append ("trimFactor" , trimFactor )
152- .append ("sparsity" , sparsity ).append ("min" , valueRange .getLowerBound ().getValue ().orElse ((T ) BsonNull .VALUE ))
153- .append ("max" , valueRange .getUpperBound ().getValue ().orElse ((T ) BsonNull .VALUE ));
245+ Document target = QueryCharacteristic .super .toDocument ();
246+ if (contention != null ) {
247+ target .append ("contention" , contention );
248+ }
249+ if (trimFactor != null ) {
250+ target .append ("trimFactor" , trimFactor );
251+ }
252+ if (valueRange != null ) {
253+ target .append ("min" , valueRange .getLowerBound ().getValue ().orElse ((T ) BsonNull .VALUE )).append ("max" ,
254+ valueRange .getUpperBound ().getValue ().orElse ((T ) BsonNull .VALUE ));
255+ }
256+ if (sparsity != null ) {
257+ target .append ("sparsity" , sparsity );
258+ }
259+
260+ return target ;
154261 }
155262 }
156-
157263}
0 commit comments