Spring boot PutMapping with Enum as RequestBody issue

Viewed 1423

I have a spring boot controller endpoint as follows.

@PutMapping("/manage/{id}")
public ResponseEntity<Boolean> manage(@PathVariable Long id, @RequestBody Type type) { 
  ...
}

Where Type is an Enum as follows.

public enum Type {
    ONE,
    TWO
}

ISSUE 1: When I test this controller, I have to send the content as "ONE" instead of ONE for a successful invocation. i.e. it works with the following code.

mvc.perform(put("/api/manage/1")
            .contentType(MediaType.APPLICATION_JSON_VALUE)
            .content("\"" + Type.ONE + '\"'))
            .andExpect(status().isOk());

It does not work with

mvc.perform(put("/api/manage/1")
            .contentType(MediaType.APPLICATION_JSON_VALUE)
            .content(Type.ONE.name()))
            .andExpect(status().isOk());

ISSUE 2: I am not able to invoke this method from the Angular service.

this.http.put<string>('/api/manage/' + id, type)

gives me

org.springframework.web.HttpMediaTypeNotSupportedException: Content type 'text/plain;charset=UTF-8' not supported

Everything works when I add the Enum to a Dto and send an object from the client. But due to some business requirements, I want to use the current structure itself. i.e the Enum as a RequestBody.

UPDATE

I also tried to change the controller method structure to

@PutMapping(value = "/manage/{id}", consumes = MediaType.TEXT_PLAIN_VALUE)

I get the following error.

Content type 'text/plain' not supported

1 Answers

Both issues stem from trying to use a JSON endpoint as a plain text endpoint.

Ad 1, ONE is invalid JSON ("ONE" is valid)

Ad 2, when you just post a string, it is sent as text/plain and the endpoint complains.

Probably adding consumes="text/plain" to your @PutMapping will solve the problem, but frankly - I am not sure if string/enum mappings work out-of-the-box in the hodge-podge that is spring boot.

Related