RestTemplate调用返回401未经授权

时间:2018-07-19 07:43:30

标签: spring-boot ibm-cloud resttemplate apache-commons-httpclient

背景

我正在尝试使用RestTemplate从SpringBoot应用程序使用IBM Cloud API上托管的REST端点。我正在使用以下代码片段进行通话:

RestTemplate send = new RestTemplate();

HttpHeaders headers = new HttpHeaders();
headers.setAccept(Collections.singletonList(MediaType.APPLICATION_JSON));
headers.setContentType(MediaType.APPLICATION_JSON);
headers.setCacheControl(CacheControl.noCache());
headers.set("x-ibm-client-id", clientId);
headers.set("x-ibm-client-secret", clientSecret);

HttpEntity<BodyEntity> httpEntity = new HttpEntity<>(bodyEntity, headers);

send.exchange(ENDPOINT_URL, HttpMethod.POST, httpEntity, Object.class);

我使用以下代码片段配置RestTemplate

@Bean
public RestTemplate restTemplate(RestTemplateBuilder builder) {
    return builder.build();
}

问题

使用此代码段,在拨打电话时会收到401未经授权。当我使用Postman拨打同一电话时,我从服务器收到正确的响应,没有任何问题。

自从我收到401响应代码以来,我设置为通过记录请求的标头和正文以及其他部分来进一步调查该请求。

我实现了ClientHttpRequestInterceptor来记录传出的请求以进一步调试问题,并将此拦截器添加到我的RestTemplate配置中,如下所示:

@Bean
public RestTemplate restTemplate(RestTemplateBuilder builder) {
    // new code
    builder.interceptors(new LoggingClientHttpRequestInterceptor());
    return builder.build();
}

再次发出请求后,我可以在日志中看到拨出电话包含应有的所有详细信息,例如标头和正文正确。

此后,我将整个事情更改为使用Apache HTTP Client,如下所示:

CloseableHttpClient httpClient = HttpClients.createDefault();
HttpPost httpPost = new HttpPost(URL);

String reqString = "BODY";
httpPost.setEntity(new StringEntity(reqString, ContentType.APPLICATION_JSON));

httpPost.setHeader("accept", "application/json");
httpPost.setHeader("content-type", "application/json");
httpPost.setHeader("cache-control", "no-cache");
httpPost.setHeader("x-ibm-client-id", clientId);
httpPost.setHeader("x-ibm-client-secret", clientSecret);

CloseableHttpResponse response = httpClient.execute(httpPost);

try {
    System.out.println("Response status: " + response.getStatusLine());
    HttpEntity entity1 = response.getEntity();
    System.out.println("Response :" + entity1.toString());
} finally {
    response.close();
}

使用上面的代码段,我执行了请求并收到了正确的响应。

问题

为什么RestTemplate调用返回并出错,而HttpClient返回正确的响应? 我是否需要进一步配置RestTemplate? 我错过了什么?

0 个答案:

没有答案