11

I have java Spring Boot application. In console json have data in(but in wrong order?) and when i'm converting it to String i can get it, but JSONObject cannot be returned, POSTman showing {"empty":false}

My controller package com.example.controller;

import java.util.List;

import javax.servlet.http.HttpServletRequest;

import org.json.JSONException;
import org.json.JSONObject;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RestController;

import com.example.dao.SeriaDao;
import com.example.model.Seria;


@RestController
public class WebController {

    @Autowired
    SeriaDao sed;


    @GetMapping("/tabelka")
    public List<Seria> showTable()
    {
        return sed.findAll();
    }

    @GetMapping("/pgTabelka")
    public JSONObject pgTable(HttpServletRequest request)
    {
        int draw = 0;
        int start = 0;
        int length = 10;

        JSONObject json = new JSONObject();
        if(request.getParameter("draw")!=null)
            draw = Integer.parseInt(request.getParameter("draw"));
        if(request.getParameter("start")!=null)
            start = Integer.parseInt(request.getParameter("start"));
        if(request.getParameter("length")!=null)
            length = Integer.parseInt(request.getParameter("length"));
        int totalRecords = sed.recordsTotal();

        List<Seria> serie = sed.findPart(start, length);

        try {
            json.put("draw", ++draw);
            json.put("recordsTotal", totalRecords);
            json.put("recordsFiltered", totalRecords);
            json.put("data", serie);
        } catch (JSONException e) {
            e.printStackTrace();
        }
        System.out.println(json);

        return json;
    }
}

What i have to add and why i can't get json like i'm trying to get?

PS. json returned in console:

