[mediacapture-handle] Use postMessage pattern for two-way messaging. (#69)

jan-ivar has just created a new issue for https://github.com/w3c/mediacapture-handle:

== Use postMessage pattern for two-way messaging. ==
We need a _"[a rudimentary messaging API](https://w3c.github.io/mediacapture-handle/identity/index.html#use-case-1)"_ to overcome storage partitioning. We also need to stop reinventing postMessage in #11 and #68. I'm proposing postMessage-shaped APIs for both directions:
1. **capturer ← capturee**: Replace the cross-origin info-surfacing "handle" and "permittedOrigins" which [reinvent postMessage](https://github.com/w3c/mediacapture-handle/issues/11)
2. **capturer → capturee**: A one-way postMessage that takes transferables (like e.g. a port!)

### What is postMessage?

It's the web's API pattern for cross-origin communications. All APIs that expose information to realms of other origins have this shape today, except for this spec.

It's a pattern, because there's no single postMessage, but three:

- (one-to-one) [MessageChannel](https://html.spec.whatwg.org/#messagechannel)
- (one-to-many) [BroadcastChannel](https://html.spec.whatwg.org/#broadcastchannel) but same-origin (no transferables)
- (one-to-any) [window.postMessage](https://html.spec.whatwg.org/multipage/web-messaging.html#dom-window-postmessage-options-dev) with targetOrigin

But none of them fit exactly, because...

### The capture comms problem is unique

There can be more than one capturer, and we'd like the capturee to remain unaware unless contacted. A fourth type, a mix of the last two, seems needed: a cross-origin broadcast-like channel.

Capturees also need to communicate _ahead_ of capture. This led to the current API which acts like publishing ahead of capture, and like postMessage during capture. But a postMessage shape can solve this too.

### The proposed API

A _capturee_ would have a `mediaDevices.capturer.postMessage(msg, "*")` that broadcasts to all capturers. Since it doesn't take  transferables, all messages are clonable, so it _caches the last message posted, and surfaces it on future capturers!_ — This lets the capturee surface whatever info it likes (ids, handles, crop targets) to present _and_ future capturers. Both present and future capturers are also updated the same way (by posting a new message).

The _capturer_ can send messages directly to the capturee. With this, exchanging a 1-1 port becomes trivial:
// capturee
navigator.mediaDevices.capturer.postMessage(msg, "*");
navigator.mediaDevices.capturer.onmessage = e => recognize(e.origin) && oneOn1Port = e.port;

// capturer
captureController.onmessage = e => {
  if (recognize(e.origin)) {
    const {port1, port2} = new MessageChannel();
    oneOn1Port = port1;
    captureController.postMessage(port2, {targetOrigin: e.origin, transfer: [port2]});
This new API as shown is on [CaptureController](https://www.w3.org/TR/screen-capture/#dom-capturecontroller), which would also solve https://github.com/w3c/mediacapture-handle/issues/12.

Please view or discuss this issue at https://github.com/w3c/mediacapture-handle/issues/69 using your GitHub account

Sent via github-notify-ml as configured in https://github.com/w3c/github-notify-ml-config

Received on Monday, 7 November 2022 22:20:22 UTC