使用curl可正常获取JWS Token但Java调用返回403错误如何解决
问题场景:使用curl发送POST请求可正常获取JWS Token,但使用Java代码调用相同接口时返回403状态码
正常curl请求信息
执行命令
curl -d "username=<user>&password=<pass>" -X POST https://example.com/wp-json/api/v1/token
实际请求报文
POST https://example.com/wp-json/api/v1/token HTTP/1.1 Host: example.com User-Agent: curl/7.55.1 Accept: */* Content-Length: <length> Content-Type: application/x-www-form-urlencoded username=<user>&password=<pass>
Java请求异常信息
HttpClient调试输出
org.apache.http.wire - http-outgoing-0 >> "POST /wp-json/api/v1/token HTTP/1.1[\r][\n]" org.apache.http.wire - http-outgoing-0 >> "Content-Length: 45[\r][\n]" org.apache.http.wire - http-outgoing-0 >> "Content-Type: application/x-www-form-urlencoded; charset=ISO-8859-1[\r][\n]" org.apache.http.wire - http-outgoing-0 >> "Host: www.example.com[\r][\n]" org.apache.http.wire - http-outgoing-0 >> "Connection: Keep-Alive[\r][\n]" org.apache.http.wire - http-outgoing-0 >> "User-Agent: Apache-HttpClient/4.5.13 (Java/1.8.0_121)[\r][\n]" org.apache.http.wire - http-outgoing-0 >> "Accept-Encoding: gzip,deflate[\r][\n]" org.apache.http.wire - http-outgoing-0 >> "[\r][\n]" org.apache.http.wire - http-outgoing-0 >> "username=<user>&password=<pass>"
问题代码
public void getToken(URI url, String username, String password) { HttpEntity entity = new StringEntity("username=" + username + "&password=" + password, ContentType.APPLICATION_FORM_URLENCODED); HttpHost target = new HttpHost(url.getHost(), 443, "https"); SSLContext sslcontext = SSLContexts.createSystemDefault(); SSLConnectionSocketFactory sslConnectionSocketFactory = new SSLConnectionSocketFactory( sslcontext, new String[] { "TLSv1.2", "SSLv3" }, null, SSLConnectionSocketFactory.getDefaultHostnameVerifier()); Registry<ConnectionSocketFactory> socketFactoryRegistry = RegistryBuilder.<ConnectionSocketFactory>create() .register("http", PlainConnectionSocketFactory.INSTANCE) .register("https", sslConnectionSocketFactory) .build(); PoolingHttpClientConnectionManager cm = new PoolingHttpClientConnectionManager(socketFactoryRegistry); CloseableHttpClient httpClient = HttpClients.custom() .setSSLSocketFactory(sslConnectionSocketFactory) .setConnectionManager(cm) .build(); HttpPost httpPost = new HttpPost(url); httpPost.setEntity(entity); int statusCode = 0; try (CloseableHttpResponse httpResponse = httpClient.execute(target, httpPost)) { statusCode = httpResponse.getStatusLine().getStatusCode(); //parse response here } }
解决方案
两者请求的核心差异为Host头字段不一致:curl请求的Host为example.com,Java代码请求的Host为www.example.com,目标服务对带www前缀的域名做了访问限制,因此返回403状态码。
将Java请求URL中的"www"前缀移除,保证Host头与curl请求一致后,接口即可正常调用。
内容的提问来源于stack exchange,提问作者AK1604
相关产品推荐
相关产品推荐

