/** * Returns true if expected is a subset of returned * * This is used for JSON serialiser comparisons. This is taken from * the 'equals' definition of JsonNode's, but without the length check * on the list of children nodes, plus location reporting. * * @param expected * @param returned * @return */ protected boolean isJsonNodeSubset(JsonNode expected, JsonNode returned) { if (returned == null) { errorDescription = "Returned value is null, expected JSON:\n" + expected.toString(); return false; } if (returned == expected) return true; if (returned.getClass() != expected.getClass()) { errorDescription = "Returned value class is incorrect, expected JSON: " + expected.toString() + ", returned JSON: " + returned.toString(); return false; } switch (expected.getNodeType()) { case ARRAY: return isArrayNodeSubset((ArrayNode)expected, (ArrayNode)returned); case OBJECT: return isObjectNodeSubset((ObjectNode)expected, (ObjectNode)returned); default: return isValueEqual((ValueNode)expected, (ValueNode)returned); // Will be a ValueNode subclass } }
public void jsonToMap(String currentPath, JsonNode jsonNode, Map<String, String> map) { if (jsonNode.isObject()) { ObjectNode objectNode = (ObjectNode) jsonNode; Iterator<Entry<String, JsonNode>> iter = objectNode.fields(); String pathPrefix = currentPath.isEmpty() ? "" : currentPath + "."; while (iter.hasNext()) { Entry<String, JsonNode> entry = iter.next(); jsonToMap(pathPrefix + entry.getKey(), entry.getValue(), map); } } else if (jsonNode.isArray()) { ArrayNode arrayNode = (ArrayNode) jsonNode; for (int i = 0; i < arrayNode.size(); i++) { jsonToMap(currentPath + "." + i, arrayNode.get(i), map); } } else if (jsonNode.isValueNode()) { ValueNode valueNode = (ValueNode) jsonNode; map.put(currentPath, valueNode.asText()); } }
private void buildQueryString(URIBuilder url, String path, ObjectNode node) { Iterator<Entry<String, JsonNode>> iterator = node.fields(); while (iterator.hasNext()) { Entry<String, JsonNode> field = iterator.next(); String fieldName = field.getKey(); JsonNode childNode = field.getValue(); if (childNode instanceof ObjectNode) { buildQueryString(url, getPath(path, fieldName), (ObjectNode) childNode); } else if (childNode instanceof ValueNode) { ValueNode valueNode = (ValueNode) childNode; if (!valueNode.isNull()) { url.addParameter(getPath(path, fieldName), valueNode.asText()); } } } }
private void addKeys(String currentPath, JsonNode jsonNode, Map<Object, Object> props) { if (jsonNode.isObject()) { ObjectNode objectNode = (ObjectNode) jsonNode; Iterator<Map.Entry<String, JsonNode>> iter = objectNode.fields(); String pathPrefix = currentPath.isEmpty() ? "" : currentPath + "."; while (iter.hasNext()) { Map.Entry<String, JsonNode> entry = iter.next(); addKeys(pathPrefix + entry.getKey(), entry.getValue(), props); } } else if (jsonNode.isArray()) { ArrayNode arrayNode = (ArrayNode) jsonNode; for (int i = 0; i < arrayNode.size(); i++) { addKeys(currentPath + "[" + i + "]", arrayNode.get(i), props); } } else if (jsonNode.isValueNode()) { ValueNode valueNode = (ValueNode) jsonNode; if(isAllowOverride || !props.containsKey(currentPath)) props.put(currentPath, valueNode.asText()); } }
@Deprecated public static ValueNode toValueNode(Object value) { if (value == null) return NullNode.instance; if (value instanceof ValueNode) return (ValueNode) value; if (value instanceof Boolean) return BooleanNode.valueOf((boolean) value); else if (value instanceof Integer) return IntNode.valueOf((int) value); else if (value instanceof Long) return LongNode.valueOf((long) value); else if (value instanceof Double) return DoubleNode.valueOf((double) value); else if (value instanceof Float) return FloatNode.valueOf((float) value); return TextNode.valueOf(value.toString()); }
public static ValueNode toValueNode(Object value) { if (value == null) return NullNode.instance; if (value instanceof ValueNode) return (ValueNode) value; if (value instanceof Boolean) return BooleanNode.valueOf((boolean) value); else if (value instanceof Integer) return IntNode.valueOf((int) value); else if (value instanceof Long) return LongNode.valueOf((long) value); else if (value instanceof Double) return DoubleNode.valueOf((double) value); else if (value instanceof Float) return FloatNode.valueOf((float) value); return TextNode.valueOf(value.toString()); }
/** * Creates a new JSON-RPC request as a JSON object * * @param id request id * @param method request method * @param params request params * @return a new request as a JSON object */ @NotNull protected ObjectNode request(@NotNull ValueNode id, @NotNull String method, @NotNull JsonNode params) { if (method.isEmpty()) { throw new IllegalArgumentException("Method is not set"); } ObjectNode requestNode = mapper.createObjectNode(); requestNode.put(JSONRPC, VERSION_2_0); requestNode.put(METHOD, method); requestNode.set(PARAMS, params); if (!id.isNull()) { requestNode.set(ID, id); } return requestNode; }
private static void buildConfigFor(String path, Map<String, String> config, JsonNode node) { for (Iterator<Map.Entry<String, JsonNode>> i = node.fields(); i.hasNext();) { Map.Entry<String, JsonNode> field = i.next(); if (field.getValue() instanceof ValueNode) { ValueNode valueNode = (ValueNode) field.getValue(); config.put(DOT_JOINER.join(path, field.getKey()), valueNode.asText()); } else if (field.getValue() instanceof ArrayNode) { StringBuilder combinedValue = new StringBuilder(); ArrayNode arrayNode = (ArrayNode) field.getValue(); for (Iterator<JsonNode> it = arrayNode.elements(); it.hasNext();) { String value = it.next().asText().replaceAll("^\"|\"$", ""); if (combinedValue.length() > 0) combinedValue.append(','); combinedValue.append(value); } config.put(DOT_JOINER.join(path, field.getKey()), combinedValue.toString()); } buildConfigFor(DOT_JOINER.join(path, field.getKey()), config, field.getValue()); } }
public static void fromJson(WithIfCurrent dest,ObjectNode node) { JsonNode x=node.get("onlyIfCurrent"); if(x instanceof ValueNode && x.booleanValue()) { dest.setIfCurrentOnly(true); x=node.get("documentVersions"); if(x instanceof ArrayNode) { List<String> versions=new ArrayList<>(x.size()); for(Iterator<JsonNode> itr=x.elements();itr.hasNext();) { JsonNode elem=itr.next(); if(!(elem instanceof NullNode)) { versions.add(elem.asText()); } } dest.setDocumentVersions(versions); } } else { dest.setIfCurrentOnly(false); } }
/** * Returns a Java object for a json value node based on the node type. */ public static Object valueFromJson(ValueNode node) { if (node instanceof NullNode) { return null; } else { if(node instanceof TextNode) { return node.textValue(); } else if(node instanceof BooleanNode) { return node.booleanValue(); } else if(node instanceof NumericNode) { return node.numberValue(); } else { throw new RuntimeException("Unsupported node type:"+node.getClass().getName()); } } }
protected boolean isValueEqual(ValueNode expected, ValueNode returned) { boolean result = returned.equals(expected); if (!result) { errorDescription = "Expected value: '" + expected.toString() + "', returned value: '" + returned.toString() + "' are not equal"; } return result; }
@Override protected boolean equals(ValueNode value1,ValueNode value2) { if(value1.isNumber()&&value2.isNumber()) { return value1.asText().equals(value2.asText()); } else { return value1.equals(value2); } }
private Duration deserializeObject(TreeNode tree, DeserializationContext c) throws JsonMappingException { if (tree == null) { throw c.mappingException("expected object"); } TreeNode node; ValueNode valueNode; final long duration; final TimeUnit unit; if ((node = tree.get("duration")) != null && node.isValueNode() && (valueNode = (ValueNode) node).isNumber()) { duration = valueNode.asLong(); } else { throw c.mappingException("duration is not a numeric field"); } if ((node = tree.get("unit")) != null && node.isValueNode() && (valueNode = (ValueNode) node).isTextual()) { unit = TimeUnit.valueOf(valueNode.asText().toUpperCase()); } else { unit = Duration.DEFAULT_UNIT; } return new Duration(duration, unit); }
public void flattenJsonIntoMap(String currentPath, JsonNode jsonNode, Map<String, Object> map) { if (jsonNode.isObject()) { ObjectNode objectNode = (ObjectNode) jsonNode; Iterator<Map.Entry<String, JsonNode>> iter = objectNode.fields(); String pathPrefix = currentPath.isEmpty() ? "" : currentPath + "."; while (iter.hasNext()) { Map.Entry<String, JsonNode> entry = iter.next(); flattenJsonIntoMap(pathPrefix + entry.getKey(), entry.getValue(), map); } } else if (jsonNode.isArray()) { ArrayNode arrayNode = (ArrayNode) jsonNode; for (int i = 0; i < arrayNode.size(); i++) { flattenJsonIntoMap(currentPath + "[" + i + "]", arrayNode.get(i), map); } } else if (jsonNode.isValueNode()) { ValueNode valueNode = (ValueNode) jsonNode; Object value = null; if (valueNode.isNumber()) { value = valueNode.numberValue(); } else if (valueNode.isBoolean()) { value = valueNode.asBoolean(); } else if (valueNode.isTextual()){ value = valueNode.asText(); } map.put(currentPath, value); } }
private void flattenJsonTree(String currentPath, JsonNode jsonNode, ByteArrayOutputStream out) throws SerializationException { if (jsonNode.isObject()) { ObjectNode objectNode = (ObjectNode) jsonNode; Iterator<Map.Entry<String, JsonNode>> iter = objectNode.fields(); String pathPrefix = currentPath.isEmpty() ? "" : currentPath + "."; while (iter.hasNext()) { Map.Entry<String, JsonNode> entry = iter.next(); flattenJsonTree(pathPrefix + entry.getKey(), entry.getValue(), out); } } else if (jsonNode.isArray()) { throw new SerializationException("Arrays in JSON are not supported yet."); } else if (jsonNode.isValueNode()) { ValueNode valueNode = (ValueNode) jsonNode; if (!fieldMapping.containsField(currentPath)) { fieldMapping.put(currentPath, delimiters[currentDelimiterIdx++], getNodeType(jsonNode)); } else { DataType existingType = fieldMapping.getDataType(currentPath); DataType newType = getNodeType(valueNode); if (existingType != newType) { DataType encapsulatingType = DataType.encapsulatingType(existingType, newType); fieldMapping.updateType(currentPath, encapsulatingType); } } try { byte fieldByte = fieldMapping.getDelimiter(currentPath); out.write(fieldByte); out.write(valueNode.asText().getBytes()); out.write(fieldByte); } catch (IOException e) { throw new SerializationException(e.getMessage()); } } }
@Override public CustomAttribute deserialize(JsonParser jp, DeserializationContext ctxt) throws IOException { CustomAttribute cda = null; final String currentName = jp.getParsingContext().getCurrentName(); final ObjectMapper mapper = (ObjectMapper) jp.getCodec(); final ValueNode vNode = mapper.readTree(jp); if (vNode.asToken().isScalarValue()) { if (vNode.getNodeType() == JsonNodeType.BOOLEAN) { cda = new CustomAttribute<Boolean>(currentName, vNode.asBoolean(), Boolean.class); } else if (vNode.getNodeType() == JsonNodeType.STRING) { cda = new CustomAttribute<String>(currentName, vNode.asText(), String.class); } else if (vNode.getNodeType() == JsonNodeType.NUMBER) { final NumericNode nNode = (NumericNode) vNode; if (currentName.endsWith("_at")) { cda = new CustomAttribute<Long>(currentName, vNode.longValue(), Long.class); } else if (nNode.isInt()) { cda = new CustomAttribute<Integer>(currentName, vNode.intValue(), Integer.class); } else if (nNode.isFloat()) { cda = new CustomAttribute<Float>(currentName, vNode.floatValue(), Float.class); } else if (nNode.isDouble()) { cda = new CustomAttribute<Double>(currentName, vNode.doubleValue(), Double.class); } else if (nNode.isLong()) { cda = new CustomAttribute<Long>(currentName, vNode.longValue(), Long.class); } else { cda = new CustomAttribute<String>(currentName, vNode.asText(), String.class); } } else { cda = new CustomAttribute<String>(currentName, vNode.asText(), String.class); } } return cda; }
private void fillDocVer(JsonNode node,ResultMetadata rmd) { if(node instanceof ValueNode) { String docver=node.asText(); if(rmd.getDocumentVersion()!=null) rmd.setDocumentVersion(docver); } }
@Test public void testMatches() { // Given ValueNode valueNode = jsonNodeFactory.numberNode(Integer.valueOf(10)); IsJsonInt matcher = new IsJsonInt(10); // When boolean matches = matcher.matches(valueNode); // Then assertTrue(matches); }
@Test public void testMatches_false() { // Given ValueNode valueNode = jsonNodeFactory.numberNode(Integer.valueOf(20)); IsJsonInt matcher = new IsJsonInt(10); // When boolean matches = matcher.matches(valueNode); // Then assertFalse(matches); }
public Request(@JsonProperty("jsonrpc") @Nullable String jsonrpc, @JsonProperty("method") @Nullable String method, @JsonProperty("params") @NotNull JsonNode params, @JsonProperty("id") @NotNull ValueNode id) { this.jsonrpc = jsonrpc; this.method = method; this.id = id; this.params = params; }
@Override protected boolean equals(ValueNode value1, ValueNode value2) { if (value1.isNumber() && value2.isNumber()) { return value1.asText().equals(value2.asText()); } else { return value1.equals(value2); } }
/** * Returns a Json value node for the given value. Dates are converted to strings */ public static ValueNode valueToJson(Object value) { if(value==null) { return JsonNodeFactory.instance.nullNode(); } else if(value instanceof String) { return JsonNodeFactory.instance.textNode((String)value); } else if(value instanceof Number) { if (value instanceof BigDecimal) { return JsonNodeFactory.instance.numberNode((BigDecimal) value); } else if (value instanceof BigInteger) { return JsonNodeFactory.instance.numberNode((BigInteger) value); } else if (value instanceof Double) { return JsonNodeFactory.instance.numberNode((Double) value); } else if (value instanceof Float) { return JsonNodeFactory.instance.numberNode((Float) value); } else if (value instanceof Long) { return JsonNodeFactory.instance.numberNode((Long) value); } else { return JsonNodeFactory.instance.numberNode( ((Number)value).intValue()); } } else if(value instanceof Boolean) { return JsonNodeFactory.instance.booleanNode( ((Boolean)value).booleanValue()); } else if(value instanceof Date) { return JsonNodeFactory.instance.textNode(Constants.getDateFormat().format((Date)value)); } else { return JsonNodeFactory.instance.textNode(value.toString()); } }
/** * Converts a json document to an object tree of maps/lists/values * * If json is a value, then the corresponding Java object is returned. * * If json is an array, a List is returned. Elements of the list are converted recursively * * If json is an object, a Map is returned. */ public static Object fromJson(JsonNode json) { if(json==null||json instanceof NullNode) { return null; } else if(json instanceof ObjectNode) { return fromJson((ObjectNode)json); } else if(json instanceof ArrayNode) { return fromJson((ArrayNode)json); } else { return valueFromJson( (ValueNode)json); } }
private void addKeys(String currentPath, JsonNode jsonNode, Map<String, JsonPathData> map, List<JsonNodeType> knownTypes) { if (jsonNode.isObject()) { ObjectNode objectNode = (ObjectNode) jsonNode; Iterator<Map.Entry<String, JsonNode>> iterator = objectNode.fields(); String pathPrefix = currentPath.isEmpty() ? "" : currentPath + "."; if (knownTypes == null) knownTypes = new ArrayList<>(); knownTypes.add(JsonNodeType.OBJECT); while (iterator.hasNext()) { Map.Entry<String, JsonNode> entry = iterator.next(); addKeys(pathPrefix + entry.getKey(), entry.getValue(), map, new ArrayList<>(knownTypes)); } } else if (jsonNode.isArray()) { ArrayNode arrayNode = (ArrayNode) jsonNode; if (currentPath.isEmpty()) currentPath = "root"; if (knownTypes == null) knownTypes = new ArrayList<>(); knownTypes.add(JsonNodeType.ARRAY); for (int i = 0; i < arrayNode.size(); i++) { addKeys(currentPath + "." + i, arrayNode.get(i), map, new ArrayList<>(knownTypes)); } } else if (jsonNode.isValueNode()) { ValueNode valueNode = (ValueNode) jsonNode; if (knownTypes == null) knownTypes = new ArrayList<>(); knownTypes.add(valueNode.getNodeType()); JsonPathData.JsonPathDataBuilder data = JsonPathData.builder().types(knownTypes); switch (valueNode.getNodeType()) { case NUMBER: { if (valueNode.asText().contains(".")) map.put(currentPath, data.value(valueNode.asDouble()).build()); else map.put(currentPath, data.value(valueNode.asLong()).build()); break; } case BOOLEAN: { map.put(currentPath, data.value(valueNode.asBoolean()).build()); break; } default: { map.put(currentPath, data.value(valueNode.asText()).build()); break; } } } }
@Override protected boolean isValue(JsonNode value) { return value instanceof ValueNode; }
@Override protected ValueNode asValue(JsonNode value) { return (ValueNode)value; }
@Override public Subscription.Topic deserialize(JsonParser jp, DeserializationContext ctxt) throws IOException { final ObjectMapper mapper = (ObjectMapper) jp.getCodec(); final ValueNode vNode = mapper.readTree(jp); return Subscription.Topic.valueOf(vNode.asText()); }
/** * Performs single JSON-RPC request and return JSON-RPC response * * @param request JSON-RPC request as a Java object * @param service service object * @return JSON-RPC response as a Java object * @throws Exception in case of a runtime error (reflections, business logic...) */ @NotNull private Response handleSingle(@NotNull Request request, @NotNull Object service) throws Exception { // Check mandatory fields and correct protocol version String requestMethod = request.getMethod(); String jsonrpc = request.getJsonrpc(); ValueNode id = request.getId(); if (jsonrpc == null || requestMethod == null) { log.error("Not a JSON-RPC request: " + request); return new ErrorResponse(id, INVALID_REQUEST); } if (!jsonrpc.equals(VERSION)) { log.error("Not a JSON_RPC 2.0 request: " + request); return new ErrorResponse(id, INVALID_REQUEST); } JsonNode params = request.getParams(); if (!params.isObject() && !params.isArray() && !params.isNull()) { log.error("Params of request: '" + request + "' should be an object, an array or null"); return new ErrorResponse(id, INVALID_REQUEST); } ClassMetadata classMetadata = classesMetadata.get(service.getClass()); if (!classMetadata.isService()) { log.warn(service.getClass() + " is not available as a JSON-RPC 2.0 service"); return new ErrorResponse(id, METHOD_NOT_FOUND); } MethodMetadata method = classMetadata.getMethods().get(requestMethod); if (method == null) { log.error("Unable find a method: '" + requestMethod + "' in a " + service.getClass()); return new ErrorResponse(id, METHOD_NOT_FOUND); } ContainerNode<?> notNullParams = !params.isNull() ? (ContainerNode<?>) params : mapper.createObjectNode(); Object[] methodParams; try { methodParams = convertToMethodParams(notNullParams, method); } catch (IllegalArgumentException e) { log.error("Bad params: " + notNullParams + " of a method '" + method.getName() + "'", e); return new ErrorResponse(id, INVALID_PARAMS); } Object result = method.getMethod().invoke(service, methodParams); return new SuccessResponse(id, result); }
public SuccessResponse(@JsonProperty("id") @NotNull ValueNode id, @JsonProperty("result") @Nullable Object result) { super(id); this.result = result; }
public Response(@NotNull ValueNode id) { this.id = id; jsonrpc = VERSION; }
public Response(@NotNull ValueNode id, @NotNull String jsonrpc) { this.id = id; this.jsonrpc = jsonrpc; }
@NotNull public ValueNode getId() { return id; }
@JsonCreator public ErrorResponse(@JsonProperty("id") @NotNull ValueNode id, @JsonProperty("error") @NotNull ErrorMessage error) { super(id); this.error = error; }
@Override protected ValueNode asValue(JsonNode value) { return (ValueNode) value; }