{
  "recordsFiltered": 488,
  "data": [
    {
      "feed": "Macroeconomic_And_Major_Markets",
      "unit": "$ per Week",
      "file": "SMU48185800500000011.csv",
      "cassid": "1d2e556b-031e-4c6f-aec4-981c4e907324",
      "name": "Average Weekly Earnings of All Employees: Total Private in Corpus Christi, TX (MSA)",
      "createdate": "2016-10-15T23:38:49",
      "changedate": "2017-01-09T00:50:01",
      "id": 41,
      "datefrom": "2006-12-31",
      "categoryid": 3,
      "frequency": 5
    },
    {
      "feed": "Macroeconomic_And_Major_Markets",
      "unit": "Index 2015=100",
      "file": "CP0910CYM086NEST.csv",
      "cassid": "6df5b8d5-ec39-4860-930f-a8b355cce37a",
      "name": "Harmonized Index of Consumer Prices: Audio-Visual, Photographic, and Information Processing Equipment for Cyprus",
      "createdate": "2016-10-15T23:38:49",
      "changedate": "2017-02-16T11:35:04",
      "id": 42,
      "datefrom": "1995-12-31",
      "categoryid": 3,
      "frequency": 5
    },
    {
      "feed": "Macroeconomic_And_Major_Markets",
      "unit": "$ per Week",
      "file": "SMU48185800500000011A.csv",
      "cassid": "c3bad2a6-7ad5-4091-846b-f84e9b9f7b50",
      "name": "Average Weekly Earnings of All Employees: Total Private in Corpus Christi, TX (MSA)",
      "createdate": "2016-10-15T23:38:49",
      "changedate": "2017-02-16T11:32:01",
      "id": 43,
      "datefrom": "2006-12-31",
      "categoryid": 3,
      "frequency": 8
    },
    {
      "feed": "Macroeconomic_And_Major_Markets",
      "unit": "Index 2015=100",
      "file": "CP0910CZM086NEST.csv",
      "cassid": "84483d95-d914-45ab-a87a-8c063bfc6d0f",
      "name": "Harmonized Index of Consumer Prices: Audio-Visual, Photographic, and Information Processing Equipment for Czech Republic",
      "createdate": "2016-10-15T23:38:49",
      "changedate": "2017-02-16T11:35:04",
      "id": 44,
      "datefrom": "1999-11-30",
      "categoryid": 3,
      "frequency": 5
    },
    {
      "feed": "Macroeconomic_And_Major_Markets",
      "unit": "$ per Week",
      "file": "SMU41187000500000011SA.csv",
      "cassid": "285056e3-94ce-4266-98b4-ddf32602c0c2",
      "name": "Average Weekly Earnings of All Employees: Total Private in Corvallis, OR (MSA)",
      "createdate": "2016-10-15T23:38:49",
      "changedate": "2017-01-09T00:50:01",
      "id": 45,
      "datefrom": "2006-12-31",
      "categoryid": 3,
      "frequency": 5
    },
    {
      "feed": "Macroeconomic_And_Major_Markets",
      "unit": "Index 2015=100",
      "file": "CP0910DKM086NEST.csv",
      "cassid": "9798eadf-1503-48a5-91e3-cad5852db745",
      "name": "Harmonized Index of Consumer Prices: Audio-Visual, Photographic, and Information Processing Equipment for Denmark",
      "createdate": "2016-10-15T23:38:49",
      "changedate": "2017-02-16T11:35:04",
      "id": 46,
      "datefrom": "1995-12-31",
      "categoryid": 3,
      "frequency": 5
    },
    {
      "feed": "Macroeconomic_And_Major_Markets",
      "unit": "$ per Week",
      "file": "SMU41187000500000011.csv",
      "cassid": "d4b22376-2f84-404f-a175-c04ad8ced5a5",
      "name": "Average Weekly Earnings of All Employees: Total Private in Corvallis, OR (MSA)",
      "createdate": "2016-10-15T23:38:49",
      "changedate": "2017-01-09T00:50:01",
      "id": 47,
      "datefrom": "2006-12-31",
      "categoryid": 3,
      "frequency": 5
    },
    {
      "feed": "Macroeconomic_And_Major_Markets",
      "unit": "Index 2015=100",
      "file": "CP0910EEM086NEST.csv",
      "cassid": "72880ba0-722e-46bb-98f4-7d388d217c26",
      "name": "Harmonized Index of Consumer Prices: Audio-Visual, Photographic, and Information Processing Equipment for Estonia",
      "createdate": "2016-10-15T23:38:49",
      "changedate": "2017-02-16T11:35:04",
      "id": 48,
      "datefrom": "1995-12-31",
      "categoryid": 3,
      "frequency": 5
    },
    {
      "feed": "Macroeconomic_And_Major_Markets",
      "unit": "$ per Week",
      "file": "SMU41187000500000011A.csv",
      "cassid": "03fdf50e-9cd9-483b-aecf-1a0a9e93fa4d",
      "name": "Average Weekly Earnings of All Employees: Total Private in Corvallis, OR (MSA)",
      "createdate": "2016-10-15T23:38:49",
      "changedate": "2017-02-16T11:32:01",
      "id": 49,
      "datefrom": "2006-12-31",
      "categoryid": 3,
      "frequency": 8
    },
    {
      "feed": "Macroeconomic_And_Major_Markets",
      "unit": "Index 2005=100",
      "file": "CP0910EZ17M086NEST.csv",
      "cassid": "2943c0f2-ad55-4ec4-98d0-70db25deaefc",
      "name": "Harmonized Index of Consumer Prices: Audio-Visual, Photographic, and Information Processing Equipment for Euro area (17 countries) (DISCONTINUED)",
      "createdate": "2016-10-15T23:38:49",
      "changedate": "2017-02-16T11:35:04",
      "id": 50,
      "datefrom": "1995-12-31",
      "categoryid": 3,
      "frequency": 5
    }
  ],
  "draw": 1,
  "recordsTotal": 488
}
5
  • I would suggest to use Jackson for JSON conversion. You wouldn't need to ever write such code or worry about JSON fields ordering. Spring Boot includes Jackson by default. Commented Aug 23, 2018 at 13:30
  • You should return json.toString() instead the JSONObject Commented Aug 23, 2018 at 13:50
  • @SimonMartinelli i tryied it, but i need to have JSON in return, because im using DataTables plugin, and data should be send to it in JSON type... Commented Aug 23, 2018 at 13:55
  • but if you return a string do you see the correct JSON in postman? Commented Aug 23, 2018 at 13:59
  • @SimonMartinelli then i see TEXT Commented Aug 23, 2018 at 17:10

