Джексону не удалось преобразовать элемент запроса - PullRequest
0 голосов
/ 27 августа 2018

Я использую Spring для создания REST API, который предоставляет конечную точку POST. Я могу достичь конечной точки, но у меня проблемы с чтением тела запроса.

Работает следующий код: payload содержит отправленный объект.

@RestController
public class RestController {

    @RequestMapping(value = "/endpoint")
    public ResponseEntity endpoint(@RequestParam("payload") String str) throws IOException {
        ObjectMapper objectMapper = new ObjectMapper();
        Payload payload = objectMapper.readValue(str, Payload.class);
        return ResponseEntity.status(HttpStatus.OK).build();
    }

}

Однако следующий код НЕ РАБОТАЕТ: он выдает исключение.

@RestController
public class RestController {

    @RequestMapping(value = "/endpoint")
    public ResponseEntity endpoint(@RequestParam("payload") Payload payload) throws IOException {
        return ResponseEntity.status(HttpStatus.OK).build();
    }

}

Исключение:

Failed to convert request element: org.springframework.web.method.annotation.MethodArgumentConversionNotSupportedException: Failed to convert value of type 'java.lang.String' to required type 'beans.Payload'; nested exception is java.lang.IllegalStateException: Cannot convert value of type 'java.lang.String' to required type 'beans.Payload': no matching editors or conversion strategy found

Почему последний не работает? Я думал, что Spring запрос параметров декодирования таким же образом ...


ОБНОВЛЕНИЕ: мой класс полезной нагрузки:

@JsonIgnoreProperties(ignoreUnknown = true)
public class Payload {

    @JsonProperty("type")
    private String type;

    @JsonProperty("callback_id")
    private String callbackId;

    @JsonProperty("message_ts")
    private String message_ts;

    @JsonProperty("response_url")
    private String responseUrl;

    protected Payload() {}

    public String getType() {
        return type;
    }

    public String getCallbackId() {
        return callbackId;
    }

    public String getMessage_ts() {
        return message_ts;
    }

    public String getResponseUrl() {
        return responseUrl;
    }

}

ОБНОВЛЕНИЕ: я проверяю конечную точку с Почтальоном. Вот что я посылаю:

KEY       VALUE
payload   { "type": "test" }

и это ошибка, которую я получил:

{
    "timestamp": "2018-08-28T10:38:33.133+0000",
    "status": 415,
    "error": "Unsupported Media Type",
    "message": "Content type 'multipart/form-data;boundary=--------------------------586093407866564427326096;charset=UTF-8' not supported",
    "path": "/endpoint"
}

Ответы [ 4 ]

0 голосов
/ 28 августа 2018

Ваши шаблоны URL настроены неправильно. Попробуйте,

@RestController
@RequestMapping(value = "/")
public class PayLoadController {

@RequestMapping(value = "endpoint/",method = RequestMethod.POST)
public ResponseEntity endpoint(@RequestBody Payload payload) throws IOException {
return ResponseEntity.status(HttpStatus.OK).build();
}}

Просто скопируйте, вставьте этот код и переименуйте имя файла контроллера. Затем опубликуйте ваши данные, локальный: 8080 / конечная точка /

0 голосов
/ 27 августа 2018

Используйте @RequestBody вместо @RequestParam. Ваш Payload находится в теле сообщения, а аннотация @RequestBody десериализует его в полезную нагрузку.

0 голосов
/ 27 августа 2018
  1. Просто избавься от protected Payload() {}. Поскольку у вас нет параметризованного конструктора, у вас все в порядке, компилятор Java позаботится о добавлении конструктора по умолчанию в скомпилированный байт-код.

  2. И вам нужно изменить это

Метод контроллера

@RestController
public class RestController {
    @RequestMapping(value = "/endpoint")
    public ResponseEntity endpoint(@RequestParam("payload") Payload payload) throws IOException {
        return ResponseEntity.status(HttpStatus.OK).build();
    }
}

Изменения

а. Измените метод HTTP-запроса на POST вместо GET. (method = RequestMethod.POST).

б. Измените полезную нагрузку на тело сообщения, содержащее параметр запроса (@RequestParam("payload") Payload payload -> @RequestBody Payload payload).

Измените его на

@RequestMapping(value = "/endpoint", method = RequestMethod.POST)
public ResponseEntity endpoint(@RequestBody Payload payload) throws IOException {
    return ResponseEntity.status(HttpStatus.OK).build();
}
0 голосов
/ 27 августа 2018

Конструктор полезной нагрузки не должен быть защищен. Это должно быть публично.

Измените его на

Public PayLoad(){}

В противном случае контроллеры не могут создать объект полезной нагрузки, когда сопоставление выполнено.

...