JSON to XML conversion without changing the sequence - java

I am using the below code to convert json to xml of multiple XML files with different JSON structures.
String toXmlRequest = fullRequest.toString();
JSONObject jsonObj = new JSONObject(toXmlRequest);
String XmlRequest = XML.toString(jsonObj);
System.out.println(XmlRequest);
Input
{
"EnrollmentRequest":
{
"data":
{
"commonDataContext":
{
"requestId": "ADA12131",
"clientId": "ABCDEF",
"timestamp":"2013-12-13T11:10:00.715-05:00"
},
"cardNumber" : "123456789012345" ,
"firstName" : "John" ,
"lastName" : "Smith" ,
"email" : "JohnSmith#g.com" ,
"enrollStatus" : "E" ,
"pathEnroll" : "NewAcct",
"cardSavedIndicator" : "Y"
}
}
}
Output
<EnrollmentRequest>
<data>
<firstName>John</firstName>
<lastName>Smith</lastName>
<commonDataContext>
<clientId>ABCDEF</clientId>
<requestId>ADA12131</requestId>
<timestamp>2013-12-13T11:10:00.715-05:00</timestamp>
</commonDataContext>
<pathEnroll>NewAcct</pathEnroll>
<enrollStatus>E</enrollStatus>
<cardSavedIndicator>Y</cardSavedIndicator>
<cardNumber>123456789012345</cardNumber>
<email>JohnSmith#g.com</email>
</data>
</EnrollmentRequest>
The sequence of the output is getting changed. It is not able to keep the actual sequence. Is there any way this can be kept intact.

This is not possible using org.json.JSONObject directly. The reason is that JSONObject uses an internal store of type HashMap. HashMap does not preserve insertion order
It would be possible with a LinkedHashMap, however it does not appear possible to configure JSONObject to use one.
/**
* Construct an empty JSONObject.
*/
public JSONObject() {
this.map = new HashMap<String, Object>();
}
An alternative would be to read using a library that does preserve order, e.g. Jackson....
ObjectMapper mapper = new ObjectMapper();
JsonNode jackson = mapper.readTree(fullRequest);
and then feed that into XML
String xmlRequest = XML.toString(new JSONAdapter(jackson));
with the necessary type adaption to make the Jackson object look like a org.json.JSONObject. Incomplete example below:
private static class JSONAdapter extends JSONObject {
private JsonNode jackson;
public JSONAdapter(JsonNode jackson) {
this.jackson = jackson;
}
#Override
public Iterator<String> keys() {
return jackson.fieldNames();
}
#Override
public Object opt(String key) {
return get(key);
}
#Override
public Object get(String key) throws JSONException {
JsonNode nested = jackson.get(key);
if (nested.isObject()) {
return new JSONAdapter(nested);
} else if (nested.isTextual()) {
return nested.asText();
} else if (nested.isNumber()) {
return nested.asDouble();
} else if (nested.isBoolean()) {
return nested.asBoolean();
}
return null;
}
}
Output
<EnrollmentRequest>
<data>
<commonDataContext>
<requestId>ADA12131</requestId>
<clientId>ABCDEF</clientId>
<timestamp>2013-12-13T11:10:00.715-05:00</timestamp>
</commonDataContext>
<cardNumber>123456789012345</cardNumber>
<firstName>John</firstName>
<lastName>Smith</lastName>
<email>JohnSmith#g.com</email>
<enrollStatus>E</enrollStatus>
<pathEnroll>NewAcct</pathEnroll>
<cardSavedIndicator>Y</cardSavedIndicator>
</data>
</EnrollmentRequest>

For embedded json arrays, you need to apply one more condition to check if it array and return it as json array.
if(nested.isArray()) {
JSONArray arr = new JSONArray();
for(JsonNode value : nested){
arr.put(value.asText());
}
return arr;
}

Related

How to model JSON with key value pairs?

