Requirements:
I want to apply some functions on the inner values of the JsonNode. The functions can be different eg:- lowercasing some values or appending something to the values or replace the values with something. How can I achieve that using Jackson library? Note that the structure of the JSON data can be different which means I want to build a generic system which will accept some path expression which will basically decide where to change. I want to use functional programming style, so that I can pass these functions as arguments.
eg:
input:
{
"name": "xyz",
"values": [
{
"id": "xyz1",
"sal": "1234",
"addresses": [
{
"id": "add1",
"name": "ABCD",
"dist": "123"
},
{
"id": "add2",
"name": "abcd3",
"dist": "345"
}
]
},
{
"id": "xyz2",
"sal": "3456",
"addresses": [
{
"id": "add1",
"name": "abcd",
"dist": "123"
},
{
"id": "add2",
"name": "XXXXX",
"dist": "345"
}
]
}
]
}
In this case I have to two functions basically, lowercase() and convert_to_number(). I want to apply lowercase() function on all the "name" attribute inside all the "addresses" of each "value".
same goes for convert_to_number() , but for all the "dist" attribute.
So, basically the JSON expressions will be something like below for the functions:
lowercase() : /values/*/addresses/*/name
convert_to_number() : /values/*/addresses/*/dist
output:
{
"name": "xyz",
"values": [
{
"id": "xyz1",
"sal": "1234",
"addresses": [
{
"id": "add1",
"name": "abcd",
"dist": 123
},
{
"id": "add2",
"name": "abcd3",
"dist": 345
}
]
},
{
"id": "xyz2",
"sal": "3456",
"addresses": [
{
"id": "add1",
"name": "abcd",
"dist": 123
},
{
"id": "add2",
"name": "xxxx",
"dist": 345
}
]
}
]
}
Client code:
JsonNode jsonNode = ...
applyFunctionsRecursivelyBasedOnExpr(JsonNode jsonNode, String expr, Function )
As @MichalZiober in his answer already pointed out, JsonPath offers a much more powerful API than Jackson, when you need to do JSON-path-based operations.
Using methods JsonPath.parse and WriteContext.map
you can solve your problem in just a few lines:
import java.io.File;
import com.jayway.jsonpath.Configuration;
import com.jayway.jsonpath.JsonPath;
public class Main {
public static void main(String[] args) throws Exception {
File file = new File("input.json");
String json = JsonPath.parse(file)
.map("$.values[*].addresses[*].name", Main::lowerCase)
.map("$.values[*].addresses[*].dist", Main::convertToNumber)
.jsonString();
System.out.println(json);
}
private static Object lowerCase(Object currentValue, Configuration configuration) {
if (currentValue instanceof String)
return ((String)currentValue).toLowerCase();
return currentValue;
}
private static Object convertToNumber(Object currentValue, Configuration configuration) {
if (currentValue instanceof String)
return Integer.valueOf((String)currentValue);
return currentValue;
}
}
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With