While I tend to use vocabulary more loosely than those who associate a model or structure to a programming language I am sorry for any confusion.
Actors : http://en.wikipedia.org/wiki/Actor_model >From my standpoint the idea of event emitters using callbacks the callbacks are being treated as actors. On a more casual level actors could relate to deferreds / promises / monads / etc. as you wish to call them if you insist on using them as the event's reactor being forcibly the object that has the callbacks associated with them. Perhaps message based programming would have been a better term, however I needed to convey a sense of shared state. In this case the closured variables that a function can concurrently mutate (not in direct parallel due to single threaded nature). Monads : http://en.wikipedia.org/wiki/Monad_(functional_programming) >From this article (simplest example is the state monad) we can see adding dynamic information to a set of calculations. How is this drastically different from a closured variable and a callback (dynamic typing aside)? Perhaps I am confused about this, but it was my understanding that monads need not be their own object aside from the invoker and that they represent a calculation tied to state information. At least that is how I have used them in the past. Strict Mode Error: Reduced example - http://jsfiddle.net/zrX5B/ This is exceedingly rare in need but an example of if you want to support streamline.js and you have a C++ module that uses the event loop, you may need to detect random junk that gets treated as async or blocks, and if it gets blocked you may need to act accordingly. Node / DOM Prior Art: Just because it is done before does not mean it is encouraged, loved, or even sane. Almost every time someone saves a NodeList in the DOM the first time, they end up searching for WTF is going on. The same is true about cacheing Node buffers related to streaming reads from the file system. Preemption / Asynchronous point: This relates to the idea of proxy asynchronous behavior not blocking code execution. By that I mean that they lack coroutine like cooperation (via a yield [JS yield behaves a bit different than the definition used here] / callback / etc.) to determine when it is safe to continue the current flow of control for our program. I will refer to blocking asynchronous function proxies as proxies that involve cooperative measures. An example of these would be best: Assume a Proxy of type ASYNC will do a remote HTTP request whenever a property is accessed / set (lets assume standard REST CRUD). This could be used for some nice database persistence without much effort. Given an example of a service helper function: function prepare(service, data) { service.data = data; } prepare(service1, 'hello world!'); console.log('data loaded!'); If the service is not an ASYNC we know that execution will block as per normal and order will be preserved. If the service is an ASYNC and Asyncchronous Proxies block execution (until cooperation) we also know order will be preserved and the event loop will be blocked during this. If one service is ASYNC and Async Proxies __do not block execution__ we have a problem: * we do not know exactly when prepare will be done (in case we need cleanup on a failure, particularly brutal if we want to fail if a certain timeout is set, but this actually ends up succeeding) * the console.log may fire before the data is loaded * even worse if we are setting variables to determine state Ok, so lets step back and take a closer look at blocking execution for asynchronous function proxies. What does this get us: * Be able to treat an asynchronous function (the handler of the proxy) as if it were synchronous. Very good. * Blocks the event loop at potentially unforeseen times. Very bad. You cannot allow this in some time critical paths (protocols that require time assurances or abort callbacks on timeout instead of waiting 180s for TCP timeout, etc). Finally I get to a point of discussion on everyone wanting everything to look pretty, even if it causes these problems, and means everyone must follow the convention. function DBEventEmitter(adaptor) { var self = this; adaptor.connectionString = 'x'; //have to do this on nexttick, adaptor may be synchronous (in memory) process.nextTick(function() { adaptor.init(); }); } Now when we move this to a land with Async Proxies, I have no doubt we will see the following: function DBEventEmitter(adaptor) { adaptor.connectionString = 'x'; } Looks nicer, but if we need to register events onto the DBEventEmitter, it must be done ... prior to the constructor? Ok, well we will just do a nexttick to allow that, even though we are guaranteed init will succeed by the time the function returns. We could get rid of event registration all together, but for that would mean wrapping all async adaptors in async proxies, that is a lot more trouble than just using a simple function invocation and callback. Even with helpers and enumeration of properties, this could become difficult to automate without adding a separate config definition to see what properties should be considered async in order to provide cooperative concurrency (actually seems to remind me of WSDL where you end up making a type for promises). Sorry if I sound aggressive, but I have strict opinions about explicit behavior rather than potentially surprising behavior for code aesthetics. If a different invocation syntax was required so that one could tell that something may take time due to being async I would have little issue. I merely do not see much gain in combining two drastically different execution types into a single syntax. _______________________________________________ es-discuss mailing list [email protected] https://mail.mozilla.org/listinfo/es-discuss

