dynimacally generte a json object - java

String json = "{\"loginForm\": [{\"formType\": \"questionAndAnswer\",\"id\": 164422,\"row\": [{\"label\": \"What is the name of your state?\",\"field\": [{\"id\":\"SQandA--QUESTION_1-1\",\"value\": \""+answer1+"\"}]},{\"label\": \"What is the name of your first school\",\"field\": [{\"id\":\"SQandA--QUESTION_2-2\",\"value\": \""+answer2+"\"}]}]}],"+dataset+"}";
this json contains questions and answer in it and its hard coded in my code what should i do to dynamically generate it as i want to remove the hard code and call it dynamically.

You can create a class file with your json fields and then convert the class object to json using Jackson apis.
private String getJsonFromJava (Object obj) {
ObjectMapper mapper = new ObjectMapper();
String jsonInString = "";
try {
jsonInString = mapper.writeValueAsString(obj);
} catch (JsonProcessingException e) {
System.out.println("Unable to parse object to prepare JSON string", e);
}
return jsonInString;
}

You need to write logic to create json using the inputs. If you are creating the json in JS then look at sample code below. Or you can do the same login in server side - java etc?
function createJSON() {
jsonObj = [];
$("input[questions]").each(function() {
var q= $(this).attr("Question");
var ans= $(this).val();
item = {}
item ["question"] = id;
item ["answer"] = ans;
jsonObj.push(item);
});
console.log(jsonObj);
}

Related

How to return a list of JSONObject as REST API response

I am creating a REST API using Spring Boot and using org.json for parsing data retrieved from another different service. From this service I am getting JSON data like in following format
{
"my_data":[
{
"user_data":{
"first_name":"FirstTest1",
"last_name":"LastTest1",
"age":"25"
}
},
{
"user_data":{
"first_name":"FirstTest2",
"last_name":"LastTest2",
"age":"35"
}
},{
"user_data":{
"first_name":"FirstTest3",
"last_name":"LastTest3",
"age":"45"
}
}
],
"count":10,
"is_safe":false
}
and I have to transform received data to the following JSON
[
{
"user_data":{
"first_name":"FirstTest1",
"last_name":"LastTest1",
"age":"25"
}
},
{
"user_data":{
"first_name":"FirstTest2",
"last_name":"LastTest2",
"age":"35"
}
},{
"user_data":{
"first_name":"FirstTest3",
"last_name":"LastTest3",
"age":"45"
}
}
]
I know I can use a POJO to map the data and send it (already doing this) but here the issue is that the data received from another service is not fixed e.g. it may or may mot have "first_name" or may have a different field like "country". So, in this situation I can not make POJO beforehand.
After going through some online resources I made some changes and my POST Controller method looks like this.
#PostMapping(path = "/searchusersdata")
public RETURN_SOMETHING searchUsersData(#RequestBody Map<String, String> searchData) {
List<JSONObject> finalDataCollection = new ArrayList<JSONObject>();
//Making some REST API CALL TO GET 'response' using 'searchData'
String someResponse = response.getBody();
JSONObject object = null;
try {
object = new JSONObject(someResponse);
} catch (JSONException e) {
e.printStackTrace();
}
String my_data= object.get("my_data").toString();
JSONArray intermediateJA = null;
intermediateJA = new JSONArray (my_data);
for(int i = 0; i < intermediateJA.length(); i++) {
JSONObject item = intermediateJA.getJSONObject(i);
if (item.keySet().contains("user_data"))
{
Object value = item.get("user_data");
finalDataCollection.add(new JSONObject(value));
}
}
//WHAT TO RESTURN HERE
}
Now, I don't know what to return hare. For a single JSONObject we can use return new ResponseEntity<>(return_data.toMap(), HttpStatus.OK); but for a collection I don't know. I am open to suggestion if I have to do it in entirely different way. I also know that with gson or jackson it might be easier but I have to use org.json.
instead of List , use JsonArray and use ResponseEntity to return it.
Example
JSONArray jsonArray = new JSONArray();
JSONObject jsonObject = new JSONObject();
jsonArray.put(jsonObject);
return new ResponseEntity( jsonArray.toString(), HttpStatus.OK);

Convert serialized JSON string to JSON object in java

