Home > database >  Spring Boot - Json RequestBody, String/Enum with/without quotation marks
Spring Boot - Json RequestBody, String/Enum with/without quotation marks

Time:12-18

I went into a strange problem. Why does the first code accept input without quotation marks, but the second does not?

To be honest, the second one makes sense. But why is the first one accepting the input given without quotation marks?

I really would like to know why this decision was taken.

package com.example.corntest;

import lombok.extern.log4j.Log4j;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RestController;

import static org.springframework.util.MimeTypeUtils.APPLICATION_JSON_VALUE;

@SpringBootApplication
@RestController
public class CornTestApplication {

    public static void main(String[] args) {
        SpringApplication.run(CornTestApplication.class, args);
    }

    //works - does NOT remove quotation marks
    //curl 'http://localhost:8080/test' -X POST -H 'Content-Type: application/json'  --data-raw '"SunGoesUp"' -vv

    //works - but doesnt make sense - in comp. to code made in the bottom
    //curl 'http://localhost:8080/test' -X POST -H 'Content-Type: application/json'  --data-raw 'SunGoesUp' -vv
    @PostMapping(value = "/test", consumes = APPLICATION_JSON_VALUE)
    void mytestPost(@RequestBody String myString){
        System.out.println(myString);
    }

    enum Test {
        TESTA,
        TESTB,
        TESTC
    }

    //works
    //curl 'http://localhost:8080/testEnum' -X POST -H 'Content-Type: application/json'  --data-raw '"TESTA"' -vv

    //does not work
    //curl 'http://localhost:8080/testEnum' -X POST -H 'Content-Type: application/json'  --data-raw 'TESTA' -vv

    //Why
    @PostMapping(value = "/testEnum", consumes = APPLICATION_JSON_VALUE)
    void myTestEnum(@RequestBody Test myEnumValue){
        System.out.println(myEnumValue);
    }
}

CodePudding user response:

In the case where you are using @RequestBody String myString the payload of the http request is put in there as-is. So whatever you send will be placed in there. The content-type doesn't matter as it will copy the payload of the request as is.

In the second case, an actual JSON string is required to be able to convert to an enum. A JSON based String needs to have quotation marks else it isn't a JSON String. Something other than a string cannot be converted to an enum.

To convert from the payload of the body to the requested object Spring uses an [HttpMessageConverter]. It will select the correct HttpMessageConverter based on the Content-Type header. In your case, assuming the defaults, this will result in the MappingJackson2HttpMessageConverter. Which will use the body to convert to the enum. Which will then fail as it isn't a valid JSON string (no quotation marks).

What is a String in JSON is explained here.

  • Related