需求:发送自定义header的GET请求,header中需要插入一个签名。
之前写过一个类似的请求,但是是POST的。这个也摸了一段时间,自己看参数整了出来。代码如下:
1 2 3 4 5 6 7 8 9 10 11 12 13
| LinkedMultiValueMap<String, String> headers = new LinkedMultiValueMap<>(); headers.put("Content-Type", Collections.singletonList("application/json;charset=UTF-8")); headers.put("signature", Collections.singletonList(makeSignature(form.getNewMobile())));
JSONObject json = new JSONObject(); json.put("oldMobile", mobile); json.put("newMobile", form.getNewMobile()); HttpEntity<String> request = new HttpEntity<String>(json.toString(), headers);
RestTemplate restTemplate = HttpInvoker.getRestTemplate();
ResponseEntityTemplate.postForEntity(whiteListURL, request, String.class);
|
很简单的想着,只需要把上面的postForEntity()
改成get的就行,但不是这样的。

Update: 2019/12/11
从链接学到了一种比较友好的写法:
1 2 3 4 5 6 7 8 9 10 11 12 13 14
| private static void getEmployees() { final String uri = "http://localhost:8080/springrestexample/employees"; RestTemplate restTemplate = new RestTemplate(); HttpHeaders headers = new HttpHeaders(); headers.setAccept(Arrays.asList(MediaType.APPLICATION_JSON)); HttpEntity<String> entity = new HttpEntity<String>("parameters", headers); ResponseEntity<String> result = restTemplate.exchange(uri, HttpMethod.GET, entity, String.class); System.out.println(result); }
|
粗略看了看postForEntity()
和getForEntity()
这两个方法的实现,都是准备参数,然后调用execute()
方法,如下:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18
| @Override public <T> ResponseEntity<T> postForEntity(String url, @Nullable Object request, Class<T> responseType, Object... uriVariables) throws RestClientException {
RequestCallback requestCallback = httpEntityCallback(request, responseType); ResponseExtractor<ResponseEntity<T>> responseExtractor = responseEntityExtractor(responseType); return nonNull(execute(url, HttpMethod.POST, requestCallback, responseExtractor, uriVariables)); }
@Override @Nullable public <T> T getForObject(String url, Class<T> responseType, Map<String, ?> uriVariables) throws RestClientException { RequestCallback requestCallback = acceptHeaderRequestCallback(responseType); HttpMessageConverterExtractor<T> responseExtractor = new HttpMessageConverterExtractor<>(responseType, getMessageConverters(), logger); return execute(url, HttpMethod.GET, requestCallback, responseExtractor, uriVariables); }
|
区别就在于RequestCallback
实例化的时候,传的参数不一样。POST的时候,是将header做为参数传给了RequestCallback
。再然后就是execute()
中的GET和POST参数不一样。到这个时候,发送自定义header的GET请求,已经很明显了。实例化的函数,都是public的。如果不是public的,或者说我们不能直接访问到,还可以考虑通过反射的方式去调用相关的方法,但这里不需要用反射了。
结果
1 2 3 4 5 6 7 8 9 10 11 12
| LinkedMultiValueMap<String, String> headers = new LinkedMultiValueMap<>(); headers.put("Content-Type", Collections.singletonList("application/json;charset=UTF-8")); headers.put("signature", Collections.singletonList(makeSignature(mobile)));
RestTemplate restTemplate = HttpInvoker.getRestTemplate(); HttpEntity request = new HttpEntity(headers);
RequestCallback requestCallback = restTemplate.httpEntityCallback(request, JSONObject.class); ResponseExtractor<ResponseEntity<JSONObject>> responseExtractor = restTemplate.responseEntityExtractor(JSONObject.class);
ResponseEntity<JSONObject> response = restTemplate.execute(apiAddress + "/xxx/whitelist/check?phone=" + mobile, HttpMethod.GET, requestCallback, responseExtractor);
|
虽然很简单,但是看似不可能,自己却做到了、完成了,就很有成就感。