I have Json String Object as below.
"{\"SuccessData\":\"Data fetched successfully\",\"ErrorData\":\"\",\"AppData\":\"[{\\\"uniqe_id\\\":{\\\"appId\\\":4,\\\"agentId\\\":1,\\\"isActive\\\":1\\\"},\\\"pid\\\":2223,\\\"appName\\\":ACMP\\\"},{\\\"uniqe_id\\\":{\\\"appId\\\":5,\\\"agentId\\\":1,\\\"isActive\\\":1\\\"},\\\"pid\\\":2225,\\\"appName\\\":ICMP\\\"}]\"}"
I want to convert this string to JSON object using java.
I have already tried,
JSONObject jsonObj = new JSONObject(response);
I'm getting an error saying,
org.json.JSONException: A JSONObject text must begin with '{'
"{\"SuccessData\": \"Data fetched successfully\",
\"ErrorData\": \"\",
\"AppData\": \"[{\\\"uniqe_id\\\":{\\\"appId\\\":4,\\\"agentId\\\":1,\\\"isActive\\\":1\\\"},\\\"pid\\\":2223,\\\"appName\\\":ACMP\\\"},{\\\"uniqe_id\\\":{\\\"appId\\\":5,\\\"agentId\\\":1,\\\"isActive\\\":1\\\"},\\\"pid\\\":2225,\\\"appName\\\":ICMP\\\"}]\"
}"
The real problem here is that this input is not valid JSON.
Let's assume that these are the exact characters that you got in your response; i.e. the first character is a double-quote. But a valid JSON object starts with a { character. Not even whitespace is allowed according to strict reading of the syntax graph at https://json.org.
But what if that is actually a Java String literal representing the JSON?
In that case, the JSON is valid1. And what is more, your code for the JSON is correct. when I compile and run this, it works ... without throwing an exception.
import org.json.JSONObject;
public class Test {
public static void main(String[] args) {
String response = "{\"SuccessData\":\"Data fetched successfully\",\"ErrorData\":\"\",\"AppData\":\"[{\\\"uniqe_id\\\":{\\\"appId\\\":4,\\\"agentId\\\":1,\\\"isActive\\\":1\\\"},\\\"pid\\\":2223,\\\"appName\\\":ACMP\\\"},{\\\"uniqe_id\\\":{\\\"appId\\\":5,\\\"agentId\\\":1,\\\"isActive\\\":1\\\"},\\\"pid\\\":2225,\\\"appName\\\":ICMP\\\"}]\"}";
JSONObject jsonObj = new JSONObject(response);
}
}
Ergo, if you are getting a JSONException then the input is not a Java String literal.
1 - I wouldn't say it was correct. The AppData attribute has a value that is a string not a JSON object. But that string is a JSON serialization. This is technically valid, but it is a poor design choice.
I tried with the following solution and it is working,
import com.fasterxml.jackson.databind.ObjectMapper;
private JSONObject deserializeResponse(String response) {
logger.info("Parsing Serialized response object to JSON object");
JSONObject responseJson = new JSONObject();
ObjectMapper mapper = new ObjectMapper();
try {
responseJson = mapper.readValue(response.toString(),
JSONObject.class);
} catch (JsonGenerationException e) {
e.printStackTrace();
} catch (JsonMappingException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
return responseJson;
}

Java map object, which contains JSON string fields to string

I have faced problem, while mapping my object to JSON.
I have an object, which I need to convert to propper JSON, but some of my object's String fields are already in JSON format:
Sdr sdr = new Sdr();
sdr.setLocation_area(("location_area"));
sdr.setEvent_info(("{\"chargeableDur\":0}"));
sdr.setAgent_info("{\"scp\":\"NAVI\",\"stack\":\"CAP2\"}");
sdr.setService_info(("{\"bcap\":\"8090A3\",\"balID\":55969859}"));
sdr.setStarttime(("starttime"));
For JSON mapping I am using ObjectMapper:
public String toJsonString() {
ObjectMapper mapper = new ObjectMapper();
try {
return mapper.writeValueAsString(this);
} catch (JsonProcessingException e) {
logger.error(e.getMessage());
}
return toString();
}
However, ObjectMapper fails to map Strings, that already contains JSON correctly, and after mapping I get this type of JSON:
{
"event_info":""{\"chargeableDur\":0}",
"location_area":"location_area",
"agent_info":"{\"scp\":\"NAVI\",\"stack\":\"CAP2\"}",
"service_info":""{\"bcap\":\"8090A3\",\"balID\":55969859}",
"starttime":"starttime"
}
I want ObjectMapper to map my object like that:
{
"event_info":{
"chargeableDur":0
},
"location_area":"location_area",
"agent_info":{
"scp":"NAVI",
"stack":"CAP2"
},
"service_info":{
"bcap":"8090A3",
"balID":55969859
},
"starttime":"starttime"
}
Seems that your json result is stringified. Try to put the string result in separate JSONObject as
return new JSONObject(mapper.writeValueAsString(this)).toString();

Any method of passing the Json data in URL format using JSONObject?

I create a java URL class which contain my Json data and have some function to obtain back my json data for doing some data comparison, I found out it's might not support by JSONObject for passing the data into the JSONObject. Do I need to use JSONArray in my case because my JSON data have array structure as well?
try
{
JSONObject obj = new JSONObject ();
obj.readJsonFromUrl(theUrl);
System.out.println(obj.toString());
}
catch(MalformedURLException e)
{
System.out.print("your problem here ...1");
}
}
else
{
System.out.print("Can't Connect");
}
I am sure that this is the place give me the error message because it return me this error in my compiler
Exception in thread "main" java.lang.Error: Unresolved compilation problem:
The method readJsonFromUrl(URL) is undefined for the type JSONObject
there are also some warning message for that the JSONObject readJsonFromUrl method
private static JSONObject readJsonFromUrl(URL theUrl) throws IOException, JSONException {
Anyone can provide me the explaination of how the JSON data work in java? I saw quite number of Java class for JSON which make me confuse for it such as JSONObject, JSONArray , JSONValue. I search some information online but I also not very clear about it since I am very new to JSON data processing This is my sample json data and the data I need is scan_result only
{
"data_id":"a71a3c2588c6472bb4daea41a0b58835",
"file_info":{
"display_name":"",
"file_size":242,
"file_type":"Not available",
"file_type_description":"Not available",
"md5":"aa69ba384f22d0dc0551ace2fbb9ad55",
"sha1":"09ceb54e65df3d3086b222e8643acffe451a6e8a",
"sha256":"dcb46d6ae2a187f789c12f19c44bbe4b9a43bd200a3b306d5e9c1fcf811dc430",
"upload_timestamp":"2016-11-18T09:09:08.390Z"
},
"process_info":{
"blocked_reason":"",
"file_type_skipped_scan":false,
"post_processing":{
"actions_failed":"",
"actions_ran":"",
"converted_destination":"",
"converted_to":"",
"copy_move_destination":""
},
"profile":"File scan",
"progress_percentage":100,
"result":"Allowed",
"user_agent":""
},
"scan_results":{
"data_id":"a71a3c2588c6472bb4daea41a0b58835",
"progress_percentage":100,
"scan_all_result_a":"No Threat Detected",
"scan_all_result_i":0,
"scan_details":{
"Ahnlab":{
"def_time":"2016-11-08T15:00:00.000Z",
"location":"local",
"scan_result_i":0,
"scan_time":1,
"threat_found":""
},
"Avira":{
"def_time":"2016-11-08T00:00:00.000Z",
"location":"local",
"scan_result_i":0,
"scan_time":133,
"threat_found":""
},
"ClamAV":{
"def_time":"2016-11-08T10:28:00.000Z",
"location":"local",
"scan_result_i":0,
"scan_time":94,
"threat_found":""
},
"ESET":{
"def_time":"2016-11-08T00:00:00.000Z",
"location":"local",
"scan_result_i":0,
"scan_time":38,
"threat_found":""
}
},
"start_time":"2016-11-18T09:09:08.405Z",
"total_avs":4,
"total_time":250
},
"vulnerability_info":{
}
}
As mentioned here, there are many ways to solve this. Either you have to implement the read, parse operations yourself (#Roland Illig 's answer)
//you have to implement the readJSON method
InputStream is = new URL(url).openStream();
try {
BufferedReader rd = new BufferedReader(new InputStreamReader(is, Charset.forName("UTF-8")));
String jsonText = readAll(rd);
JSONObject json = new JSONObject(jsonText);
return json;
} finally {
is.close();
}
Or you could use a library. The most well-known and widely used libraries are jackson and gson.
The big picture is that you try to "map" your json Object to a class.
You have your json file:
{
"id":1,
"name":"eirini",
"hobbies":["music","philosophy","football"]
}
and a class that represents this file and will store the values (depending on the library that you use there might be different requirements, for example getters, setters etc..)
public class Person {
public int id;
public String name;
public List<String> hobbies = new ArrayList<String>();
public String toString() {
return name +" has the id: " + id + " the following hobbies" + hobbies.get(0) + " " + hobbies.get(2);
}
}
Finally in your main method:
public static void main(String[] args) throws IOException, ParseException {
ObjectMapper mapper = new ObjectMapper();
InputStream input = this.getClass().getResourceAsStream(FILE); //read your file. There are many ways to achieve this.
ObjectMapper mapper = new ObjectMapper(); // just need one
Person eirini = mapper.readValue(input, Person.class);
System.out.println(eirini.toString());
You cannot pass json in url, you can pass it in body. Writing Json to stream body and post it using regular java method.
Here is oracle community url of explanation of your problem.
Required Jar can be downloaded from here.
Test Code Follows:
URL url = new URL("https://graph.facebook.com/search?q=java&type=post");
try (InputStream is = url.openStream();
JsonReader rdr = Json.createReader(is)) {
JsonObject obj = rdr.readObject();
JsonArray results = obj.getJsonArray("data");
for (JsonObject result : results.getValuesAs(JsonObject.class)){
System.out.print(result.getJsonObject("from").getString("name"));
System.out.print(": ");
System.out.println(result.getString("message", ""));
System.out.println("-----------");
}
}

Parsing the nested JSON Array using Jackson library in java

I would like to know how to parse the following JSON using jackson library in java to construct the URI like http://api.statdns.com/google.com/cname
{
"status": {
"status": 200,
"msg": "SUCCESS"
},
"apicalls": [
{
"API": {
"method": "get",
"success": "200",
"baseURL": "http://api.statdns.com/",
"param1": "google.com/",
"param2": "cname",
"continue_on_fail": "1",
"add_header2": "'Accept', 'application/json'",
"add_header1": "'Content-Type', 'application/json'",
"client_id": "101"
},
"id": 1385
}
]
}
I have written bad code to parse the above json array. Following is the code i used,
public void parseJSON(String json) {
try{
JsonFactory factory = new JsonFactory();
JsonParser parser;
parser = factory.createJsonParser(json);
parser.setCodec(new ObjectMapper()); // to avoid IllegalStateException
JsonToken current;
current = parser.nextToken();
if (current != JsonToken.START_OBJECT) {
System.out.println("Error: root should be object: quiting.");
return;
}
while (parser.nextToken() != JsonToken.END_OBJECT) {
String fieldName = parser.getCurrentName();
// Move from field name to field value
current = parser.nextToken();
if (fieldName.equals("APIcalls")) {
JsonNode node = parser.readValueAsTree();
JsonNode currentJson = node.findValue("API");
System.out.println("Current JSON :: " + currentJson);
JsonNode url = currentJson.get("baseURL");
JsonNode param1 = currentJson.get("param1");
JsonNode param2 = currentJson.get("param2");
String baseURL = url.asText();
String params1 = param1.asText();
String params2 = param2.asText();
String uri = baseURL + params1 + params2;
System.out.println("URL :: " + uri);
initiateRESTCall(uri);
}
}
} catch (JsonParseException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
}
Could anyone help me to know parsing the JSON using jackson? Help is highly appreciated.
If you are using jackson library, then you should go something like this:
I am using response from http://api.statdns.com/google.com/cname
public void parseJSON(String json) {
JSONObject parse = new JSONObject(data);
if(parse.get("question") instanceof JSONObject){
JSONObject questionJson = (JSONObject) parse.get("question");
System.out.println("Name"+questionJson.getString("name"));
System.out.println("Type"+questionJson.getString("type"));
System.out.println("Class"+questionJson.getString("class"));
}
else if(parse.get("question") instanceof JSONArray){
JSONArray questionJson = (JSONArray) parse.get("question");
String[] nameAttrib=new String[questionJson.length()];
String[] typeAttrib=new String[questionJson.length()];
String[] classAttrib=new String[questionJson.length()];
for(int i=0;i<questionJson.length();i++){
JSONObject questionJsonData=(JSONObject)questionJson.get(i);
nameAttrib[i]=questionJsonData.getString("name");
typeAttrib[i]=questionJsonData.getString("type");
classAttrib[i]=questionJsonData.getString("class");
System.out.println("Name: "+nameAttrib[i]);
System.out.println("Type: "+typeAttrib[i]);
System.out.println("Class: "+classAttrib[i]);
}
}
else if (parse.get("question").equals(null)){
System.out.println("question"+null);
}
}
Here I am doing for "question" only, similarly you can do other as well say "answer", "authority" in case url you have mentioned http://api.statdns.com/google.com/cname.
Hopefully it helps you with your problem..!!!!
If you are confident in the JSON not changing, a quick and dirty way to simplify your code is to use JSON Pointers.
// prefer injecting your project's ObjectMapper
private static final ObjectMapper om = new ObjectMapper();
public void parseJSON(String json) throws IOException {
JsonNode jsonNode = om.readTree(json);
String uri = new StringBuilder(jsonNode.findValue("baseURL").asText())
.append(jsonNode.findValue("param1").asText())
.append(jsonNode.findValue("param2").asText())
.toString();
initiateRESTCall(uri);
}
This becomes vulnerable if multiple apicalls entries are returned.
I don't know JACKSON library but I think it is similar to GSON. You just have to make some POJO and the library will take care of filling the fields for you.
For instance to convert your string to MyJSONClass use the following classes :
class Status {
int status;
String msg;
}
class APIClass {
String method;
String success;
String baseURL;
String param1;
String param2;
String continue_on_fail;
String add_header2;
String add_header1;
String client_id;
}
class APICall {
APIClass API;
int id;
}
class MyJSONClass {
Status status;
List<APICall> apicalls;
}
This set of classes could be transformed to JSON with JACKSON library (thanks to this stackoverflow answer) like that:
ObjectWriter ow = new ObjectMapper().writer().withDefaultPrettyPrinter();
String json = ow.writeValueAsString(object);

Categories