Spring RestTemplate POST Request с URL-кодированными данными
Я новичок в Spring и пытаюсь сделать запрос на отдых с помощью RestTemplate. Код Java должен делать то же самое, что и команда curl:
curl --data "name=feature&color=#5843AD" --header "PRIVATE-TOKEN: xyz" "https://someserver.com/api/v3/projects/1/labels"
Но сервер отказывается от RestTemplate с 400 Bad Request
RestTemplate restTemplate = new RestTemplate();
HttpHeaders headers = new HttpHeaders();
headers.add("PRIVATE-TOKEN", "xyz");
HttpEntity<String> entity = new HttpEntity<String>("name=feature&color=#5843AD", headers);
ResponseEntity<LabelCreationResponse> response = restTemplate.exchange("https://someserver.com/api/v3/projects/1/labels", HttpMethod.POST, entity, LabelCreationResponse.class);
Может кто-нибудь сказать мне, что я делаю неправильно?
Ответы
Ответ 1
Я думаю, что проблема в том, что при попытке отправить данные на сервер не был установлен заголовок типа контента, который должен быть одним из двух: "application/json" или "application/x-www-form-urlencoded". В вашем случае это "application/x-www-form-urlencoded" на основе ваших параметров (имя и цвет). Этот заголовок означает "какой тип данных мой клиент отправляет на сервер".
RestTemplate restTemplate = new RestTemplate();
HttpHeaders headers = new HttpHeaders();
headers.setContentType(MediaType.APPLICATION_FORM_URLENCODED);
headers.add("PRIVATE-TOKEN", "xyz");
MultiValueMap<String, String> map = new LinkedMultiValueMap<>();
map.add("name","feature");
map.add("color","#5843AD");
HttpEntity<MultiValueMap<String, String>> entity = new HttpEntity<>(map, headers);
ResponseEntity<LabelCreationResponse> response =
restTemplate.exchange("https://foo/api/v3/projects/1/labels",
HttpMethod.POST,
entity,
LabelCreationResponse.class);
Ответ 2
Вам необходимо установить Content-Type в application/json. В запросе должен быть указан Content-Type. Ниже приведен модифицированный код для установки Content-Type
final String uri = "https://someserver.com/api/v3/projects/1/labels";
String input = "US";
HttpHeaders headers = new HttpHeaders();
headers.setContentType(MediaType.APPLICATION_FORM_URLENCODED);
headers.add("PRIVATE-TOKEN", "xyz");
HttpEntity<String> request = new HttpEntity<String>(input, headers);
ResponseEntity<LabelCreationResponse> response = restTemplate.postForObject(uri, request, LabelCreationResponse.class);
Здесь HttpEntity построен с вашим вводом, т.е. "US" и с заголовками. Дайте мне знать, если это сработает, если нет, пожалуйста, разделите исключение. Ура!
Ответ 3
Возможно, это проблема с заголовком, если заголовок является допустимым заголовком, ссылаются ли вы на заголовок "BasicAuth"?
HttpHeader headers = new HttpHeaders();
headers.add("Content-Type", MediaType.APPLICATION_FORM_URLENCODED.toString());
headers.add("Accept", MediaType.APPLICATION_JSON.toString()); //Optional in case server sends back JSON data
MultiValueMap<String, String> requestBody = new LinkedMultiValueMap<String, String>();
requestBody.add("name", "feature");
requestBody.add("color", "#5843AD");
HttpEntity formEntity = new HttpEntity<MultiValueMap<String, String>>(requestBody, headers);
ResponseEntity<LabelCreationResponse> response =
restTemplate.exchange("https://example.com/api/request", HttpMethod.POST,
formEntity, LabelCreationResponse.class);