This simple JSON is returned by https://httpbin.org/get which is handy for testing.
{
"args": {},
"headers": {
"Content-Length": "0",
"Host": "httpbin.org",
"User-Agent": "AemSConnector v1.0",
"X-Amzn-Trace-Id": "Root=1-606c333f-338353e14fc31e375617f4ba"
},
"origin": "81.40.159.142",
"url": "https://httpbin.org/get"
}
I'm trying to figure out how to build a Java class to model this.
I have tried:
public class ModelTest {
public String origin;
public String url;
public HashMap<String, String> headers;
public HashMap<String, String> args;
// getters and setters and default constructor here...
}
}
And also just this:
public class ModelTest {
public String origin;
public String url;
// getters and setters and default constructor here...
}
}
But when I try to convert the JSON string to this model, I just get a null point exception in the logs, no helpful info.
The code I am using is this:
// ModelTest model = null;
ModelTest model = new ModelTest();
model = (ModelTest) getObjectFromJson(reply, model);
}
:
public static Object getObjectFromJson(String jsonString, Object obj) {
Gson gson = new Gson();
Object returnValue = null;
try {
returnValue = gson.fromJson(jsonString, obj.getClass());
} catch (Exception e) {
log.error("Exception occured in Something :: getObjectFromJson --> ", e);
}
return returnValue;
}
exception:
2021-04-06 12:09:04.245 ERROR [com.adobe.aem.guides.wknd.core.util.MyConnector] Exception occured in Something :: getObjectFromJson -->
java.lang.NullPointerException: null
at com.adobe.aem.guides.wknd.core.util.SpineConnector.getObjectFromJson(MyConnector.java:77) [aem-guides-wknd.core:0.2.1.SNAPSHOT]
at com.adobe.aem.guides.wknd.core.util.SpineConnector.get(MyConnector.java:50) [aem-guides-wknd.core:0.2.1.SNAPSHOT]
at com.adobe.aem.guides.wknd.core.servlets.SpineServlet.doGet(MyServlet.java:64) [aem-guides-wknd.core:0.2.1.SNAPSHOT]
I found a solution. The Model was fine, it was the getObjectFromJson method which was causing the issues, even with a non-null object (as the commenters pointed out)
I scrapped it, and did the mapping in-line and it worked as expected:
Gson gson = new Gson();
model = gson.fromJson(reply, ModelTest.class);

JSON Response Has Escaped Quotations Using Jackson and JAX-RS Exception Mapper

