After a bit of a hiatus, I'm back to working on Halley. Today I am finalizing the wire representation of events between the Halley server side (Perl) and the Halley client side (JavaScript). This only affects application developers in that they will see a very nice interface for the two halves of their application to communicate with each other, so while the internals won't affect users, it would be good to get them solidified so I won't be as tempted to change it again.
On both sides, when the application sends a Halley event to the other side, the event will be queued up and then event queue processing will be queued. Let's be more clear. A Halley event is queued by the application. The Halley framework places that event in the send queue. Then it schedules the send queue to be processed -- with setTimeout for the browser side and by queueing a POE-event on the server side -- as soon as reasonably possible. Why the double queueing? If the application is firing off events rapidly, this will allow the communication to happen in larger batches, reducing the number of round-trips, and (I am guessing, but it sounds reasonable) reducing the overall latency.
The Perl application sends by executing:
POE::Kernel->post($client, 'send', $event_type, arg1, arg2, ...)
where arg1, arg2, ... are any number of arguments of any type. (Of course, the arguments must be encodable as JSON objects, but that should be obvious and not too strong of a restriction for most cases. Anything that's not a subref should be okay.) This is then queued up as a Perl hash of the form { event => $event_type, args => [ arg1, arg2, ... ] }.
A future enhancement might remove the 'send' POE-event type and have the POE-client pass on any POE-events it doesn't have reserved (received on a _default event handler) but this is not critical or difficult.
When it comes to send the pending events, assuming there was a second event with no arguments queued after the above, the JSON object transmitted to the browser-side code will be:
[ { "event": "event_type", "args": [ "arg1", "arg2", "..." ] },
{ "event": "another_event_type", "args": [ ] } ]
This is simply the string that results from JSON-encoding a Perl array of the above internal form.
The JavaScript application sends by executing:
halley.sendEvent(event_type, arg1, arg2, ...);
where again, arg1, arg2, ... are any number of arguments of any type. Anything sensible (i.e. not functions) should be okay. This is then queued up as a JavaScript object of the form { event: event_type, args: [ arg1, arg2, ... ] }.
The wire representation of events from the browser to the application server is the same as for the other direction, and is simply the string that results from JSON-encoding a JavaScript array of the above internal form.