Remove Elements from JSON String - java

I have a JSON string as follows:
{
"account": "1234",
"type": "ar-type",
"eventTypes": "Update",
"objectClassName": "com.triype",
"objectJson": "{\"Name\":\"pdpot\",\"traptype\":\"adpot",\"displayName\":\"pdpot",\"experimentName\":\"pdpotpie\",\"creationTime\":\"Mar 18, 2020 5:58:58 PM\",\"createdBy\":{\"userProfileOne\":\"s:pdx\",\"userProfileTwo\":\"sid\",\"domainId\":\"did:pdx-tod-64003\"},\"lastModifiedBy\":{\"userProfileArn\":\"s:pdx-tod-64003\"},\"createdBy\":{\"userProfileOne\":\"s:p\",\"userProfileTwo\":\"si\",\"domainId\":\"did:ppot\"}}}
}
I get this input as a string and before passing it as a string to a parser I need to perform some string filtering and remove all "userProfileOne", "userProfileTwo","domainId" and their keys, without compromising the JSON structure. I am currently writing this code in Java using gson and json.
Note: There are multiple occurences of UserProfileOne, UserProfileTwo and DomainID.
The required Output is as follows:
{
"account": "1234",
"type": "ar-type",
"eventTypes": "Update",
"objectClassName": "com.triype",
"objectJson": "{\"Name\":\"pdpot\",\"traptype\":\"adpot",\"displayName\":\"pdpot",\"experimentName\":\"pdpotpie\",\"creationTime\":\"Mar 18, 2020 5:58:58 PM\"}}
}
Currently I am using substringBetween. But the operation does not work as intended.

A potential approach is to deserialize the json into a java structure then filter this structure by set to null fields you don't want to be serialize.
By using framework like Jackson you can set this before serialization on the ObjectMapper
mapper.setSerializationInclusion(Include.NON_NULL). So all null values won't be serialized in the final json/result.

I think the best maintainable way would be to create a class structure corresponding to that json and map it to the class.
Use #JsonIgnore on the fields to be ignored and then map it back to JSON from the class structure.
Another approach, a bit complex to implement, is to go through each node in the json and remove that node if it's not required
You can also do it by string matching but I don't think that is a good approach.

Related

How to get the set inside nested JsonNode using Jackson

I have a below JSON structure. which I need to parse using the Jackson library. I am building a web-service, which accept below JSON in a POST method's BODY.
{
"organization": {
"products": [
"foo",
"bar",
"baz"
]
},
"mission" : "to be the best in domain"
}
Till, now I was having simple JSON body, which wasn't having nested and JSON element, like in this case organization is another JSON node which contains a Set of products.
This JSON keys are not mandatory, And I am accepting/storing organization JSON in JsonNode. And doing below checks.
If organization is null.
If organization is not null and it has products key.
But after that I don't know how to fetch the set of boards from this JsonNode and store it in Java's HashSet.
My expected O/P should be to have a set of boards extracted from my organization JsonNode.
P.S. :- I think I have to use the ObjectMapper but couldn't find a direct way of getting the Set. Looks like I need to use some JsonParser with which I am not very familier.
You can create DTOs(Data Transfer Objects) for your purpose. The nested objects could have the structure as below:
class Organization {
List<String> Products;
.....
}
class WebOrganizationRequest {
Organization organization;
String mission;
}
By creating objects in this way you are mapping your JSON objects to classes and Jackson will typecast the JSON as an instance of WebOrganizationRequest when you pass it in the controller with WebOrganizationRequest as the request body type.

Jersey - Moxy returning appended json in class property

