我在“ 302 Found” HTTP响应中遇到问题。在任何网络浏览器中,它都能正常工作。当我尝试通过HTTP客户端(httpcomponents)以编程方式导航某些URL时,虽然它不起作用。我知道那里有很多类似的讨论。但是到目前为止,他们都没有帮助我。因此,我要在这里提出来。
我正在使用的网页具有两要素认证。它通过了需要登录名/密码的第一个身份验证部分(POST请求)。它还通过了第二步身份验证(POST请求),该身份验证是短信代码。然后,当我按下任何URL时,服务器将返回“ 302 Found” HTTP响应。当我查看HTTP响应标头时,看到“ Location:./?logout”。我知道302表示我需要重定向到“位置”键下HTTP响应标头中显示的URL。但是成功登录后重定向到“注销”是没有意义的。相同的东西在浏览器中也可以正常工作,并且始终返回200 OK。我不明白为什么服务器端使用API时会返回302 Found HTTP,而浏览器返回200 OK。我也完全没有看到浏览器向“?logout” URL发送请求。
这是我的HttpClient(4.4.1版本)的样子:
final Registry<ConnectionSocketFactory> registry = RegistryBuilder.<ConnectionSocketFactory>create()
.register("http", new PlainConnectionSocketFactory())
.build();
final PoolingHttpClientConnectionManager connectionManager = new PoolingHttpClientConnectionManager(registry);
connectionManager.setMaxTotal(30);
connectionManager.setDefaultMaxPerRoute(5);
final HttpHost localhost = new HttpHost("localhost", 80);
connectionManager.setMaxPerRoute(new HttpRoute(localhost), 10);
final int timeout = 20 * 1000;
final RequestConfig requestConfig = RequestConfig.custom()
.setConnectTimeout(timeout)
.setConnectionRequestTimeout(timeout)
.setSocketTimeout(timeout)
.setCookieSpec(CookieSpecs.STANDARD)
.setCircularRedirectsAllowed(true)
.setRedirectsEnabled(true)
.build();
final CloseableHttpClient httpClient =
HttpClients.custom()
.setSSLSocketFactory(sslConnectionSocketFactory)
.setConnectionManager(connectionManager)
.setRedirectStrategy(new LaxRedirectStrategy())
.setDefaultRequestConfig(requestConfig)
.setDefaultCookieStore(new BasicCookieStore())
.build();
这是我执行简单的GET请求的方式:
CloseableHttpResponse httpResponse = null;
try {
final String url = "web-page-url";
final HttpGet getRequest = new HttpGet(url);
httpResponse = httpClient.execute(getRequest, getHttpContext(cookie));
final StatusLine status = httpResponse.getStatusLine();
if (status.getStatusCode() >= 200 && status.getStatusCode() < 300) {
LOGGER.debug("Successfully executed '{}' URL", url);
} else {
LOGGER.warn("'{}' response came from '{}' URL", status.getStatusCode(), url);
}
} finally {
if (httpResponse != null) {
try {
httpResponse.close();
} catch (final IOException e) {
LOGGER.error("Couldn't close HTTP response. Error:", e);
}
}
}
HTTP上下文方法:
private HttpContext getHttpContext(final String cookie) {
final BasicClientCookie clientCookie = new BasicClientCookie(cookie.split("=")[0], cookie.split("=")[1]);
clientCookie.setDomain("webpage-domain-name");
clientCookie.setPath("/");
final BasicCookieStore cookieStore = new BasicCookieStore();
cookieStore.addCookie(clientCookie);
final HttpContext context = new BasicHttpContext();
context.setAttribute(HttpClientContext.COOKIE_STORE, cookieStore);
return context;
}
成功登录后,以上GET请求始终返回302响应代码。任何想法/帮助将不胜感激!