[webkit-dev] Passing data structures through postMessage()

Darin Fisher darin at chromium.org
Thu Sep 10 22:30:17 PDT 2009

Given shared workers (and indeed Chromium's out-of-process dedicated
workers), it seems like we also have cross process boundaries to consider.

On Thu, Sep 10, 2009 at 5:21 PM, Maciej Stachowiak <mjs at apple.com> wrote:

> On Sep 10, 2009, at 3:12 PM, Chris Campbell wrote:
>  Hi All,
>> I had it in mind to implement support for passing data structures
>> through postMessage() using the "structured clone" algorithm laid out
>> in the HTML5 spec:
>> http://dev.w3.org/html5/spec/Overview.html#posting-messages
>> http://dev.w3.org/html5/spec/Overview.html#safe-passing-of-structured-data
>> I've had some brief discussion with Dave Levin and Drew Wilson on
>> #chromium IRC about this, and have an approach in mind that follows
>> and elaborates on their suggestions, but there are still some holes in
>> it and I'd very much like input from people familiar with this area.
>> Currently, there are several postMessage() handlers (in
>> MessagePort.idl, DOMWindow.idl, DedicatedWorkerContext.idl, and
>> Worker.idl), and they all take a DOMString for the message parameter.
>> The general idea is to change that message parameter from a DOMString
>> to a new AttributeIterator type that allows walking of any sort of JS
>> structure/type.  AttributeIterator would essentially be an adapter to
>> translate native V8 or JSC JavaScript objects to an agnostic interface
>> suitable for walking the structure and serializing it.  I'm thinking
>> it would look something like this:
>> interface AttributeIterator {
>>   bool isUndefined();
>>   bool isNull();
>>   bool isFalse();
>>   bool isTrue();
>>   bool isNumber();
>>   String getNumber();
>>   bool isString();
>>   // ... cover the other types including Date, RegExp, ImageData,
>>   // File, FileData, and FileList ...
>>   // Retrieve the key for the next property (for Objects and Arrays)
>>   String nextEnumerableProperty();
>>   AttributeIterator getPropertyValue(key);
>> }
> Some thoughts off the cuff:
> I think it would be better to write custom code for doing the cloning for
> each JS engine. For one thing, turning everything into a string is not
> necessarily the most efficient way to do things. It might be possible to
> clone the object graph more directly in a threadsafe way. Also, things like
> File and ImageData fundamentally can't be turned into a string (well
> ImageData can)
> Second, to be really agnostic about it, postMessage should take a generic
> Message object that has some methods that can be used to do the cross-thread
> clone without building in the assumption that it serializes to a string in
> the middle.
> Third, using a stateful iterator for this instead of an interface
> representing a value is not a great design. Iterators are not good when what
> you are traversing is in general a graph.
> Fourth, this doesn't give a way to detect if an object graph is not in fact
> legal to clone.
> It's kind of a shame that we have the baggage of multiple JavaScript
> engines to contend with. Trying to do things in a generic way will make this
> task needlessly more difficult.
> You may also want to get input on this from Oliver Hunt, who wrote the JSC
> JSON parse/stringify code; from past discussions I know has opinions on how
> cross-thread cloning should work.
>> I'm also thinking that depending on compile-time flags, the
>> contstructor for AttributeIterator would either take a
>> v8::Handle<v8::Value> or JSC::JSvalue value.
>> Then in each implementation of postMessage() the AttributeIterator
>> instance could be passed to the structured clone serializer, which
>> would return a string.  Thereafter, no changes would be required to
>> WebCore internals since they already pass strings around... until on
>> the receiving end we get to MessageEvent.data where we would do the
>> deserialization in a custom getter.
>> Open questions:
>> (1) Is passing an AttributeIterator type into postMessage() really the
>> best way to go?  Drew mentioned that this might incur a bunch of ObjC
>> binding work on the JSC side...
>> (2) Where should AttributeIterator live in the source tree?
>> (3) Where should the serialization and deserialization routines live
>> in the source tree?
>> (3) I haven't addressed the specifics of the serialized string format.
>> Plain JSON is not quite sufficient since it doesn't retain type
>> information for Date, RegExp, etc..  However, I'm not too worried
>> about coming up with a suitable format for this.
>> Comments, advice, admonitions welcome!  :)
> In general I'm not sure this approach is workable. At the very least File,
> FileData, FileList and ImageData need to be passed as something other than
> strings. And I think the value of making the object graph traversal code
> generic while everything else is JS-engine-specific is pretty low. In
> addition, I do not think the proposed interface is adequate to implement the
> cloning algorithm.
> Regards,
> Maciej
> _______________________________________________
> webkit-dev mailing list
> webkit-dev at lists.webkit.org
> http://lists.webkit.org/mailman/listinfo.cgi/webkit-dev
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.webkit.org/pipermail/webkit-dev/attachments/20090910/42df7104/attachment.html>

More information about the webkit-dev mailing list