Skip to main content

[jsr356-experts] Re: [jsr356-users] Re: V003 API for your review

  • From: Greg Wilkins < >
  • To: Danny Coward < >
  • Cc:
  • Subject: [jsr356-experts] Re: [jsr356-users] Re: V003 API for your review
  • Date: Sat, 11 Aug 2012 12:23:46 +1000



On 10 August 2012 09:57, Danny Coward < " target="_blank"> > wrote:
Also for ease of use, I'd really like to see the API offer message aggregation as part of the API.  With annotations this could be:

@WebSocketEndPoint(maxMessage=8192)
public class MyPojoWebSocket
{
  @WebSocketMessage
  public void myAsyncTextHandler(String part)
  { ... }
}
Does this mean that the 'part' variable passed in would be the size of the message if less than 8192 bytes in length, otherwise the first 8192 bytes of the message ?

Interesting. What kind of use case are you thinking of ?


If you are writing an application where you know your maximum message size (eg for chess.com we know exactly the size of a move or a representation of the chess board).
Because these messages are small (typically 10s of bytes) then if we code to the API

  public void myAsyncTextHandler(String part, boolean last)

we will almost almost always receive the messages in a single callback with all the bytes and last==true.   This could result in lazy programmers assuming that "almost always" == "always" and not handle the case where last==false.    There code would mostly work until somebody deploys some evil proxy that fragments all frames into 1 byte messages... or similar strange stuff.    This will break code that has assumed last==true always.

That I think we should allow users to delegate aggregation of the parts to the protocol handling so they can just implement

  public void myAsyncTextHandler(String completeMessage)

But to do so, they need to tell the protocol handling what is the max message size they expect, so that if any parts add up to more than that, that is an error  - close the connection etc.



with neither being blocking.  The user simply needs to call sendBytes(data).get() to achieve blocking.

Alternately if you want to keep the blocking call, then don't have a future in the API at all.   Instead provide a utility implementation of SendHandler that is a Future and can be used like:

 SendHandlerFuture future=new SendHandlerFuture();
 wsEndPoint.sendBytes(data,future);
 future.get(10,TimeUnit.SECONDS);

This mantra could easily be wrapped up in a static method to make it a one liner:

  SendHandlerFuture.sendBytes(wsEndPoint,data).get(10,TimeUnit.SECONDS);

Yeah, I agree combining the byFuture and the byCompletion version into one method is neither typical nor efficient if you don't use the future, even if its compact. Probably should separate them out.
I do think that the blocking version is going to be the easy/70% kind of style that developers would use. So I think it ought to be as simple as possible - i.e. only one method call.
Maybe we should just have 3 calls for the three styles: blocking, byFuture, byCompletion, nice and explicit and no extra steps needed ?


I'm ok with either:

1 method (async callback only with future/blocking provided by a SendHandlerFuture)
2 methods (async callback and one returning future - just like NIO.2)
3 methods (async callback, return future, blocking)

but with a slight preference for 1, then 2, then 3

cheers

 


--
Greg Wilkins < " target="_blank"> >
http://www.webtide.com
Developer advice and support from the Jetty & CometD experts.


[jsr356-experts] V003 API for your review

Danny Coward 08/03/2012

[jsr356-experts] Re: V003 API for your review

Greg Wilkins 08/08/2012

[jsr356-experts] Re: [jsr356-users] Re: V003 API for your review

Danny Coward 08/09/2012

[jsr356-experts] Re: [jsr356-users] Re: V003 API for your review

Greg Wilkins 08/11/2012
 
 
Close
loading
Please Confirm
Close