0

I've implemented a GetMapping that takes a RequestBody and returns a status code:

@GetMapping(consumes = "application/json", produces = "application/json")
public ResponseEntity getAgreement(@RequestBody DataObject payload) {
    Boolean found = agreementService.findSingleAgreement(payload);
    if (found) {
        return new ResponseEntity(HttpStatus.OK);
    } else {
        return new ResponseEntity(HttpStatus.NOT_FOUND);
    }
}

I do not want to implement a GetMapping with multiple RequestParams, that's what the JSON's for.

Now I'm having a hard time testing that Get-Request because ResponseEntity either can't be deserialized by Jackson or the RequestBody in HttpEntity is not being read:

@Test
public void testGetRequest() {

    DataObject dataObject = new DataObject();
    dataObject.setAgrType("A"); // more setters exist

    HttpHeaders headers = new HttpHeaders();
    headers.setContentType(MediaType.APPLICATION_JSON);
    HttpEntity<DataObject> entity = new HttpEntity<>(dataObject, headers);

    ResponseEntity<DataObject> answer = this.restTemplate
            .withBasicAuth(username, password)
            .exchange(URL, HttpMethod.GET, entity,
                    new ParameterizedTypeReference<ResponseEntity>() {}); // exhange's causing trouble!!

    assertThat(answer.getStatusCode()).isEqualTo(HttpStatus.OK);
}

Here's the Exception from Jackson:

org.springframework.http.converter.HttpMessageConversionException: Type definition error: [simple type, class org.springframework.http.ResponseEntity]; nested exception is com.fasterxml.jackson.databind.exc.InvalidDefinitionException: Cannot construct instance of `org.springframework.http.ResponseEntity` (no Creators, like default construct, exist): cannot deserialize from Object value (no delegate- or property-based Creator) at [Source: (PushbackInputStream); line: 1, column: 2]
Matti
  • 5
  • 3
  • Why are you creating a get mapping for non-get type call? Rather use post call. – Vinay Prajapati Oct 16 '19 at 09:27
  • The HTTP `GET` method [should not have a body](https://stackoverflow.com/a/983458/5221149), so you can't do that. Change to a `POST`, i.e. use `@PostMapping` instead. – Andreas Oct 16 '19 at 09:30
  • @VinayPrajapati i want the client to perform a get request as he checks for the existince of an agreement in the database via that rest service. the client does not post new data to the api – Matti Oct 16 '19 at 09:31
  • You don't need multiple request parameters, as you can use databinding to bind those to a model attribute. So that understanding of a GET request isn't correct. Also the standard is a bit vague about GET requests with a body although Spring supports it your container/proxy/... might block it. – M. Deinum Oct 16 '19 at 09:33
  • @M.Deinum The standard is not vague about GET requests with a body, it says that it's ok for a body to be present, but the server shouldn't use it, as it "has no semantic meaning". See e.g. [HTTP GET with request body](https://stackoverflow.com/a/983458/5221149). – Andreas Oct 16 '19 at 09:37
  • 1
    Post is not for new data only. Anyways your might get some help at https://stackoverflow.com/questions/978061/http-get-with-request-body – Vinay Prajapati Oct 16 '19 at 09:37
  • @Andreas which is what I meant with vague :)., It is ok to have a body but should be ignored. But lets not move the discussion in that direction... – M. Deinum Oct 16 '19 at 10:25
  • Use post method, And you need to get data from request cody parameter in order to process it. @RequestMapping(method=RequestMethod.POST,value={"/Mobile/Abc"} ) public BasicResponce abc(@RequestHeader(value="parameterOne", required = false) String parameterOne, @RequestParam(value = "parameterSecond", required = false) String parameterSecond, @RequestParam(value = "parameterThird", required = true) long parameterThird, @RequestBody List dtoClass) { // Method Body } – Abdul Majid Bajwa Oct 16 '19 at 11:47

1 Answers1

1

@GetMapping is a specialized version of @RequestMapping annotation that acts as a shortcut for @RequestMapping(method = RequestMethod.GET). consumes makes sense for @RequestMapping(method = RequestMethod.POST) (or for the specialized version, @PostMapping) but not for @GetMapping. You need to use HTTP POST to be able to consume your JSON data.

Roger Gustavsson
  • 1,639
  • 10
  • 19