I have a simple requirement where, if application encounters an exception, my JAX-RS Rest endpoint should return a custom JSON response with 500 HTTP header status.
Data needed to construct the response comes from an object with several properties (see below). The problem is, I am only interested in one or two values from each property (out of several dozens). And I cannot modify any of these models/classes (some have a Jackson annotation for JSON processing, e.g. null properties should be discarded during serialization).
public class MainObject {
private FirstProperty firstProperty;
private SecondProperty secondProperty;
private ThirdProperty thirdProperty;
// other codes
public String toString() {
ObjectMapper mapper = new ObjectMapper();
try { return mapper.writeValueAsString(this); }
catch (Exception e) { return null; }
}
}
public class FirstProperty {
private boolean bol = true;
private double dob = 5.0;
private List<String> subProperty;
// other properties
public String toString() {
ObjectMapper mapper = new ObjectMapper();
try { return mapper.writeValueAsString(this); }
catch (Exception e) { return null; }
}
}
#JsonSerialize(include=JsonSerialize.Inclusion.NON_NULL)
public class SecondProperty {
private String str;
private List<String> subProperty;
// other properties
public String toString() {
ObjectMapper mapper = new ObjectMapper();
try { return mapper.writeValueAsString(this); }
catch (Exception e) { return null; }
}
}
#JsonSerialize(include=JsonSerialize.Inclusion.NON_NULL)
public class ThirdProperty {
private int intProp = true;
private List<String> subProperty;
// other properties
public String toString() {
ObjectMapper mapper = new ObjectMapper();
try { return mapper.writeValueAsString(this); }
catch (Exception e) { return null; }
}
}
The expected JSON that I should be seeing coming back is on the client side (say, a browser -- testing in Edge):
{
"firstProperty" : { "subProperty" : [ "val1" ] },
"secondProperty" : { "str" : "val2", "subproperty" : [ "val3", "val6" ] },
"thirdProperty" : { "subProperty" : [ "val4" ] }
}
Instead, all my field names and their values have their quotations escaped, and extra double quotes around the entire value, e.g.:
{
"firstProperty" : "{ \"subProperty\" : [ \"val1\" ] }",
"secondProperty" : "{ \"str\" : \"val2\", \"subproperty\" : [ \"val3\", \"val6\" ] }",
"thirdProperty" : "{ \"subProperty\" : [ \"val4\" ] }"
}
Please note the extra " before and after the curly brackets. My environment is:
Java 1.8.45
FasterXML Jackson 2.9.8
Spring Boot 2.0.1
RestEasy (JBoss) JAX-RS
JBoss 6.4
I eliminated the majority of "noise" in the code to see at what point this happens. This is the controller:
#Path("/")
public class MainController {
#GET
#Produces(MediaType.APPLICATION_JSON)
#Path("/rest/path")
public MainObject getMainObject throws MyCustomException {
// A service call that throws MyCustomException
}
}
And JAX-RS ExceptionMapper where I send the response back:
#Provider
public class MyCustomExceptionMapper extends ExceptionMapper<MyCustomException> {
#Override
public Response toResponse(MyCustomException ex) {
HashMap<String, Object> responseBody = new HashMap<>();
String strEx = ex.getStrEx(); // Comes from SecondProperty.str stored in MyCustomException, not that it matters
// Instantiate an empty object that contains
MainObject obj = new MainObject();
obj.getFirstProperty().setSubProperty(ex.getStrs());
obj.getSecondProperty().setStr(strEx);
obj.getSecondProperty().setSubProperty(ex.getStrs());
obj.getThirdProperty().setSubProperty(ex.getStrs());
responseBody.put("firstProperty", serializeFirstProperty(obj.getFirstProperty()));
responseBody.put("secondProperty", serializeSecondProperty(obj.getSecondProperty()));
responseBody.put("thirdProperty", serializeThirdProperty(obj.getThirdProperty()));
Response response = Response.status(/* 500 status */).entity(responseBody).build();
return response;
}
}
Since I only need to send back a very small subset of overall properties from each of my types, I created a custom StdSerializer that would only populate a needed property. For brevity, I only do serializeFirstProperty() but they are all more or less identical:
private StdSerializer<FirstProperty> getFPSerializer(FirstProperty firstProperty) {
return new StdSerializer<FirstProperty>(FirstProperty.class) {
#Override
public void serialize(FirstProperty value, JsonGenerator gen, SerializerProvider provider) throws IOException {
gen.writeStartObject();
if (/* there are items in FirstProperty.subProperty */) {
gen.writeArrayFieldStart("subProperty");
for (String str : value.getSubProperty()) {
gen.writeString(str);
}
gen.writeEndArray();
}
gen.writeEndObject();
}
}
private <T> ObjectMapper getCustomOM(StdSerializer<?> serializer) {
ObjectMapper mapper = new ObjectMapper();
SimpleModule sm = new SimpleModule();
sm.addSerializer(serializer);
mapper.registerModule(module);
return mapper;
}
Then use these helper methods like:
private String serializeFirstProperty(FirstProperty firstProperty) {
ObjectMapper mapper = getCustomOM(getFPSerializer(firstProperty));
String ser = null;
try { ser = mapper.writeValueAsString(firstProperty); }
catch (JsonProcessingException e) { return null; }
return ser;
}
I have tried countless of configurations with ObjectMapper, e.g. disable(JsonParser.Feature.ALLOW_BACKLASH_ESCAPING_ANY_CHARACTER) (couldn't find any relevant flag for JsonGenerator which I really want to disable in a similar fashion).
Or explicitly returning Object from serializeFirstProperty(), or replacing all the \" with " in serializeFirstProperty() when ser is returned.
Or set custom StdSerializer's JsonGenerator.setCharacterEscapes(new CharacterEscapes() { //... } or play around with JAX-RS Response at no avail. I always seem to get a "string" value with quotations, e.g.:
"firstProperty" : "{ \"subProperty\" : [ \"val1\" ] }"
If I simply just do
responseBody.put("firstProperty", mapper.writeValueAsString(obj.getFirstProperty()));
somehow this produces the right JSON output, however, it includes a lot of unnecessary properties which I don't want in this exception handling case.
Funny thing is, when I peer into response (or responseBody map), everything looks right (I don't see values having double quotations).
Please also note that not only I can't modify the models, but some of their properties are instantiated during creation with default values, so not-null inclusion doesn't work, and they will appear in the final JSON if I don't use a custom serialization.
Does anyone know what's causing this escaped and extra quotations?
I think I misunderstood the question in the first attempt of answering it.
The problem is that you serialize a property as string (using mapper.writeValueAsString(this) and then add it to the responseBody which you think of being string to json object map but it is a string to Java object map. In your case at runtime it is a string mapping to another string (the serialized json object is represented as Java string) and a Java string is a Java object as well.
What you want to do instead is to construct a Java object responseBody instead of a map. It should act as a DTO having all the specific properties etc and then serializing it in in one action using the mapper. Because if you first serialize a property to a json string than it it is just a string from the Java point of view and the mapper has no chance to interpret it as a json object.

Add Map Values to a JSON object in identical key field names

I have the following Java Map. Map<String, String> containing values such as:
876234876, google
mike#hotmail, hotmail
9879892, google
I need to convert it to the following JSON object structure and Java JSON objects are not my friend.
"addresses" : [
{ "address":"876234876", "domain":"google" },
{ "address":"mike#hotmail", "domain":"hotmail" },
{ "address":"9879892", "domain":"google" }
]
To create the JSON you ask, you need to insert a JSONObject into a JSONArray. So for each Entry of your Map<String, String>, create a JSONObject like {"address": entry.key, "domain": entry.value} and add those to a JSONArray.
Let's use a Stream.map to create that object and insert the result into the array directly:
public static JSONObject createJson(Map<String, String> value) {
JSONObject result = new JSONObject();
JSONArray addresses = new JSONArray();
result.put("addresses", addresses);
value.entrySet().stream() //iterate the map
.map(e -> { //build an object
JSONObject address = new JSONObject();
address.put("address", e.getKey());
address.put("domain", e.getValue());
return address;
})
.forEach(addresses::put); //insert into the array
return result;
}
And test it with :
public static void main(String[] args) {
Map<String, String> values = new HashMap<>();
values.put("876234876", "google");
values.put("mike#hotmail", "hotmail");
values.put("9879892", "google");
System.out.println(createJson(values).toString(4));
}
And the result :
{"addresses": [
{
"address": "9879892",
"domain": "google"
},
{
"address": "876234876",
"domain": "google"
},
{
"address": "mike#hotmail",
"domain": "hotmail"
}
]}
Using the API : JSON In Java
<!-- https://mvnrepository.com/artifact/org.json/json -->
<dependency>
<groupId>org.json</groupId>
<artifactId>json</artifactId>
<version>20180130</version>
</dependency>
Check this solution:
List<String> addresses = new ArrayList<>();
map.forEach((k, v) -> {
Map<String, String> nn = new HashMap<>();
nn.put("address", k);
nn.put("domain", v);
addresses.add(JSONValue.toJSONString(nn));
});
JSONObject result = new JSONObject(Collections.singletonMap("addresses", new JSONArray(addresses)));
Your JAVA objects should look like this :
List of addresses
#XmlRootElement
public class Foo {
private List<Address> addresses;
// Getter, Setter, ...
}
Address
public class Address {
private String address;
private String domain;
// Getters, setters, ...
}

Adding a new element to an array in the json object java

I am writing automation script to validate json responses of REST APIs and i am using faster xml to serialize and convert java object to json format.
I have a user case where I have to get the json response and add a new array element to an existing array and post it back.
The json response after GET looks like this :
{
"name":"test",
"id":"1234",
"nodes":[
{
"nodeId":"node1"
},
{
"nodeId":"node2"
}
]
}
To this json response, I need to add a third entry for nodes array
{ "nodeId": "node3" } and then post this.
Can someone please help me understand how to add a new array element to an existing array?
You can try:
//Your JSON response will be in this format
String response = "{ \"name\":\"test\", \"id\":\"1234\", \"nodes\":[ { \"nodeId\":\"node1\" }, { \"nodeId\":\"node2\" } ] }";
try {
JSONObject jsonResponse = new JSONObject(response);
JSONArray nodesArray = jsonResponse.getJSONArray("nodes");
JSONObject newEntry = new JSONObject();
newEntry.put("nodeId","node3");
nodesArray.put(newEntry);
jsonResponse.put("nodes",nodesArray);
} catch (JSONException e) {
e.printStackTrace();
}
Now you can post your jsonResponse.toString() as required.
I would rather go for cleaner approach, create Object with below structure -
public class Response{
private String name;
private int id;
private List<Node> nodes;
<Getter & Setter>
}
public class Node{
private String nodeId;
}
Serialize the json -
Response response = objectMapper.readValue(responseJson,
Response.class);
Add the new incoming node object to response -
response.getNodes().add(New Node("{new node Value}"));
Deserialize before post -
objectMapper.writeValueAsString(response);

How to convert jsonString to JSONObject in Java

I have String variable called jsonString:
{"phonetype":"N95","cat":"WP"}
Now I want to convert it into JSON Object. I searched more on Google but didn't get any expected answers!
Using org.json library:
try {
JSONObject jsonObject = new JSONObject("{\"phonetype\":\"N95\",\"cat\":\"WP\"}");
}catch (JSONException err){
Log.d("Error", err.toString());
}
To anyone still looking for an answer:
JSONParser parser = new JSONParser();
JSONObject json = (JSONObject) parser.parse(stringToParse);
You can use google-gson. Details:
Object Examples
class BagOfPrimitives {
private int value1 = 1;
private String value2 = "abc";
private transient int value3 = 3;
BagOfPrimitives() {
// no-args constructor
}
}
(Serialization)
BagOfPrimitives obj = new BagOfPrimitives();
Gson gson = new Gson();
String json = gson.toJson(obj);
==> json is {"value1":1,"value2":"abc"}
Note that you can not serialize objects with circular references since that will result in infinite recursion.
(Deserialization)
BagOfPrimitives obj2 = gson.fromJson(json, BagOfPrimitives.class);
==> obj2 is just like obj
Another example for Gson:
Gson is easy to learn and implement, you need to know is the following two methods:
-> toJson() – convert java object to JSON format
-> fromJson() – convert JSON into java object
import com.google.gson.Gson;
public class TestObjectToJson {
private int data1 = 100;
private String data2 = "hello";
public static void main(String[] args) {
TestObjectToJson obj = new TestObjectToJson();
Gson gson = new Gson();
//convert java object to JSON format
String json = gson.toJson(obj);
System.out.println(json);
}
}
Output
{"data1":100,"data2":"hello"}
Resources:
Google Gson Project Home Page
Gson User Guide
Example
There are various Java JSON serializers and deserializers linked from the JSON home page.
As of this writing, there are these 22:
JSON-java.
JSONUtil.
jsonp.
Json-lib.
Stringtree.
SOJO.
json-taglib.
Flexjson.
Argo.
jsonij.
fastjson.
mjson.
jjson.
json-simple.
json-io.
google-gson.
FOSS Nova JSON.
Corn CONVERTER.
Apache johnzon.
Genson.
cookjson.
progbase.
...but of course the list can change.
Java 7 solution
import javax.json.*;
...
String TEXT;
JsonObject body = Json.createReader(new StringReader(TEXT)).readObject()
;
To convert String into JSONObject you just need to pass the String instance into Constructor of JSONObject.
Eg:
JSONObject jsonObj = new JSONObject("your string");
String to JSON using Jackson with com.fasterxml.jackson.databind:
Assuming your json-string represents as this: jsonString = {"phonetype":"N95","cat":"WP"}
import com.fasterxml.jackson.databind.JsonNode;
import com.fasterxml.jackson.databind.ObjectMapper;
/**
* Simple code exmpl
*/
ObjectMapper mapper = new ObjectMapper();
JsonNode node = mapper.readTree(jsonString);
String phoneType = node.get("phonetype").asText();
String cat = node.get("cat").asText();
I like to use google-gson for this, and it's precisely because I don't need to work with JSONObject directly.
In that case I'd have a class that will correspond to the properties of your JSON Object
class Phone {
public String phonetype;
public String cat;
}
...
String jsonString = "{\"phonetype\":\"N95\",\"cat\":\"WP\"}";
Gson gson = new Gson();
Phone fooFromJson = gson.fromJson(jsonString, Phone.class);
...
However, I think your question is more like, How do I endup with an actual JSONObject object from a JSON String.
I was looking at the google-json api and couldn't find anything as straight forward as
org.json's api which is probably what you want to be using if you're so strongly in need of using a barebones JSONObject.
http://www.json.org/javadoc/org/json/JSONObject.html
With org.json.JSONObject (another completely different API) If you want to do something like...
JSONObject jsonObject = new JSONObject("{\"phonetype\":\"N95\",\"cat\":\"WP\"}");
System.out.println(jsonObject.getString("phonetype"));
I think the beauty of google-gson is that you don't need to deal with JSONObject. You just grab json, pass the class to want to deserialize into, and your class attributes will be matched to the JSON, but then again, everyone has their own requirements, maybe you can't afford the luxury to have pre-mapped classes on the deserializing side because things might be too dynamic on the JSON Generating side. In that case just use json.org.
Those who didn't find solution from posted answers because of deprecation issues, you can use JsonParser from com.google.gson.
Example:
JsonObject jsonObject = JsonParser.parseString(jsonString).getAsJsonObject();
System.out.println(jsonObject.get("phonetype"));
System.out.println(jsonObject.get("cat"));
you must import org.json
JSONObject jsonObj = null;
try {
jsonObj = new JSONObject("{\"phonetype\":\"N95\",\"cat\":\"WP\"}");
} catch (JSONException e) {
e.printStackTrace();
}
Codehaus Jackson - I have been this awesome API since 2012 for my RESTful webservice and JUnit tests. With their API, you can:
(1) Convert JSON String to Java bean
public static String beanToJSONString(Object myJavaBean) throws Exception {
ObjectMapper jacksonObjMapper = new ObjectMapper();
return jacksonObjMapper.writeValueAsString(myJavaBean);
}
(2) Convert JSON String to JSON object (JsonNode)
public static JsonNode stringToJSONObject(String jsonString) throws Exception {
ObjectMapper jacksonObjMapper = new ObjectMapper();
return jacksonObjMapper.readTree(jsonString);
}
//Example:
String jsonString = "{\"phonetype\":\"N95\",\"cat\":\"WP\"}";
JsonNode jsonNode = stringToJSONObject(jsonString);
Assert.assertEquals("Phonetype value not legit!", "N95", jsonNode.get("phonetype").getTextValue());
Assert.assertEquals("Cat value is tragic!", "WP", jsonNode.get("cat").getTextValue());
(3) Convert Java bean to JSON String
public static Object JSONStringToBean(Class myBeanClass, String JSONString) throws Exception {
ObjectMapper jacksonObjMapper = new ObjectMapper();
return jacksonObjMapper.readValue(JSONString, beanClass);
}
REFS:
Codehaus Jackson
JsonNode API - How to use, navigate, parse and evaluate values from a JsonNode object
Tutorial - Simple tutorial how to use Jackson to convert JSON string to JsonNode
Converting String to Json Object by using org.json.simple.JSONObject
private static JSONObject createJSONObject(String jsonString){
JSONObject jsonObject=new JSONObject();
JSONParser jsonParser=new JSONParser();
if ((jsonString != null) && !(jsonString.isEmpty())) {
try {
jsonObject=(JSONObject) jsonParser.parse(jsonString);
} catch (org.json.simple.parser.ParseException e) {
e.printStackTrace();
}
}
return jsonObject;
}
To convert a string to json and the sting is like json. {"phonetype":"N95","cat":"WP"}
String Data=response.getEntity().getText().toString(); // reading the string value
JSONObject json = (JSONObject) new JSONParser().parse(Data);
String x=(String) json.get("phonetype");
System.out.println("Check Data"+x);
String y=(String) json.get("cat");
System.out.println("Check Data"+y);
Use JsonNode of fasterxml for the Generic Json Parsing. It internally creates a Map of key value for all the inputs.
Example:
private void test(#RequestBody JsonNode node)
input String :
{"a":"b","c":"d"}
If you are using http://json-lib.sourceforge.net
(net.sf.json.JSONObject)
it is pretty easy:
String myJsonString;
JSONObject json = JSONObject.fromObject(myJsonString);
or
JSONObject json = JSONSerializer.toJSON(myJsonString);
get the values then with
json.getString(param) or/and json.getInt(param) and so on.
No need to use any external library.
You can use this class instead :) (handles even lists , nested lists and json)
public class Utility {
public static Map<String, Object> jsonToMap(Object json) throws JSONException {
if(json instanceof JSONObject)
return _jsonToMap_((JSONObject)json) ;
else if (json instanceof String)
{
JSONObject jsonObject = new JSONObject((String)json) ;
return _jsonToMap_(jsonObject) ;
}
return null ;
}
private static Map<String, Object> _jsonToMap_(JSONObject json) throws JSONException {
Map<String, Object> retMap = new HashMap<String, Object>();
if(json != JSONObject.NULL) {
retMap = toMap(json);
}
return retMap;
}
private static Map<String, Object> toMap(JSONObject object) throws JSONException {
Map<String, Object> map = new HashMap<String, Object>();
Iterator<String> keysItr = object.keys();
while(keysItr.hasNext()) {
String key = keysItr.next();
Object value = object.get(key);
if(value instanceof JSONArray) {
value = toList((JSONArray) value);
}
else if(value instanceof JSONObject) {
value = toMap((JSONObject) value);
}
map.put(key, value);
}
return map;
}
public static List<Object> toList(JSONArray array) throws JSONException {
List<Object> list = new ArrayList<Object>();
for(int i = 0; i < array.length(); i++) {
Object value = array.get(i);
if(value instanceof JSONArray) {
value = toList((JSONArray) value);
}
else if(value instanceof JSONObject) {
value = toMap((JSONObject) value);
}
list.add(value);
}
return list;
}
}
To convert your JSON string to hashmap use this :
HashMap<String, Object> hashMap = new HashMap<>(Utility.jsonToMap(
For setting json single object to list
ie
"locations":{
}
in to List<Location>
use
ObjectMapper mapper = new ObjectMapper();
mapper.configure(DeserializationConfig.Feature.ACCEPT_SINGLE_VALUE_AS_ARRAY, true);
jackson.mapper-asl-1.9.7.jar
NOTE that GSON with deserializing an interface will result in exception like below.
"java.lang.RuntimeException: Unable to invoke no-args constructor for interface XXX. Register an InstanceCreator with Gson for this type may fix this problem."
While deserialize; GSON don't know which object has to be intantiated for that interface.
This is resolved somehow here.
However FlexJSON has this solution inherently. while serialize time it is adding class name as part of json like below.
{
"HTTPStatus": "OK",
"class": "com.XXX.YYY.HTTPViewResponse",
"code": null,
"outputContext": {
"class": "com.XXX.YYY.ZZZ.OutputSuccessContext",
"eligible": true
}
}
So JSON will be cumber some; but you don't need write InstanceCreator which is required in GSON.
Using org.json
If you have a String containing JSON format text, then you can get JSON Object by following steps:
String jsonString = "{\"phonetype\":\"N95\",\"cat\":\"WP\"}";
JSONObject jsonObj = null;
try {
jsonObj = new JSONObject(jsonString);
} catch (JSONException e) {
e.printStackTrace();
}
Now to access the phonetype
Sysout.out.println(jsonObject.getString("phonetype"));
Better Go with more simpler way by using org.json lib. Just do a very simple approach as below:
JSONObject obj = new JSONObject();
obj.put("phonetype", "N95");
obj.put("cat", "WP");
Now obj is your converted JSONObject form of your respective String. This is in case if you have name-value pairs.
For a string you can directly pass to the constructor of JSONObject. If it'll be a valid json String, then okay otherwise it'll throw an exception.

Categories

Resources