Cleanup additional messages and add messagr types to MessagePort

This commit is contained in:
hensm
2021-04-25 02:49:22 +01:00
committed by Matt Hensman
parent 0c2535ff1e
commit d424637191
9 changed files with 64 additions and 74 deletions

View File

@@ -57,20 +57,20 @@ decodeTransform.on("data", (message: Message) => {
} }
// Receiver selector // Receiver selector
case "bridge:receiverSelector/open": { case "bridge:openReceiverSelector": {
startReceiverSelector(message.data); break; startReceiverSelector(message.data); break;
} }
case "bridge:receiverSelector/close": { case "bridge:closeReceiverSelector": {
stopReceiverSelector(); break; stopReceiverSelector(); break;
} }
// Media server // Media server
case "bridge:mediaServer/start": { case "bridge:startMediaServer": {
const { filePath, port } = message.data; const { filePath, port } = message.data;
startMediaServer(filePath, port); startMediaServer(filePath, port);
break; break;
} }
case "bridge:mediaServer/stop": { case "bridge:stopMediaServer": {
stopMediaServer(); stopMediaServer();
break; break;
} }

View File

@@ -124,23 +124,26 @@ type MessageDefinitions = {
shouldWatchStatus: boolean shouldWatchStatus: boolean
} }
, "bridge:receiverSelector/open": any , "bridge:openReceiverSelector": string
, "bridge:receiverSelector/close": {} , "bridge:closeReceiverSelector": {}
, "bridge:stopReceiverApp": { receiver: Receiver } , "bridge:stopReceiverApp": { receiver: Receiver }
, "bridge:mediaServer/start": {
, "bridge:startMediaServer": {
filePath: string filePath: string
, port: number , port: number
} }
, "bridge:mediaServer/stop": {} , "bridge:stopMediaServer": {}
, "mediaCast:mediaServer/started": {
, "mediaCast:mediaServerStarted": {
mediaPath: string mediaPath: string
, subtitlePaths: string[] , subtitlePaths: string[]
, localAddress: string , localAddress: string
} }
, "mediaCast:mediaServer/stopped": {} , "mediaCast:mediaServerStopped": {}
, "mediaCast:mediaServer/error": {} , "mediaCast:mediaServerError": {}
, "main:serviceUp": Receiver , "main:serviceUp": Receiver
, "main:serviceDown": { id: string } , "main:serviceDown": { id: string }

View File

