Apache HttpComponents 5:POST 使用 HttpAsyncClient 形成数据
Apache HttpComponents 5: POST form data with HttpAsyncClient
我正在寻找 POST 使用 HttpAsyncClient
表单数据的解决方案。到目前为止,我发现的所有 examples 都只发送了简单的 GET 请求。这是我到目前为止所得到的:
try (CloseableHttpAsyncClient client = HttpAsyncClients.createDefault()) {
SimpleHttpRequest httpPost = SimpleHttpRequests.post("http://httpbin.org");
// How to add key=value as form data to httpPost?
Future<SimpleHttpResponse> future = client.execute(httpPost, new FutureCallback<SimpleHttpResponse>() {
@Override
public void completed(SimpleHttpResponse simpleHttpResponse) {
System.out.println(simpleHttpResponse.getCode());
System.out.println(simpleHttpResponse.getBody());
}
@Override
public void failed(Exception e) {
System.out.println(e);
}
@Override
public void cancelled() {
System.out.println("cancelled");
}
}
}
我也查看了源代码,在那里我找到了 SimpleHttpRequest::setBody
方法和相应的 SimpleBody
class。但它们似乎也不支持表单数据。
基本上,我需要相当于 OkHttp
的 FormBody
。
在深入了解 Apache HttpComponents 5 的文档和源代码之后,我想到了以下解决方案。我需要创建一个 AsyncRequestProducer
和一个 AsyncResponseConsumer
,而不是使用 SimpleHttpRequests
。请求生成器对象定义了如何创建我的请求,与 SimpleHttpRequest
相比,它还能够生成我需要的表单主体。示例代码:
try (CloseableHttpAsyncClient client = HttpAsyncClients.createDefault()) {
client.start();
AsyncRequestProducer producer = AsyncRequestBuilder.post()
.setUri("http://httpbin.org")
.addParameter("key", "value") // <- form parameters in body
.build();
AsyncResponseConsumer<SimpleHttpResponse> consumer = SimpleResponseConsumer.create();
client.execute(producer, consumer, new FutureCallback<SimpleHttpResponse>() {
@Override
public void completed(SimpleHttpResponse simpleHttpResponse) {
System.out.println(simpleHttpResponse.getCode());
System.out.println(simpleHttpResponse.getBody());
}
@Override
public void failed(Exception e) {
System.out.println(e);
}
@Override
public void cancelled() {
System.out.println("cancelled");
}
});
}
或者,我可以使用 AsyncEntityProducer
生成表单正文:
Iterable<NameValuePair> params = Stream.of(new BasicNameValuePair("key", "value"))
.collect(Collectors.toList());
AsyncEntityProducer entityProducer = AsyncEntityProducers.createUrlEncoded(params, Charsets.UTF_8);
AsyncRequestProducer producer = AsyncRequestBuilder.post()
.setUri("http://httpbin.org")
.setEntity(entityProducer)
.build();
我正在寻找 POST 使用 HttpAsyncClient
表单数据的解决方案。到目前为止,我发现的所有 examples 都只发送了简单的 GET 请求。这是我到目前为止所得到的:
try (CloseableHttpAsyncClient client = HttpAsyncClients.createDefault()) {
SimpleHttpRequest httpPost = SimpleHttpRequests.post("http://httpbin.org");
// How to add key=value as form data to httpPost?
Future<SimpleHttpResponse> future = client.execute(httpPost, new FutureCallback<SimpleHttpResponse>() {
@Override
public void completed(SimpleHttpResponse simpleHttpResponse) {
System.out.println(simpleHttpResponse.getCode());
System.out.println(simpleHttpResponse.getBody());
}
@Override
public void failed(Exception e) {
System.out.println(e);
}
@Override
public void cancelled() {
System.out.println("cancelled");
}
}
}
我也查看了源代码,在那里我找到了 SimpleHttpRequest::setBody
方法和相应的 SimpleBody
class。但它们似乎也不支持表单数据。
基本上,我需要相当于 OkHttp
的 FormBody
。
在深入了解 Apache HttpComponents 5 的文档和源代码之后,我想到了以下解决方案。我需要创建一个 AsyncRequestProducer
和一个 AsyncResponseConsumer
,而不是使用 SimpleHttpRequests
。请求生成器对象定义了如何创建我的请求,与 SimpleHttpRequest
相比,它还能够生成我需要的表单主体。示例代码:
try (CloseableHttpAsyncClient client = HttpAsyncClients.createDefault()) {
client.start();
AsyncRequestProducer producer = AsyncRequestBuilder.post()
.setUri("http://httpbin.org")
.addParameter("key", "value") // <- form parameters in body
.build();
AsyncResponseConsumer<SimpleHttpResponse> consumer = SimpleResponseConsumer.create();
client.execute(producer, consumer, new FutureCallback<SimpleHttpResponse>() {
@Override
public void completed(SimpleHttpResponse simpleHttpResponse) {
System.out.println(simpleHttpResponse.getCode());
System.out.println(simpleHttpResponse.getBody());
}
@Override
public void failed(Exception e) {
System.out.println(e);
}
@Override
public void cancelled() {
System.out.println("cancelled");
}
});
}
或者,我可以使用 AsyncEntityProducer
生成表单正文:
Iterable<NameValuePair> params = Stream.of(new BasicNameValuePair("key", "value"))
.collect(Collectors.toList());
AsyncEntityProducer entityProducer = AsyncEntityProducers.createUrlEncoded(params, Charsets.UTF_8);
AsyncRequestProducer producer = AsyncRequestBuilder.post()
.setUri("http://httpbin.org")
.setEntity(entityProducer)
.build();