|
|
@@ -1,9 +1,15 @@
|
|
|
package org.leumasjaffe.json.schema.tester;
|
|
|
|
|
|
+import java.util.ArrayList;
|
|
|
import java.util.Arrays;
|
|
|
+import java.util.Collections;
|
|
|
import java.util.List;
|
|
|
+import java.util.stream.Collectors;
|
|
|
+import java.util.stream.IntStream;
|
|
|
|
|
|
+import org.leumasjaffe.container.EitherStream;
|
|
|
import org.leumasjaffe.json.schema.Tester;
|
|
|
+import org.leumasjaffe.json.schema.ValidationException;
|
|
|
|
|
|
import com.fasterxml.jackson.databind.JsonNode;
|
|
|
|
|
|
@@ -20,9 +26,45 @@ public class OneOfTester implements Tester {
|
|
|
this(Arrays.asList(testers));
|
|
|
}
|
|
|
|
|
|
+ @Override
|
|
|
+ public void validate(final JsonNode node) {
|
|
|
+ final List<ValidationException> exceptions = this.new Helper(node).validate();
|
|
|
+ if (!exceptions.isEmpty()) {
|
|
|
+ throw new ValidationException("oneOf", "failed to match exactly one sub-schema",
|
|
|
+ exceptions);
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
@Override
|
|
|
public boolean accepts(JsonNode node) {
|
|
|
return children.parallelStream().filter(t -> t.accepts(node)).count() == 1;
|
|
|
}
|
|
|
|
|
|
+ @RequiredArgsConstructor
|
|
|
+ @FieldDefaults(makeFinal=true)
|
|
|
+ private class Helper {
|
|
|
+ JsonNode node;
|
|
|
+
|
|
|
+ List<ValidationException> validate() {
|
|
|
+ final List<Integer> hits = new ArrayList<>();
|
|
|
+ final List<ValidationException> exceptions = new ArrayList<>();
|
|
|
+ EitherStream.from(IntStream.range(0, children.size()))
|
|
|
+ .map(this::validateIdx, ValidationException.class)
|
|
|
+ .forEach(e -> e.consume(hits::add, exceptions::add));
|
|
|
+ if (hits.isEmpty()) {
|
|
|
+ return exceptions;
|
|
|
+ } else if (hits.size() > 1) {
|
|
|
+ return hits.stream().map(i -> new ValidationException("", "matched schema at index " + i))
|
|
|
+ .collect(Collectors.toList());
|
|
|
+ } else {
|
|
|
+ return Collections.emptyList();
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ private Integer validateIdx(int i) {
|
|
|
+ children.get(i).validate(node);
|
|
|
+ return i;
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
}
|