@@ -57,7 +57,7 @@ export default class NativeReceiverSelector extends ReceiverSelector {
"receiverSelectorCloseIfFocusLost"); "receiverSelectorCloseIfFocusLost");
this.bridgePort.postMessage({ this.bridgePort.postMessage({
subject: "bridge:receiverSelector/open" subject: "bridge:openReceiverSelector"
, data: JSON.stringify({ , data: JSON.stringify({
receivers receivers
, defaultMediaType , defaultMediaType
@@ -93,7 +93,7 @@ export default class NativeReceiverSelector extends ReceiverSelector {
public close (): void { public close (): void {
if (this.bridgePort) { if (this.bridgePort) {
this.bridgePort.postMessage({ this.bridgePort.postMessage({
subject: "bridge:receiverSelector/close" subject: "bridge:closeReceiverSelector"
}); });
} }

View File

@@ -0,0 +1,6 @@
"use strict";
export interface TypedMessagePort<T> extends MessagePort {
postMessage(message: T, transfer: Transferable[]): void;
postMessage(message: T, options?: PostMessageOptions): void;
}

View File

@@ -1,53 +1,27 @@
"use strict"; "use strict";
const portMap = new WeakMap<TypedPort<any>, browser.runtime.Port>();
/** /**
* Allows typed access to a runtime.Port object. * Allows typed access to a runtime.Port object.
*/ */
export class TypedPort<T> { export interface TypedPort<T>
public name: string; extends Omit<browser.runtime.Port
public error?: { message: string }; , "onDisconnect"
public sender?: browser.runtime.MessageSender; | "onMessage"
| "postMessage"> {
constructor (port: browser.runtime.Port) { onDisconnect: {
portMap.set(this, port); addListener (cb: (port: TypedPort<T>) => void): void | Promise<void>
this.name = port.name; , removeListener (cb: (port: TypedPort<T>) => void): void | Promise<void>
, hasListener (cb: (port: TypedPort<T>) => void): boolean
// @ts-ignore , hasListeners (): boolean
this.error = null;
} }
public disconnect () { , onMessage: {
portMap.get(this)?.disconnect(); addListener (cb: (message: T) => void): void | Promise<void>
, removeListener (cb: (message: T) => void): void | Promise<void>
, hasListener (cb: (message: T) => void): boolean
, hasListeners (): boolean
} }
public onDisconnect = { , postMessage (message: T): void
addListener: (cb: (port: TypedPort<T>) => void) => {
portMap.get(this)?.onDisconnect.addListener(cb as any);
}
, removeListener: (cb: (port: TypedPort<T>) => void) => {
portMap.get(this)?.onDisconnect.addListener(cb as any);
}
, hasListener: (cb: (port: TypedPort<T>) => void) => {
return portMap.get(this)?.onDisconnect.hasListener(cb as any)
?? false;
}
};
public onMessage = {
addListener: (cb: (message: T) => void) => {
portMap.get(this)?.onMessage.addListener(cb as any);
}
, removeListener: (cb: (message: T) => void) => {
portMap.get(this)?.onMessage.removeListener(cb as any);
}
, hasListener: (cb: (message: T) => void) => {
return portMap.get(this)?.onMessage.hasListener(cb as any) ?? false;
}
};
public postMessage (message: T) {
portMap.get(this)?.postMessage(message as any);
}
} }

View File

@@ -3,14 +3,14 @@
import logger from "./logger"; import logger from "./logger";
import options from "./options"; import options from "./options";
import { Message } from "../messaging"; import { Message, Port } from "../messaging";
type DisconnectListener = (port: browser.runtime.Port) => void; type DisconnectListener = (port: Port) => void;
type MessageListener = (message: Message) => void; type MessageListener = (message: Message) => void;
function connectNative (application: string) { function connectNative (application: string): Port {
/** /**
* In order to preserve the synchronous API, messages are * In order to preserve the synchronous API, messages are
* queued before either the native messaging host or the * queued before either the native messaging host or the
@@ -34,7 +34,7 @@ function connectNative (application: string) {
const onMessageListeners = new Set<MessageListener>(); const onMessageListeners = new Set<MessageListener>();
// Port proxy API // Port proxy API
const portObject: browser.runtime.Port = { const portObject: Port = {
error: null as any error: null as any
, name: "" , name: ""
@@ -48,6 +48,9 @@ function connectNative (application: string) {
, hasListener (cb: DisconnectListener) { , hasListener (cb: DisconnectListener) {
return onDisconnectListeners.has(cb); return onDisconnectListeners.has(cb);
} }
, hasListeners () {
return onDisconnectListeners.size > 0;
}
} }
, onMessage: { , onMessage: {
addListener (cb: MessageListener) { addListener (cb: MessageListener) {
@@ -59,9 +62,9 @@ function connectNative (application: string) {
, hasListener (cb: MessageListener) { , hasListener (cb: MessageListener) {
return onMessageListeners.has(cb); return onMessageListeners.has(cb);
} }
, hasListeners () {
// Workaround for modified types return onMessageListeners.size > 0;
, hasListeners () { return false; } }
} }
, disconnect () { , disconnect () {

View File

@@ -181,23 +181,26 @@ type AppMessageDefinitions = {
shouldWatchStatus: boolean shouldWatchStatus: boolean
} }
, "bridge:receiverSelector/open": any , "bridge:openReceiverSelector": string
, "bridge:receiverSelector/close": {} , "bridge:closeReceiverSelector": {}
, "bridge:stopReceiverApp": { receiver: Receiver } , "bridge:stopReceiverApp": { receiver: Receiver }
, "bridge:mediaServer/start": {
, "bridge:startMediaServer": {
filePath: string filePath: string
, port: number , port: number
} }
, "bridge:mediaServer/stop": {} , "bridge:stopMediaServer": {}
, "mediaCast:mediaServer/started": {
, "mediaCast:mediaServerStarted": {
mediaPath: string mediaPath: string
, subtitlePaths: string[] , subtitlePaths: string[]
, localAddress: string , localAddress: string
} }
, "mediaCast:mediaServer/stopped": {} , "mediaCast:mediaServerStopped": {}
, "mediaCast:mediaServer/error": {} , "mediaCast:mediaServerError": {}
, "main:serviceUp": Receiver , "main:serviceUp": Receiver
, "main:serviceDown": { id: string } , "main:serviceDown": { id: string }

View File

@@ -15,7 +15,7 @@ function startMediaServer (filePath: string, port: number)
return new Promise((resolve, reject) => { return new Promise((resolve, reject) => {
backgroundPort.postMessage({ backgroundPort.postMessage({
subject: "bridge:mediaServer/start" subject: "bridge:startMediaServer"
, data: { , data: {
filePath: decodeURI(filePath) filePath: decodeURI(filePath)
, port , port
@@ -25,16 +25,16 @@ function startMediaServer (filePath: string, port: number)
backgroundPort.addEventListener("message", function onMessage (ev) { backgroundPort.addEventListener("message", function onMessage (ev) {
const message = ev.data as Message; const message = ev.data as Message;
if (message.subject.startsWith("mediaCast:mediaServer/")) { if (message.subject.startsWith("mediaCast:mediaServer")) {
backgroundPort.removeEventListener("message", onMessage); backgroundPort.removeEventListener("message", onMessage);
} }
switch (message.subject) { switch (message.subject) {
case "mediaCast:mediaServer/started": { case "mediaCast:mediaServerStarted": {
resolve(message.data); resolve(message.data);
break; break;
} }
case "mediaCast:mediaServer/error": { case "mediaCast:mediaServerError": {
reject(); reject();
break; break;
} }

View File

@@ -4,6 +4,7 @@ import * as cast from "./cast";
import { Message } from "../messaging"; import { Message } from "../messaging";
import { BridgeInfo } from "../lib/bridge"; import { BridgeInfo } from "../lib/bridge";
import { TypedMessagePort } from "../lib/TypedMessagePort";
import { onMessage import { onMessage
, onMessageResponse , onMessageResponse
@@ -20,7 +21,7 @@ let initializedBackgroundPort: MessagePort;
* for and emits these messages, and changing that behavior * for and emits these messages, and changing that behavior
* is too messy. * is too messy.
*/ */
export function ensureInit (): Promise<MessagePort> { export function ensureInit (): Promise<TypedMessagePort<Message>> {
return new Promise(async (resolve, reject) => { return new Promise(async (resolve, reject) => {
// If already initialized, just return existing bridge info // If already initialized, just return existing bridge info