5 Answers 5

17

Spring boot uses jackson as default serializer and you're trying to return JSONObject itself. Jackson does not know how to serialize it.

If you want to return dynamic json you can use Map as below :

@GetMapping("/pgTabelka")
public Map<String, Object> pgTable(HttpServletRequest request)
{
    Map<String, Object> json = new HashMap();

    int draw = 0;
    int start = 0;
    int length = 10;

    if(request.getParameter("draw")!=null)
        draw = Integer.parseInt(request.getParameter("draw"));
    if(request.getParameter("start")!=null)
        start = Integer.parseInt(request.getParameter("start"));
    if(request.getParameter("length")!=null)
        length = Integer.parseInt(request.getParameter("length"));
    int totalRecords = sed.recordsTotal();

    List<Seria> serie = sed.findPart(start, length);

    json.put("draw", ++draw);
    json.put("recordsTotal", totalRecords);
    json.put("recordsFiltered", totalRecords);
    json.put("data", serie);

    return json;
}

Or you can create a class represents your json structure and return your custom data class as your response, spring will handle the rest for you.

@GetMapping("/pgTabelka")
public YourJsonDataClass pgTable(HttpServletRequest request)
{
    ...

    YourJsonDataClass json = new YourJsonDataClass();
    json.setDraw(++draw);
    json.setRecordsTotal(totalRecords);
    json.setRecordsFiltered(totalRecords);
    json.setData(serie);

    return json;
}
Sign up to request clarification or add additional context in comments.

Comments

3

Use HashMap instead of using JSONObject

List<HashMap<String, String>> myList = new ArrayList<HashMap<String, String>>();

HashMap<String, String> map = new HashMap<>();

map.put(key, value);

myList.add(map);

If you have a ResultSet, you can loop this code thru the rs. It is worth noting that if your HashMap has duplicate keys, you will have to use a Multimap since HashMap doesn't allow duplicate Keys

Multimap<String, String> map = ArrayListMultimap.create();
map.put(key1, "value1");
map.put(key1, "value2");
map.put(key2, "value3");

Comments

2

Using generic type ResponseEntity<?> combined with json.toString() does the trick.

    @ResponseBody
    public ResponseEntity<?> create(@RequestBody User user) {
        return ResponseEntity.status(HttpStatus.OK).body(json.toString());
    }

Comments

0

Other than using Map or calling toString() everywhere.

You can also add your own Serializer to ObjectMapper for org.json.JSONObject.

The serializer for JSONObject (JSONObjectSerializer.java):

package com.example;

import com.fasterxml.jackson.core.JsonGenerator;
import com.fasterxml.jackson.databind.SerializerProvider;
import com.fasterxml.jackson.databind.ser.std.StdSerializer;
import org.json.JSONObject;

import java.io.IOException;

public class JSONObjectSerializer extends StdSerializer<JSONObject> {

    public JSONObjectSerializer() {
        this(null);
    }

    public JSONObjectSerializer(Class<JSONObject> t) {
        super(t);
    }

    @Override
    public void serialize(JSONObject value, JsonGenerator jgen, SerializerProvider provider) throws IOException {
        jgen.writeRawValue(value.toString());
    }
}

To add serializer to ObjectMapper (Example to override Spring Boot default ObjectMapper):

@Bean
public ObjectMapper getObjectMapper() {
    var objectMapper = new ObjectMapper();

    SimpleModule module = new SimpleModule();
    module.addSerializer(JSONObject.class, new JSONObjectSerializer());
    objectMapper.registerModule(module);

    return objectMapper;
}

Comments

-2

I get this error because I wrote

JSONObject j1 = method()
JSONObject j2 = new JSONObject(j1)

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.