JSActors ======== In the Fission world, the preferred method of communication between between things-that-may-live-in-a-different-process are JSActors. At the time of this writing, Fission offers the following JSActors: - `JSProcessActor`, to communicate between a child process and its parent; - `JSWindowActor`, to communicate between a frame and its parent. JSProcessActor --------------- What are JSProcessActors? ~~~~~~~~~~~~~~~~~~~~~~~~~ A JSProcess pair (see below) is the preferred method of communication between a child process and its parent process. In the Fission world, JSProcessActors are the replacement for e10s-era *process scripts*. The life of a JSProcessActor pair ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ JSProcessActors always exist by pair: - one instance of `JSProcessActorChild`, which lives in the child process – for instance, `MyActorChild`; - one instance of `JSProcessActorParent`, which lives in the parent process – for instance, `MyActorParent`. The pair is instantiated lazily, upon the first call to `getActor("MyActor")` (see below). Note that if a parent process has several children, the parent process will typically host several instances of `MyActorParent` whereas the children will each host a single instance of `MyActorChild`. JSProcessActor primitives allow sending and receiving messages *within the pair*. As of this writing, JSProcessActor does not offer primitives for broadcasting, enumerating, etc. The pair dies when the child process dies. About actor names `````````````````` Note that the names `MyActorChild` and `MyActorParent` are meaningful – suffixes `Child` and `Parent` are how `getActor(...)` finds the correct classes to load within the JS code. JSWindowActor --------------- What are JSWindowActors? ~~~~~~~~~~~~~~~~~~~~~~~~~ A JSWindowActor pair (see below) is the preferred method of communication between a frame and its parent, regardless of whether the frame and parent live in the same process or in distinct processes. In the Fission world, JSWindowActors are the replacement for *framescripts*. Framescripts were how we structured code to be aware of the parent (UI) and child (content) separation, including establishing the communication channel between the two (via the Frame Message Manager). However, the framescripts had no way to establish further process separation downwards (that is, for out-of-process iframes). JSWindowActors will be the replacement. How are they structured? ~~~~~~~~~~~~~~~~~~~~~~~~~~ A review of the pre-Fission Message Manager mechanism ````````````````````````````````````````````````````` .. note:: There are actually several types of Message Managers: Frame Message Managers, Window Message Managers, Group Message Managers and Process Message Managers. For the purposes of this documentation, it's simplest to refer to all of these mechanisms altogether as the "Message Manager mechanism". Most of the examples in this document will be operating on the assumption that the Message Manager is a Frame Message Manager, which is the most commonly used one. Currently, in the post `Electrolysis Project`_ Firefox codebase, we have code living in the parent process (UI) that is in plain JS (.js files) or in JS modules (.jsm files). In the child process (hosting the content), we use framescripts (.js) and also JS modules. The framescripts are instantiated once per top-level frame (or, in simpler terms, once per tab). This code has access to all of the DOM from the web content, including all iframes within it. The two processes communicate via the Frame Message Manager (mm) using the ``sendAsyncMessage`` / ``receiveMessage`` API, and any code in the parent can communicate with any code in the child (and vice versa), by just listening to the messages of interest. The Frame Message Manager communication mechanism follows a publish / subscribe pattern similar to how Events work in Firefox: 1. Something exposes a mechanism for subscribing to notifications (``addMessageListener`` for the Frame Message Manager, ``addEventListener`` for Events). 2. The subscriber is responsible for unsubscribing when there's no longer interest in the notifications (``removeMessageListener`` for the Frame Message Manager, ``removeEventListener`` for Events). 3. Any number of subscribers can be attached at any one time. .. figure:: Fission-framescripts.png :width: 320px :height: 200px How JSWindowActors differ from the Frame Message Manager `````````````````````````````````````````````````````````` For Fission, the JSWindowActors replacing framescripts will be structured in pairs. A pair of JSWindowActors will be instantiated lazily: one in the parent and one in the child process, and a direct channel of communication between the two will be established. The JSWindowActor in the parent must extend the global ``JSWindowActorParent`` class, and the JSWindowActor in the child must extend the global ``JSWindowActorChild`` class. The JSWindowActor mechanism is similar to how `IPC Actors`_ work in the native layer of Firefox: #. Every Actor has one counterpart in another process that they can communicate directly with. #. Every Actor inherits a common communications API from a parent class. #. Every Actor has a name that ends in either ``Parent`` or ``Child``. #. There is no built-in mechanism for subscribing to messages. When one JSWindowActor sends a message, the counterpart JSWindowActor on the other side will receive it without needing to explicitly listen for it. Other notable differences between JSWindowActor's and Message Manager / framescripts: #. Each JSWindowActor pair is associated with a particular frame. For example, given the following DOM hierarchy::