I have a Jersey client that makes a call to a 3rd party rest api and retrieves some JSON.
{"A":1,"W":2,"List":[{"name":"John","amount":10.0}]}
After that I need to append this JSON to my response class and give it back in the response.
#XmlRootElement
public class MyResponse {
private JsonObject body;
private String status;
I manage to assign the value that comes from the 3rd party api to body but the response that's sent is like this:
{
"status": "success",
"body": {
"entry": [
{
"key": "A",
"value": 1
} ,
{
"key": "W",
"value": 2
},
{
"key": "List",
"value": "[{\"name\":\"John\",\"amount\":10.0}]"
}
]
}
}
So there are two main issues, moxy is generating key and value elements while I would like it to be key: value and also it is not generating properly the 2nd level objects in the JSON structure provided by the API.
MOXy is a JAXB implementation, while JsonObject is part of JSON-P. MOXy happens to be able to deal with JSON too, but that is a proprietary extension over the JAXB standard. As far as I know, there is no default mapping available between JSON-P and JAXB. The reason you're seeing those key/value entries must be because JsonObject extends java.util.Map, so you get the default MOXy mapping for that type.
I think you have the following possibilities:
Go with either JSON-P or JAXB/MOXy (MOXy required for its additional JSON binding) only.
Use one of the JAXB/MOXy mechanisms for mapping custom types from/to JAXB. The standard way is to use an XmlAdapter, examples for dealing with Maps in particular are here and here. But I think this will be difficult if you don't know the structure of the 3rd party JSON content and want to keep nested levels intact.
Yet another possibility might be to use a proprietary API like Jackson, but I can't help with that.

Check if JSON is valid in JAVA using Jackson

I have a JSON string which I am storing it in DB as a string. In front-end, I am rendering this JSON as object.
I am using:
JSON.parse(string);
Uncaught Syntax error: Unexpected Token
String :
{
"id": "295cd59f-4033-438c-9bf4-c571829f134e",
"from": "Shrisha S.<shrisha#s.com>",
"to": [
"Katie Porter <katie.porter#ss.com>"
],
"cc": [
"Jack d<jack.d#dd.com>, Keerthi<keerthi.s#dd.com>"
],
"bcc": [
]
}
Is there any way I can check If JSON is valid or not in JAVA?
One thing to be noted here is that, I don't have a schema defined for JSON which I can map to, i.e. JSON can hold anything.
I am currently trying out with JACKSON but for that I need a pre-defined schema which I don't have. Is there anyway this can be fixed?
You can read it as a JsonNode, no need to map it to a specific Class, its generic:
try{
ObjectMapper objectMapper = ...;
JsonNode jsonNode = objectMapper.readTree(yourJsonString);
} catch(JsonProcessingException e){........}
There are two different parts to the question. First is whether it is valid JSON, and second whether it contains specific set of information.
#pdem already answered first part (you can also read JSON as java.lang.Object to get the same effect).
But for second part, JSON Schema is not usually a good way, as it focuses on JSON aspects but not on more meaningful part of actual data, possible sub-typing and so on, which matter at Java level where all actual data processing occurs.
So usually you would define a POJO (or ideally just use one you use for actual data processing), bind to it (with ObjectMapper.readValue()), and then check whether data is not only technically valid wrt low-level data types, but also that it conforms to additional business constraints.
For latter part you can either write Java code, or use an annotation based framework such as Bean Validation API (JSR-303); see for example:
http://beanvalidation.org/
plus there are many #bean-validation tagged questions here as well related to usage. Some frameworks add explicit support for it; for example the best Java service framework, DropWizard does this. Others like Spring Boot have support as well.
JSON specification forbids it from using newline characters, make sure you are replacing newline characters see
Regex replace all newline characters with comma
make sure you do this before storing it in DB.
public boolean isValidJson(final String json) {
try {
final ObjectMapper objectMapper = new ObjectMapper();
final JsonNode jsonNode = objectMapper.readTree(json);
return jsonNode instanceof ContainerNode;
} catch (JsonProcessingException jpe) {
return false;
}
}

Deserialize only some fields of JSON objects array (Java)

Given this JSON response I get from an website :
{
"Items":
[
{ "Name":"Apple", "Price":12.3, "Quantity":30 },
{ "Name":"Grape", "Price":3.21, "Quantity":60 }
],
"Date":"21/11/2010"
}
How could i deserialize this JSON, splitting it in an array called Fruits, containing only name and quantity ? I don't care about date field or other fields like price.
My class should look like:
class Fruit{
String name;
String quantity;
}
And this is the array:
Fruit myfruits[] = new Fruit [this number depends on JSON response I get]
How could I achive this ?
I've tried to give my best explanation, if it is still not clear, feel free to ask.
P.S: btw, the real JSON response has many more fields
You need to ignore the fields you don't wont.
Each serialization frameworks does it in different ways.
In some you can add annotations to you POJO, or set it with the serializer instance
Using Gson:
Gson ignore json field and deserialize
Using Jackson:
Ignoring new fields on JSON objects using Jackson

Using json Schema to filter json instances in Java

I'm searching for a library which enables me to filter out a json instance in accordance with a json schema. If the json instance contains elements not defined in the schema they should be filtered out. I have found this for JavaScript: https://www.npmjs.org/package/json-schema-filter, but have been unable to find something that does this in Java.
Does anyone have suggestion as to how this can be achieved in Java? Or where to find a library that does the job?
Regards
Morten
An example
File schemaname.json:
{
"type": "object",
"properties": {
"aid": {
"type": "string"
}
}
}
final String json =
{
"aid" : "123954",
"newfield" : "itsValue"
}
What I'm asking is if the filterInstance(instance,schema) method shown below exists.
JsonNode schema = JsonLoader.fromResource("path/schemaname.json");
JsonNode instance = (new ObjectMapper()).readTree(json);
JsonNode fInstance = filterInstance(instance,schema);
fInstance =
{
"aid" : "123954"
}
You can use https://github.com/chathurabuddi/json-schema-filter.
This is the Java version of the above-mentioned json-schema-filter
You can just ignore new fields in JSON, when you are mapping to POJO.
Ignoring new fields on JSON objects using Jackson
In this case your POJO is your Jackson scheme, and use Jackson for serialization in this case :)
This questions was posted long ago and specification may have changed but as of JSON Schema 2020-12 the JSON in the example above is valid and no fields should be removed according to the schema.
The JSON schema of schemaname.json in the example above implies that the JSON String is valid because keyword "additionalProperties" has default value of empty schema {}.
I have not found any JSON Schema filter that filters based on the full schema so I am about to create my own implementation for this but would be happy if anyone knows any JSON Schema filter implementation written in Java (or other JVM-based language).

Categories

Resources