Re: HTTP 2 client API

2015-08-01 Thread Michael McMahon

Wenbo,

On WebSockets, that API work is being handled separately to this work
and will be put out for review very soon.

- Michael


On 31/07/15 19:37, Wenbo Zhu wrote:



On Fri, Jul 31, 2015 at 11:32 AM, Simone Bordet 
mailto:simone.bor...@gmail.com>> wrote:


Hi,

On Fri, Jul 31, 2015 at 7:54 PM, Wenbo Zhu mailto:wen...@google.com>> wrote:
> Thanks for the update.
>
> ===
>
> Is WebSocket out of the scope now?
>
> == async streams
>
> I.e. how bodies are to be read/written asynchronously, with
flow-control
> (aka back pressures).
>
> There are many different styles or abstractions. IMO, if
reactive streams
> are to be included in jdk9, we may want to adopt the same model
(if not the
> API).

Okay.

> Or we follow the NIO2 model (readiness),

Please no ! :)

Ignoring the epoll part, is the issue in the API styles or the actual 
model?



> to not introduce another concept.

Reactive streams and NIO2 are at 2 different levels of abstraction.
If it's not reactive streams, then it must be something new.

FWIW, we're discussing with the Servlet 4 EG about introducing a
reactive stream API for Servlet 4 async I/O.
Not yet carved in stone, but it's getting a little traction.

Ah, I just cross-post this thread to the EG mailing list.


--
Simone Bordet
http://bordet.blogspot.com
---
Finally, no matter how good the architecture and design are,
to deliver bug-free software with optimal performance and reliability,
the implementation technique must be flawless.  Victoria Livschitz






Re: HTTP 2 client API

2015-08-01 Thread Michael McMahon

Here is what I propose on some of the issues you raised yesterday:

1. make it clear that HttpRequest.send() blocks until entire request is sent
and the response headers received.

2. Add a new method to HttpRequest
/**
 * Notifies when this request has been completely sent. If the 
request is

 * sent asynchronously then its response may be received before a
 * potentially large request body has been fully sent. If the request
 * was already sent when this method is called, then the returned
 * {@code CompletableFuture} will be already completed. If an error
 * occurs when sending the request, the returned CompletableFuture
 * completes exceptionally.
 *
 * @return a {@code CompletableFuture}
 */
public abstract CompletableFuture sentAsync();

So, to create the exact same behavior as HttpRequest.send() you would
have to wait on both the CFs returned from HttpRequest.sendAsync() and
HttpRequest.sentAsync().

3. Having done that makes me wonder if send() and sendAsync() should be
renamed response() and responseAsync(). It seems to be more consistent
with the rest of the API. And sendAsync() sounds too similar to 
sentAsync()


4. Add a new method to HttpRequest
/**
 * Cancels this request and its response. Any pending asynchronous
 * operations associated with the request or its response will complete
 * exceptionally.
 */
public abstract void cancel();


5. Rename HttpResponse.responseCode() to statusCode()

I'm not proposing to add any direct timeout control, since CF already 
provides
timed waits and with the addition of cancel() above, I don't see a need 
for further

methods.

- Michael

On 31/07/15 18:22, Simone Bordet wrote:

Hi,

On Fri, Jul 31, 2015 at 6:33 PM, Michael McMahon
 wrote:

Well, it needs co-operation between the producer and the consumer
obviously. But, the onResponseBodyChunk() method could write to a queue
and block if it reaches a certain size. The onRequestBodyChunk() would
read off the data and send it on. When the queue reaches a lower limit it
notifies the producer to continue. It's not asynchronous, but is possible
and I'm not sure we're aiming at this type of application.

Sure, it's possible to implement it in a blocking way with the current APIs.
But the whole world is moving to asynchronous APIs, so... :)


Having said that, this is an area we planned to look at again, after the
initial putback.

Great! Please notify this list when you have a further revision to review.


Strangely, Future.cancel() doesn't specify any such restriction, but
CompletableFuture.cancel() does. In theory, one could sub-class
CompletableFuture and implement cancellation behavior that way,
but the intent does seem to be that cancellation should come from outside
and just be reported through this class. And considering the point above
about stopping runaway request sends then maybe an explicit
cancellation API would be useful.

Right. Just remember that in my experience, supporting abort() would
complicate the implementation a lot, but I guess it's just an
implementation detail.


IMHO the API is confusing, I prefer just doing builder.header("Foo",
"foovalue").header("Bar", "barvalue").


the parameters have to be specified in pairs
with (header name first, then value) * n

Right, but you cannot enforce that, so the API is brittle, hence my dislike :)

Thanks !