mirror of
https://github.com/mozilla/gecko-dev.git
synced 2024-12-01 17:23:59 +00:00
Bug 1714082 - Only attach one message listener to devtools workers r=nchevobbe
Previously, a separate listener was added for every message, and all of them were called for every response. Differential Revision: https://phabricator.services.mozilla.com/D115312
This commit is contained in:
parent
abbbf94915
commit
c92df274ed
75
devtools/client/debugger/dist/parser-worker.js
vendored
75
devtools/client/debugger/dist/parser-worker.js
vendored
@ -7750,7 +7750,10 @@ module.exports = networkRequest;
|
||||
* file, You can obtain one at <http://mozilla.org/MPL/2.0/>. */
|
||||
function WorkerDispatcher() {
|
||||
this.msgId = 1;
|
||||
this.worker = null;
|
||||
this.worker = null; // Map of message ids -> promise resolution functions, for dispatching worker responses
|
||||
|
||||
this.pendingCalls = new Map();
|
||||
this._onMessage = this._onMessage.bind(this);
|
||||
}
|
||||
|
||||
WorkerDispatcher.prototype = {
|
||||
@ -7760,6 +7763,8 @@ WorkerDispatcher.prototype = {
|
||||
this.worker.onerror = err => {
|
||||
console.error(`Error in worker ${url}`, err.message);
|
||||
};
|
||||
|
||||
this.worker.addEventListener("message", this._onMessage);
|
||||
},
|
||||
|
||||
stop() {
|
||||
@ -7767,8 +7772,10 @@ WorkerDispatcher.prototype = {
|
||||
return;
|
||||
}
|
||||
|
||||
this.worker.removeEventListener("message", this._onMessage);
|
||||
this.worker.terminate();
|
||||
this.worker = null;
|
||||
this.pendingCalls.clear();
|
||||
},
|
||||
|
||||
task(method, {
|
||||
@ -7782,7 +7789,11 @@ WorkerDispatcher.prototype = {
|
||||
Promise.resolve().then(flush);
|
||||
}
|
||||
|
||||
calls.push([args, resolve, reject]);
|
||||
calls.push({
|
||||
args,
|
||||
resolve,
|
||||
reject
|
||||
});
|
||||
|
||||
if (!queue) {
|
||||
flush();
|
||||
@ -7802,35 +7813,9 @@ WorkerDispatcher.prototype = {
|
||||
this.worker.postMessage({
|
||||
id,
|
||||
method,
|
||||
calls: items.map(item => item[0])
|
||||
calls: items.map(item => item.args)
|
||||
});
|
||||
|
||||
const listener = ({
|
||||
data: result
|
||||
}) => {
|
||||
if (result.id !== id) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (!this.worker) {
|
||||
return;
|
||||
}
|
||||
|
||||
this.worker.removeEventListener("message", listener);
|
||||
result.results.forEach((resultData, i) => {
|
||||
const [, resolve, reject] = items[i];
|
||||
|
||||
if (resultData.error) {
|
||||
const err = new Error(resultData.message);
|
||||
err.metadata = resultData.metadata;
|
||||
reject(err);
|
||||
} else {
|
||||
resolve(resultData.response);
|
||||
}
|
||||
});
|
||||
};
|
||||
|
||||
this.worker.addEventListener("message", listener);
|
||||
this.pendingCalls.set(id, items);
|
||||
};
|
||||
|
||||
return (...args) => push(args);
|
||||
@ -7838,6 +7823,36 @@ WorkerDispatcher.prototype = {
|
||||
|
||||
invoke(method, ...args) {
|
||||
return this.task(method)(...args);
|
||||
},
|
||||
|
||||
_onMessage({
|
||||
data: result
|
||||
}) {
|
||||
const items = this.pendingCalls.get(result.id);
|
||||
this.pendingCalls.delete(result.id);
|
||||
|
||||
if (!items) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (!this.worker) {
|
||||
return;
|
||||
}
|
||||
|
||||
result.results.forEach((resultData, i) => {
|
||||
const {
|
||||
resolve,
|
||||
reject
|
||||
} = items[i];
|
||||
|
||||
if (resultData.error) {
|
||||
const err = new Error(resultData.message);
|
||||
err.metadata = resultData.metadata;
|
||||
reject(err);
|
||||
} else {
|
||||
resolve(resultData.response);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
};
|
||||
|
@ -559,7 +559,10 @@ module.exports = networkRequest;
|
||||
* file, You can obtain one at <http://mozilla.org/MPL/2.0/>. */
|
||||
function WorkerDispatcher() {
|
||||
this.msgId = 1;
|
||||
this.worker = null;
|
||||
this.worker = null; // Map of message ids -> promise resolution functions, for dispatching worker responses
|
||||
|
||||
this.pendingCalls = new Map();
|
||||
this._onMessage = this._onMessage.bind(this);
|
||||
}
|
||||
|
||||
WorkerDispatcher.prototype = {
|
||||
@ -569,6 +572,8 @@ WorkerDispatcher.prototype = {
|
||||
this.worker.onerror = err => {
|
||||
console.error(`Error in worker ${url}`, err.message);
|
||||
};
|
||||
|
||||
this.worker.addEventListener("message", this._onMessage);
|
||||
},
|
||||
|
||||
stop() {
|
||||
@ -576,8 +581,10 @@ WorkerDispatcher.prototype = {
|
||||
return;
|
||||
}
|
||||
|
||||
this.worker.removeEventListener("message", this._onMessage);
|
||||
this.worker.terminate();
|
||||
this.worker = null;
|
||||
this.pendingCalls.clear();
|
||||
},
|
||||
|
||||
task(method, {
|
||||
@ -591,7 +598,11 @@ WorkerDispatcher.prototype = {
|
||||
Promise.resolve().then(flush);
|
||||
}
|
||||
|
||||
calls.push([args, resolve, reject]);
|
||||
calls.push({
|
||||
args,
|
||||
resolve,
|
||||
reject
|
||||
});
|
||||
|
||||
if (!queue) {
|
||||
flush();
|
||||
@ -611,35 +622,9 @@ WorkerDispatcher.prototype = {
|
||||
this.worker.postMessage({
|
||||
id,
|
||||
method,
|
||||
calls: items.map(item => item[0])
|
||||
calls: items.map(item => item.args)
|
||||
});
|
||||
|
||||
const listener = ({
|
||||
data: result
|
||||
}) => {
|
||||
if (result.id !== id) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (!this.worker) {
|
||||
return;
|
||||
}
|
||||
|
||||
this.worker.removeEventListener("message", listener);
|
||||
result.results.forEach((resultData, i) => {
|
||||
const [, resolve, reject] = items[i];
|
||||
|
||||
if (resultData.error) {
|
||||
const err = new Error(resultData.message);
|
||||
err.metadata = resultData.metadata;
|
||||
reject(err);
|
||||
} else {
|
||||
resolve(resultData.response);
|
||||
}
|
||||
});
|
||||
};
|
||||
|
||||
this.worker.addEventListener("message", listener);
|
||||
this.pendingCalls.set(id, items);
|
||||
};
|
||||
|
||||
return (...args) => push(args);
|
||||
@ -647,6 +632,36 @@ WorkerDispatcher.prototype = {
|
||||
|
||||
invoke(method, ...args) {
|
||||
return this.task(method)(...args);
|
||||
},
|
||||
|
||||
_onMessage({
|
||||
data: result
|
||||
}) {
|
||||
const items = this.pendingCalls.get(result.id);
|
||||
this.pendingCalls.delete(result.id);
|
||||
|
||||
if (!items) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (!this.worker) {
|
||||
return;
|
||||
}
|
||||
|
||||
result.results.forEach((resultData, i) => {
|
||||
const {
|
||||
resolve,
|
||||
reject
|
||||
} = items[i];
|
||||
|
||||
if (resultData.error) {
|
||||
const err = new Error(resultData.message);
|
||||
err.metadata = resultData.metadata;
|
||||
reject(err);
|
||||
} else {
|
||||
resolve(resultData.response);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
};
|
||||
|
75
devtools/client/debugger/dist/search-worker.js
vendored
75
devtools/client/debugger/dist/search-worker.js
vendored
@ -220,7 +220,10 @@ module.exports = networkRequest;
|
||||
* file, You can obtain one at <http://mozilla.org/MPL/2.0/>. */
|
||||
function WorkerDispatcher() {
|
||||
this.msgId = 1;
|
||||
this.worker = null;
|
||||
this.worker = null; // Map of message ids -> promise resolution functions, for dispatching worker responses
|
||||
|
||||
this.pendingCalls = new Map();
|
||||
this._onMessage = this._onMessage.bind(this);
|
||||
}
|
||||
|
||||
WorkerDispatcher.prototype = {
|
||||
@ -230,6 +233,8 @@ WorkerDispatcher.prototype = {
|
||||
this.worker.onerror = err => {
|
||||
console.error(`Error in worker ${url}`, err.message);
|
||||
};
|
||||
|
||||
this.worker.addEventListener("message", this._onMessage);
|
||||
},
|
||||
|
||||
stop() {
|
||||
@ -237,8 +242,10 @@ WorkerDispatcher.prototype = {
|
||||
return;
|
||||
}
|
||||
|
||||
this.worker.removeEventListener("message", this._onMessage);
|
||||
this.worker.terminate();
|
||||
this.worker = null;
|
||||
this.pendingCalls.clear();
|
||||
},
|
||||
|
||||
task(method, {
|
||||
@ -252,7 +259,11 @@ WorkerDispatcher.prototype = {
|
||||
Promise.resolve().then(flush);
|
||||
}
|
||||
|
||||
calls.push([args, resolve, reject]);
|
||||
calls.push({
|
||||
args,
|
||||
resolve,
|
||||
reject
|
||||
});
|
||||
|
||||
if (!queue) {
|
||||
flush();
|
||||
@ -272,35 +283,9 @@ WorkerDispatcher.prototype = {
|
||||
this.worker.postMessage({
|
||||
id,
|
||||
method,
|
||||
calls: items.map(item => item[0])
|
||||
calls: items.map(item => item.args)
|
||||
});
|
||||
|
||||
const listener = ({
|
||||
data: result
|
||||
}) => {
|
||||
if (result.id !== id) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (!this.worker) {
|
||||
return;
|
||||
}
|
||||
|
||||
this.worker.removeEventListener("message", listener);
|
||||
result.results.forEach((resultData, i) => {
|
||||
const [, resolve, reject] = items[i];
|
||||
|
||||
if (resultData.error) {
|
||||
const err = new Error(resultData.message);
|
||||
err.metadata = resultData.metadata;
|
||||
reject(err);
|
||||
} else {
|
||||
resolve(resultData.response);
|
||||
}
|
||||
});
|
||||
};
|
||||
|
||||
this.worker.addEventListener("message", listener);
|
||||
this.pendingCalls.set(id, items);
|
||||
};
|
||||
|
||||
return (...args) => push(args);
|
||||
@ -308,6 +293,36 @@ WorkerDispatcher.prototype = {
|
||||
|
||||
invoke(method, ...args) {
|
||||
return this.task(method)(...args);
|
||||
},
|
||||
|
||||
_onMessage({
|
||||
data: result
|
||||
}) {
|
||||
const items = this.pendingCalls.get(result.id);
|
||||
this.pendingCalls.delete(result.id);
|
||||
|
||||
if (!items) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (!this.worker) {
|
||||
return;
|
||||
}
|
||||
|
||||
result.results.forEach((resultData, i) => {
|
||||
const {
|
||||
resolve,
|
||||
reject
|
||||
} = items[i];
|
||||
|
||||
if (resultData.error) {
|
||||
const err = new Error(resultData.message);
|
||||
err.metadata = resultData.metadata;
|
||||
reject(err);
|
||||
} else {
|
||||
resolve(resultData.response);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
};
|
||||
|
75
devtools/client/debugger/dist/vendors.js
vendored
75
devtools/client/debugger/dist/vendors.js
vendored
@ -156,7 +156,10 @@ module.exports = networkRequest;
|
||||
* file, You can obtain one at <http://mozilla.org/MPL/2.0/>. */
|
||||
function WorkerDispatcher() {
|
||||
this.msgId = 1;
|
||||
this.worker = null;
|
||||
this.worker = null; // Map of message ids -> promise resolution functions, for dispatching worker responses
|
||||
|
||||
this.pendingCalls = new Map();
|
||||
this._onMessage = this._onMessage.bind(this);
|
||||
}
|
||||
|
||||
WorkerDispatcher.prototype = {
|
||||
@ -166,6 +169,8 @@ WorkerDispatcher.prototype = {
|
||||
this.worker.onerror = err => {
|
||||
console.error(`Error in worker ${url}`, err.message);
|
||||
};
|
||||
|
||||
this.worker.addEventListener("message", this._onMessage);
|
||||
},
|
||||
|
||||
stop() {
|
||||
@ -173,8 +178,10 @@ WorkerDispatcher.prototype = {
|
||||
return;
|
||||
}
|
||||
|
||||
this.worker.removeEventListener("message", this._onMessage);
|
||||
this.worker.terminate();
|
||||
this.worker = null;
|
||||
this.pendingCalls.clear();
|
||||
},
|
||||
|
||||
task(method, {
|
||||
@ -188,7 +195,11 @@ WorkerDispatcher.prototype = {
|
||||
Promise.resolve().then(flush);
|
||||
}
|
||||
|
||||
calls.push([args, resolve, reject]);
|
||||
calls.push({
|
||||
args,
|
||||
resolve,
|
||||
reject
|
||||
});
|
||||
|
||||
if (!queue) {
|
||||
flush();
|
||||
@ -208,35 +219,9 @@ WorkerDispatcher.prototype = {
|
||||
this.worker.postMessage({
|
||||
id,
|
||||
method,
|
||||
calls: items.map(item => item[0])
|
||||
calls: items.map(item => item.args)
|
||||
});
|
||||
|
||||
const listener = ({
|
||||
data: result
|
||||
}) => {
|
||||
if (result.id !== id) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (!this.worker) {
|
||||
return;
|
||||
}
|
||||
|
||||
this.worker.removeEventListener("message", listener);
|
||||
result.results.forEach((resultData, i) => {
|
||||
const [, resolve, reject] = items[i];
|
||||
|
||||
if (resultData.error) {
|
||||
const err = new Error(resultData.message);
|
||||
err.metadata = resultData.metadata;
|
||||
reject(err);
|
||||
} else {
|
||||
resolve(resultData.response);
|
||||
}
|
||||
});
|
||||
};
|
||||
|
||||
this.worker.addEventListener("message", listener);
|
||||
this.pendingCalls.set(id, items);
|
||||
};
|
||||
|
||||
return (...args) => push(args);
|
||||
@ -244,6 +229,36 @@ WorkerDispatcher.prototype = {
|
||||
|
||||
invoke(method, ...args) {
|
||||
return this.task(method)(...args);
|
||||
},
|
||||
|
||||
_onMessage({
|
||||
data: result
|
||||
}) {
|
||||
const items = this.pendingCalls.get(result.id);
|
||||
this.pendingCalls.delete(result.id);
|
||||
|
||||
if (!items) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (!this.worker) {
|
||||
return;
|
||||
}
|
||||
|
||||
result.results.forEach((resultData, i) => {
|
||||
const {
|
||||
resolve,
|
||||
reject
|
||||
} = items[i];
|
||||
|
||||
if (resultData.error) {
|
||||
const err = new Error(resultData.message);
|
||||
err.metadata = resultData.metadata;
|
||||
reject(err);
|
||||
} else {
|
||||
resolve(resultData.response);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
};
|
||||
|
@ -7,7 +7,9 @@ const { WorkerDispatcher, workerHandler } = require("../worker-utils");
|
||||
describe("worker utils", () => {
|
||||
it("starts a worker", () => {
|
||||
const dispatcher = new WorkerDispatcher();
|
||||
global.Worker = jest.fn();
|
||||
global.Worker = jest.fn(function() {
|
||||
this.addEventListener = jest.fn();
|
||||
});
|
||||
dispatcher.start("foo");
|
||||
expect(dispatcher.worker).toEqual(global.Worker.mock.instances[0]);
|
||||
});
|
||||
@ -17,6 +19,8 @@ describe("worker utils", () => {
|
||||
const terminateMock = jest.fn();
|
||||
|
||||
global.Worker = jest.fn(() => ({
|
||||
addEventListener: jest.fn(),
|
||||
removeEventListener: jest.fn(),
|
||||
terminate: terminateMock,
|
||||
}));
|
||||
|
||||
|
@ -5,6 +5,9 @@
|
||||
function WorkerDispatcher() {
|
||||
this.msgId = 1;
|
||||
this.worker = null;
|
||||
// Map of message ids -> promise resolution functions, for dispatching worker responses
|
||||
this.pendingCalls = new Map();
|
||||
this._onMessage = this._onMessage.bind(this);
|
||||
}
|
||||
|
||||
WorkerDispatcher.prototype = {
|
||||
@ -13,6 +16,7 @@ WorkerDispatcher.prototype = {
|
||||
this.worker.onerror = err => {
|
||||
console.error(`Error in worker ${url}`, err.message);
|
||||
};
|
||||
this.worker.addEventListener("message", this._onMessage);
|
||||
},
|
||||
|
||||
stop() {
|
||||
@ -20,8 +24,10 @@ WorkerDispatcher.prototype = {
|
||||
return;
|
||||
}
|
||||
|
||||
this.worker.removeEventListener("message", this._onMessage);
|
||||
this.worker.terminate();
|
||||
this.worker = null;
|
||||
this.pendingCalls.clear();
|
||||
},
|
||||
|
||||
task(method, { queue = false } = {}) {
|
||||
@ -32,7 +38,7 @@ WorkerDispatcher.prototype = {
|
||||
Promise.resolve().then(flush);
|
||||
}
|
||||
|
||||
calls.push([args, resolve, reject]);
|
||||
calls.push({ args, resolve, reject });
|
||||
|
||||
if (!queue) {
|
||||
flush();
|
||||
@ -52,34 +58,10 @@ WorkerDispatcher.prototype = {
|
||||
this.worker.postMessage({
|
||||
id,
|
||||
method,
|
||||
calls: items.map(item => item[0]),
|
||||
calls: items.map(item => item.args),
|
||||
});
|
||||
|
||||
const listener = ({ data: result }) => {
|
||||
if (result.id !== id) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (!this.worker) {
|
||||
return;
|
||||
}
|
||||
|
||||
this.worker.removeEventListener("message", listener);
|
||||
|
||||
result.results.forEach((resultData, i) => {
|
||||
const [, resolve, reject] = items[i];
|
||||
|
||||
if (resultData.error) {
|
||||
const err = new Error(resultData.message);
|
||||
err.metadata = resultData.metadata;
|
||||
reject(err);
|
||||
} else {
|
||||
resolve(resultData.response);
|
||||
}
|
||||
});
|
||||
};
|
||||
|
||||
this.worker.addEventListener("message", listener);
|
||||
this.pendingCalls.set(id, items);
|
||||
};
|
||||
|
||||
return (...args) => push(args);
|
||||
@ -88,6 +70,30 @@ WorkerDispatcher.prototype = {
|
||||
invoke(method, ...args) {
|
||||
return this.task(method)(...args);
|
||||
},
|
||||
|
||||
_onMessage({ data: result }) {
|
||||
const items = this.pendingCalls.get(result.id);
|
||||
this.pendingCalls.delete(result.id);
|
||||
if (!items) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (!this.worker) {
|
||||
return;
|
||||
}
|
||||
|
||||
result.results.forEach((resultData, i) => {
|
||||
const { resolve, reject } = items[i];
|
||||
|
||||
if (resultData.error) {
|
||||
const err = new Error(resultData.message);
|
||||
err.metadata = resultData.metadata;
|
||||
reject(err);
|
||||
} else {
|
||||
resolve(resultData.response);
|
||||
}
|
||||
});
|
||||
},
|
||||
};
|
||||
|
||||
function workerHandler(publicInterface) {
|
||||
|
@ -135,7 +135,10 @@ module.exports = networkRequest;
|
||||
* file, You can obtain one at <http://mozilla.org/MPL/2.0/>. */
|
||||
function WorkerDispatcher() {
|
||||
this.msgId = 1;
|
||||
this.worker = null;
|
||||
this.worker = null; // Map of message ids -> promise resolution functions, for dispatching worker responses
|
||||
|
||||
this.pendingCalls = new Map();
|
||||
this._onMessage = this._onMessage.bind(this);
|
||||
}
|
||||
|
||||
WorkerDispatcher.prototype = {
|
||||
@ -145,6 +148,8 @@ WorkerDispatcher.prototype = {
|
||||
this.worker.onerror = err => {
|
||||
console.error(`Error in worker ${url}`, err.message);
|
||||
};
|
||||
|
||||
this.worker.addEventListener("message", this._onMessage);
|
||||
},
|
||||
|
||||
stop() {
|
||||
@ -152,8 +157,10 @@ WorkerDispatcher.prototype = {
|
||||
return;
|
||||
}
|
||||
|
||||
this.worker.removeEventListener("message", this._onMessage);
|
||||
this.worker.terminate();
|
||||
this.worker = null;
|
||||
this.pendingCalls.clear();
|
||||
},
|
||||
|
||||
task(method, {
|
||||
@ -167,7 +174,11 @@ WorkerDispatcher.prototype = {
|
||||
Promise.resolve().then(flush);
|
||||
}
|
||||
|
||||
calls.push([args, resolve, reject]);
|
||||
calls.push({
|
||||
args,
|
||||
resolve,
|
||||
reject
|
||||
});
|
||||
|
||||
if (!queue) {
|
||||
flush();
|
||||
@ -187,35 +198,9 @@ WorkerDispatcher.prototype = {
|
||||
this.worker.postMessage({
|
||||
id,
|
||||
method,
|
||||
calls: items.map(item => item[0])
|
||||
calls: items.map(item => item.args)
|
||||
});
|
||||
|
||||
const listener = ({
|
||||
data: result
|
||||
}) => {
|
||||
if (result.id !== id) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (!this.worker) {
|
||||
return;
|
||||
}
|
||||
|
||||
this.worker.removeEventListener("message", listener);
|
||||
result.results.forEach((resultData, i) => {
|
||||
const [, resolve, reject] = items[i];
|
||||
|
||||
if (resultData.error) {
|
||||
const err = new Error(resultData.message);
|
||||
err.metadata = resultData.metadata;
|
||||
reject(err);
|
||||
} else {
|
||||
resolve(resultData.response);
|
||||
}
|
||||
});
|
||||
};
|
||||
|
||||
this.worker.addEventListener("message", listener);
|
||||
this.pendingCalls.set(id, items);
|
||||
};
|
||||
|
||||
return (...args) => push(args);
|
||||
@ -223,6 +208,36 @@ WorkerDispatcher.prototype = {
|
||||
|
||||
invoke(method, ...args) {
|
||||
return this.task(method)(...args);
|
||||
},
|
||||
|
||||
_onMessage({
|
||||
data: result
|
||||
}) {
|
||||
const items = this.pendingCalls.get(result.id);
|
||||
this.pendingCalls.delete(result.id);
|
||||
|
||||
if (!items) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (!this.worker) {
|
||||
return;
|
||||
}
|
||||
|
||||
result.results.forEach((resultData, i) => {
|
||||
const {
|
||||
resolve,
|
||||
reject
|
||||
} = items[i];
|
||||
|
||||
if (resultData.error) {
|
||||
const err = new Error(resultData.message);
|
||||
err.metadata = resultData.metadata;
|
||||
reject(err);
|
||||
} else {
|
||||
resolve(resultData.response);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
};
|
||||
|
@ -183,7 +183,10 @@ module.exports = networkRequest;
|
||||
* file, You can obtain one at <http://mozilla.org/MPL/2.0/>. */
|
||||
function WorkerDispatcher() {
|
||||
this.msgId = 1;
|
||||
this.worker = null;
|
||||
this.worker = null; // Map of message ids -> promise resolution functions, for dispatching worker responses
|
||||
|
||||
this.pendingCalls = new Map();
|
||||
this._onMessage = this._onMessage.bind(this);
|
||||
}
|
||||
|
||||
WorkerDispatcher.prototype = {
|
||||
@ -193,6 +196,8 @@ WorkerDispatcher.prototype = {
|
||||
this.worker.onerror = err => {
|
||||
console.error(`Error in worker ${url}`, err.message);
|
||||
};
|
||||
|
||||
this.worker.addEventListener("message", this._onMessage);
|
||||
},
|
||||
|
||||
stop() {
|
||||
@ -200,8 +205,10 @@ WorkerDispatcher.prototype = {
|
||||
return;
|
||||
}
|
||||
|
||||
this.worker.removeEventListener("message", this._onMessage);
|
||||
this.worker.terminate();
|
||||
this.worker = null;
|
||||
this.pendingCalls.clear();
|
||||
},
|
||||
|
||||
task(method, {
|
||||
@ -215,7 +222,11 @@ WorkerDispatcher.prototype = {
|
||||
Promise.resolve().then(flush);
|
||||
}
|
||||
|
||||
calls.push([args, resolve, reject]);
|
||||
calls.push({
|
||||
args,
|
||||
resolve,
|
||||
reject
|
||||
});
|
||||
|
||||
if (!queue) {
|
||||
flush();
|
||||
@ -235,35 +246,9 @@ WorkerDispatcher.prototype = {
|
||||
this.worker.postMessage({
|
||||
id,
|
||||
method,
|
||||
calls: items.map(item => item[0])
|
||||
calls: items.map(item => item.args)
|
||||
});
|
||||
|
||||
const listener = ({
|
||||
data: result
|
||||
}) => {
|
||||
if (result.id !== id) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (!this.worker) {
|
||||
return;
|
||||
}
|
||||
|
||||
this.worker.removeEventListener("message", listener);
|
||||
result.results.forEach((resultData, i) => {
|
||||
const [, resolve, reject] = items[i];
|
||||
|
||||
if (resultData.error) {
|
||||
const err = new Error(resultData.message);
|
||||
err.metadata = resultData.metadata;
|
||||
reject(err);
|
||||
} else {
|
||||
resolve(resultData.response);
|
||||
}
|
||||
});
|
||||
};
|
||||
|
||||
this.worker.addEventListener("message", listener);
|
||||
this.pendingCalls.set(id, items);
|
||||
};
|
||||
|
||||
return (...args) => push(args);
|
||||
@ -271,6 +256,36 @@ WorkerDispatcher.prototype = {
|
||||
|
||||
invoke(method, ...args) {
|
||||
return this.task(method)(...args);
|
||||
},
|
||||
|
||||
_onMessage({
|
||||
data: result
|
||||
}) {
|
||||
const items = this.pendingCalls.get(result.id);
|
||||
this.pendingCalls.delete(result.id);
|
||||
|
||||
if (!items) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (!this.worker) {
|
||||
return;
|
||||
}
|
||||
|
||||
result.results.forEach((resultData, i) => {
|
||||
const {
|
||||
resolve,
|
||||
reject
|
||||
} = items[i];
|
||||
|
||||
if (resultData.error) {
|
||||
const err = new Error(resultData.message);
|
||||
err.metadata = resultData.metadata;
|
||||
reject(err);
|
||||
} else {
|
||||
resolve(resultData.response);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
};
|
||||
|
Loading…
Reference in New Issue
Block a user