brian clozel created HTTPCLIENT-2281:
----------------------------------------

             Summary: AsyncExecChain is not aware of cancellations
                 Key: HTTPCLIENT-2281
                 URL: https://issues.apache.org/jira/browse/HTTPCLIENT-2281
             Project: HttpComponents HttpClient
          Issue Type: Bug
          Components: HttpClient (async)
    Affects Versions: 5.2.1
            Reporter: brian clozel


When working on a AsyncExecChain implementation, the "execute" method is tied 
to the lifecycle of the exchange through the AsyncExecCallback that is provided 
to the next element in the chain.

It's not clear how the AsyncExecChain is supposed to be notified of 
cancellations and how it should clear resources. None of the AsyncExecCallback 
contracts are not called when a cancellation occurs.

Given the following sample implementation, that allocates resources when the 
execution starts. The handler is not notified of cancellations and resources 
cannot be cleared as a result.
{code:java}
public class CustomHandler implements AsyncExecChainHandler {

    @Override
    public void execute(HttpRequest request, AsyncEntityProducer 
entityProducer, AsyncExecChain.Scope scope,
            AsyncExecChain chain, AsyncExecCallback asyncExecCallback) throws 
HttpException, IOException {
        
        CustomResource resource = CustomResource.allocate();

        chain.proceed(request, entityProducer, newScope, new 
AsyncExecCallback() {

            @Override
            public AsyncDataConsumer handleResponse(HttpResponse response, 
EntityDetails entityDetails)
                    throws HttpException, IOException {
                // not called in case of cancellation
                resource.clear();
                return asyncExecCallback.handleResponse(response, 
entityDetails);
            }

            @Override
            public void handleInformationResponse(HttpResponse response) throws 
HttpException, IOException {
                // not called in case of cancellation                
            }

            @Override
            public void completed() {
                // not called in case of cancellation
                resource.clear();
            }

            @Override
            public void failed(Exception cause) {
                resource.clear();
            }

        });

    }
{code}
Here is a concrete sample using the custom handler:
{code:java}
CustomHandler customHandler = new CustomHandler();
CloseableHttpAsyncClient client = HttpAsyncClients.custom()
  .addExecInterceptorFirst("custom", customHandler)
  .build();
client.start();

final SimpleHttpRequest request = 
SimpleRequestBuilder.get("http://localhost/delay/10";).build();
final Future<SimpleHttpResponse> future = client.execute(request,
    new FutureCallback<SimpleHttpResponse>() {
        @Override
        public void completed(final SimpleHttpResponse response) {
        }

        @Override
        public void failed(final Exception ex) {
        }

        @Override
        public void cancelled() {
          // this method is called but the custom handler is not made aware of 
cancellations
          System.out.println(request + " cancelled");
        }
});
future.cancel(true);
{code}
So far I have used the AsyncExecChain.Scope CancellableDependency and tried to 
wrap it to be notified of cancellations but I'm not sure this is the right 
choice.



--
This message was sent by Atlassian Jira
(v8.20.10#820010)

---------------------------------------------------------------------
To unsubscribe, e-mail: [email protected]
For additional commands, e-mail: [email protected]

Reply via email to