fix: return statement is not necessary to execute .then and .catch execution (#16802)

This commit is contained in:
Apeksha Bhosale 2022-09-30 07:01:05 +05:30 committed by GitHub
parent cafb0d37b0
commit a0646bca77
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
9 changed files with 134 additions and 169 deletions

View File

@ -1,6 +1,6 @@
import { ObjectsRegistry } from "../../../../support/Objects/Registry"; import { ObjectsRegistry } from "../../../../support/Objects/Registry";
let agHelper = ObjectsRegistry.AggregateHelper, const agHelper = ObjectsRegistry.AggregateHelper,
ee = ObjectsRegistry.EntityExplorer, ee = ObjectsRegistry.EntityExplorer,
jsEditor = ObjectsRegistry.JSEditor, jsEditor = ObjectsRegistry.JSEditor,
locator = ObjectsRegistry.CommonLocators, locator = ObjectsRegistry.CommonLocators,
@ -10,7 +10,7 @@ let agHelper = ObjectsRegistry.AggregateHelper,
describe("Validate basic Promises", () => { describe("Validate basic Promises", () => {
it("1. Verify storeValue via .then via direct Promises", () => { it("1. Verify storeValue via .then via direct Promises", () => {
let date = new Date().toDateString(); const date = new Date().toDateString();
cy.fixture("promisesBtnDsl").then((val: any) => { cy.fixture("promisesBtnDsl").then((val: any) => {
agHelper.AddDsl(val, locator._spanButton("Submit")); agHelper.AddDsl(val, locator._spanButton("Submit"));
}); });
@ -254,7 +254,7 @@ return InspiringQuotes.run().then((res) => { showAlert("Today's quote for " + us
it("9. Bug 10150: Verify Promise.all via JSObjects", () => { it("9. Bug 10150: Verify Promise.all via JSObjects", () => {
deployMode.NavigateBacktoEditor(); deployMode.NavigateBacktoEditor();
let date = new Date().toDateString(); const date = new Date().toDateString();
cy.fixture("promisesBtnDsl").then((val: any) => { cy.fixture("promisesBtnDsl").then((val: any) => {
agHelper.AddDsl(val, locator._spanButton("Submit")); agHelper.AddDsl(val, locator._spanButton("Submit"));
}); });
@ -337,24 +337,27 @@ showAlert("Wonderful! all apis executed", "success")).catch(() => showAlert("Ple
"{{resetWidget('Input1').then(() => showAlert(Input1.text))}}", "{{resetWidget('Input1').then(() => showAlert(Input1.text))}}",
); );
deployMode.DeployApp(locator._widgetInputSelector("inputwidgetv2")); deployMode.DeployApp(locator._widgetInputSelector("inputwidgetv2"));
agHelper.TypeText(locator._widgetInputSelector("inputwidgetv2"), "Update value") agHelper.TypeText(
locator._widgetInputSelector("inputwidgetv2"),
"Update value",
);
agHelper.ClickButton("Submit"); agHelper.ClickButton("Submit");
agHelper.ValidateToastMessage("Test"); agHelper.ValidateToastMessage("Test");
}); });
//Skipping until this bug this is addressed! it("12. Bug 9782: Verify .then & .catch (show alert should trigger) via JS Objects without return keyword", () => {
it.skip("12. Bug 9782: Verify .then & .catch (show alert should trigger) via JS Objects without return keyword", () => {
deployMode.NavigateBacktoEditor(); deployMode.NavigateBacktoEditor();
cy.fixture("promisesBtnDsl").then((val: any) => { cy.fixture("promisesBtnDsl").then((val: any) => {
agHelper.AddDsl(val); agHelper.AddDsl(val);
}); });
jsEditor.CreateJSObject(`const user = 'You'; jsEditor.CreateJSObject(`const user = 'You';
InspiringQuotes.run().then((res) => { showAlert("Today's quote for " + user + " is " + JSON.stringify(res.quote.body), 'success') }).catch(() => showAlert("Unable to fetch quote for " + user, 'warning'))`); InspiringQuotes.run().then((res) => { showAlert("Today's quote for " + user + " is " + JSON.stringify(res.quote.body), 'success') }).catch(() => showAlert("Unable to fetch quote for " + user, 'warning'))`);
ee.SelectEntityByName("Button1"); ee.SelectEntityByName("Button1", "Widgets");
cy.get("@jsObjName").then((jsObjName) => { cy.get("@jsObjName").then((jsObjName) => {
propPane.EnterJSContext("onClick", "{{" + jsObjName + ".myFun1()}}"); propPane.EnterJSContext("onClick", "{{" + jsObjName + ".myFun1()}}");
}); });
agHelper.ClickButton("Submit"); agHelper.ClickButton("Submit");
agHelper.Sleep(1000);
agHelper agHelper
.GetNAssertContains( .GetNAssertContains(
locator._toastMsg, locator._toastMsg,

View File

@ -251,6 +251,7 @@ export function* evaluateActionBindings(
* worker. Worker will evaluate a block of code and ask the main thread to execute it. The result of this * worker. Worker will evaluate a block of code and ask the main thread to execute it. The result of this
* execution is returned to the worker where it can resolve/reject the current promise. * execution is returned to the worker where it can resolve/reject the current promise.
*/ */
export function* evaluateAndExecuteDynamicTrigger( export function* evaluateAndExecuteDynamicTrigger(
dynamicTrigger: string, dynamicTrigger: string,
eventType: EventType, eventType: EventType,
@ -260,17 +261,23 @@ export function* evaluateAndExecuteDynamicTrigger(
) { ) {
const unEvalTree: DataTree = yield select(getUnevaluatedDataTree); const unEvalTree: DataTree = yield select(getUnevaluatedDataTree);
log.debug({ execute: dynamicTrigger }); log.debug({ execute: dynamicTrigger });
const { isFinishedChannel } = yield call(
const { requestChannel, responseChannel } = yield call(
worker.duplexRequest, worker.duplexRequest,
EVAL_WORKER_ACTIONS.EVAL_TRIGGER, EVAL_WORKER_ACTIONS.EVAL_TRIGGER,
{ dataTree: unEvalTree, dynamicTrigger, callbackData, globalContext }, {
dataTree: unEvalTree,
dynamicTrigger,
callbackData,
globalContext,
},
); );
let keepAlive = true; let keepAlive = true;
while (keepAlive) { while (keepAlive) {
const { requestData } = yield take(requestChannel); const { requestData } = yield take(isFinishedChannel);
log.debug({ requestData, eventType, triggerMeta, dynamicTrigger }); log.debug({ requestData, eventType, triggerMeta, dynamicTrigger });
if (requestData.finished) { if (requestData.finished) {
keepAlive = false; keepAlive = false;
@ -326,20 +333,38 @@ export function* evaluateAndExecuteDynamicTrigger(
); );
} }
// Return value of a promise is returned // Return value of a promise is returned
isFinishedChannel.close();
return result; return result;
} }
yield call(evalErrorHandler, requestData.errors); yield call(evalErrorHandler, requestData.errors);
if (requestData.trigger) { isFinishedChannel.close();
}
}
export function* executeDynamicTriggerRequest(
mainThreadRequestChannel: Channel<any>,
) {
while (true) {
const { mainThreadResponseChannel, requestData, requestId } = yield take(
mainThreadRequestChannel,
);
log.debug({ requestData });
if (requestData?.trigger) {
// if we have found a trigger, we need to execute it and respond back // if we have found a trigger, we need to execute it and respond back
log.debug({ trigger: requestData.trigger }); log.debug({ trigger: requestData.trigger });
yield spawn( yield spawn(
executeTriggerRequestSaga, executeTriggerRequestSaga,
requestId,
requestData, requestData,
eventType, requestData.eventType,
responseChannel, mainThreadResponseChannel,
triggerMeta, requestData.triggerMeta,
); );
} }
if (requestData?.errors) {
yield call(evalErrorHandler, requestData.errors);
}
} }
} }
@ -357,9 +382,10 @@ interface ResponsePayload {
* resolve or reject it with the data the execution has provided * resolve or reject it with the data the execution has provided
*/ */
function* executeTriggerRequestSaga( function* executeTriggerRequestSaga(
requestId: string,
requestData: { trigger: ActionDescription; subRequestId: string }, requestData: { trigger: ActionDescription; subRequestId: string },
eventType: EventType, eventType: EventType,
responseChannel: Channel<unknown>, responseFromExecutionChannel: Channel<unknown>,
triggerMeta: TriggerMeta, triggerMeta: TriggerMeta,
) { ) {
const responsePayload: ResponsePayload = { const responsePayload: ResponsePayload = {
@ -386,8 +412,9 @@ function* executeTriggerRequestSaga(
responsePayload.data.reason = { message: error.message }; responsePayload.data.reason = { message: error.message };
responsePayload.success = false; responsePayload.success = false;
} }
responseChannel.put({ responseFromExecutionChannel.put({
method: EVAL_WORKER_ACTIONS.PROCESS_TRIGGER, method: EVAL_WORKER_ACTIONS.PROCESS_TRIGGER,
requestId: requestId,
...responsePayload, ...responsePayload,
}); });
} }
@ -548,8 +575,11 @@ function getPostEvalActions(
function* evaluationChangeListenerSaga() { function* evaluationChangeListenerSaga() {
// Explicitly shutdown old worker if present // Explicitly shutdown old worker if present
yield call(worker.shutdown); yield call(worker.shutdown);
yield call(worker.start); const { mainThreadRequestChannel } = yield call(worker.start);
yield call(worker.request, EVAL_WORKER_ACTIONS.SETUP); yield call(worker.request, EVAL_WORKER_ACTIONS.SETUP);
yield spawn(executeDynamicTriggerRequest, mainThreadRequestChannel);
widgetTypeConfigMap = WidgetFactory.getWidgetTypeConfigMap(); widgetTypeConfigMap = WidgetFactory.getWidgetTypeConfigMap();
const initAction: { const initAction: {
postEvalActions: Array<ReduxAction<unknown>>; postEvalActions: Array<ReduxAction<unknown>>;

View File

@ -228,8 +228,7 @@ describe("GracefulWorkerService", () => {
requestData, requestData,
); );
const handlers = await duplexRequest.toPromise(); const handlers = await duplexRequest.toPromise();
expect(handlers).toHaveProperty("requestChannel"); expect(handlers).toHaveProperty("isFinishedChannel");
expect(handlers).toHaveProperty("responseChannel");
expect(MockWorker.instance.postMessage).toBeCalledWith({ expect(MockWorker.instance.postMessage).toBeCalledWith({
method, method,
requestData, requestData,
@ -237,54 +236,6 @@ describe("GracefulWorkerService", () => {
}); });
}); });
test("duplex request channel handler", async () => {
const w = new GracefulWorkerService(MockWorker);
await runSaga({}, w.start);
const mockChannel = (name = "mock") => ({
name,
take: jest.fn(),
put: jest.fn(),
flush: jest.fn(),
close: jest.fn(),
});
const workerChannel = channel();
const mockRequestChannel = mockChannel("request");
const mockResponseChannel = mockChannel("response");
runSaga(
{},
// @ts-expect-error: type mismatch
w.duplexRequestHandler,
workerChannel,
mockRequestChannel,
mockResponseChannel,
);
let randomRequestCount = Math.floor(Math.random() * 10);
for (randomRequestCount; randomRequestCount > 0; randomRequestCount--) {
workerChannel.put({
responseData: {
test: randomRequestCount,
},
});
expect(mockRequestChannel.put).toBeCalledWith({
requestData: {
test: randomRequestCount,
},
});
}
workerChannel.put({
responseData: {
finished: true,
},
});
expect(mockResponseChannel.put).toBeCalledWith({ finished: true });
expect(mockRequestChannel.close).toBeCalled();
});
test("duplex response channel handler", async () => { test("duplex response channel handler", async () => {
const w = new GracefulWorkerService(MockWorker); const w = new GracefulWorkerService(MockWorker);
await runSaga({}, w.start); await runSaga({}, w.start);
@ -294,42 +245,27 @@ describe("GracefulWorkerService", () => {
expect(MockWorker.instance).toBeDefined(); expect(MockWorker.instance).toBeDefined();
return; return;
} }
const mockChannel = (name = "mock") => ({ const mainThreadResponseChannel = channel();
name,
take: jest.fn(),
put: jest.fn(),
flush: jest.fn(),
close: jest.fn(),
});
const mockWorkerChannel = mockChannel("worker");
const responseChannel = channel();
const workerRequestId = "testID"; const workerRequestId = "testID";
runSaga( runSaga(
{}, {},
// @ts-expect-error: type mismatch // @ts-expect-error: type mismatch
w.duplexResponseHandler, w.duplexResponseHandler,
workerRequestId, mainThreadResponseChannel,
mockWorkerChannel,
responseChannel,
); );
MockWorker.instance.postMessage = jest.fn(); MockWorker.instance.postMessage = jest.fn();
let randomRequestCount = Math.floor(Math.random() * 10); let randomRequestCount = Math.floor(Math.random() * 10);
for (randomRequestCount; randomRequestCount > 0; randomRequestCount--) { for (randomRequestCount; randomRequestCount > 0; randomRequestCount--) {
responseChannel.put({ mainThreadResponseChannel.put({
test: randomRequestCount, test: randomRequestCount,
requestId: workerRequestId,
}); });
expect(MockWorker.instance.postMessage).toBeCalledWith({ expect(MockWorker.instance.postMessage).toBeCalledWith({
test: randomRequestCount, test: randomRequestCount,
requestId: workerRequestId, requestId: workerRequestId,
}); });
} }
responseChannel.put({
finished: true,
});
expect(mockWorkerChannel.close).toBeCalled();
}); });
}); });

View File

@ -3,6 +3,7 @@ import { channel, Channel, buffers } from "redux-saga";
import _ from "lodash"; import _ from "lodash";
import log from "loglevel"; import log from "loglevel";
import WebpackWorker from "worker-loader!"; import WebpackWorker from "worker-loader!";
// import { executeDynamicTriggerRequest } from "sagas/EvaluationsSaga";
/** /**
* Wrap a webworker to provide a synchronous request-response semantic. * Wrap a webworker to provide a synchronous request-response semantic.
* *
@ -50,13 +51,15 @@ export class GracefulWorkerService {
private readonly _workerClass: typeof WebpackWorker; private readonly _workerClass: typeof WebpackWorker;
public mainThreadRequestChannel: Channel<any>;
public mainThreadResponseChannel: Channel<any>;
constructor(workerClass: typeof WebpackWorker) { constructor(workerClass: typeof WebpackWorker) {
this.shutdown = this.shutdown.bind(this); this.shutdown = this.shutdown.bind(this);
this.start = this.start.bind(this); this.start = this.start.bind(this);
this.request = this.request.bind(this); this.request = this.request.bind(this);
this._broker = this._broker.bind(this); this._broker = this._broker.bind(this);
this.duplexRequest = this.duplexRequest.bind(this); this.duplexRequest = this.duplexRequest.bind(this);
this.duplexRequestHandler = this.duplexRequestHandler.bind(this);
this.duplexResponseHandler = this.duplexResponseHandler.bind(this); this.duplexResponseHandler = this.duplexResponseHandler.bind(this);
// Do not buffer messages on this channel // Do not buffer messages on this channel
@ -64,6 +67,8 @@ export class GracefulWorkerService {
this._isReady = false; this._isReady = false;
this._channels = new Map<string, Channel<any>>(); this._channels = new Map<string, Channel<any>>();
this._workerClass = workerClass; this._workerClass = workerClass;
this.mainThreadRequestChannel = channel();
this.mainThreadResponseChannel = channel();
} }
/** /**
@ -77,6 +82,10 @@ export class GracefulWorkerService {
// Inform all pending requests that we're good to go! // Inform all pending requests that we're good to go!
this._isReady = true; this._isReady = true;
yield put(this._readyChan, true); yield put(this._readyChan, true);
yield spawn(this.duplexResponseHandler, this.mainThreadResponseChannel);
return {
mainThreadRequestChannel: this.mainThreadRequestChannel,
};
} }
/** /**
@ -96,6 +105,8 @@ export class GracefulWorkerService {
this._evaluationWorker.removeEventListener("message", this._broker); this._evaluationWorker.removeEventListener("message", this._broker);
this._evaluationWorker.terminate(); this._evaluationWorker.terminate();
this._evaluationWorker = undefined; this._evaluationWorker = undefined;
this.mainThreadRequestChannel.close();
this.mainThreadResponseChannel.close();
} }
/** /**
@ -182,29 +193,8 @@ export class GracefulWorkerService {
const workerRequestId = `${method}__${_.uniqueId()}`; const workerRequestId = `${method}__${_.uniqueId()}`;
// The worker channel is the main channel // The worker channel is the main channel
// where the web worker messages will get posted // where the web worker messages will get posted
const workerChannel = channel(); const isFinishedChannel = channel();
this._channels.set(workerRequestId, workerChannel); this._channels.set(workerRequestId, isFinishedChannel);
// The main thread will listen to the
// request channel where it will get worker messages
const mainThreadRequestChannel = channel();
// The main thread will respond back on the
// response channel which will be relayed to the worker
const mainThreadResponseChannel = channel();
// We spawn both the main thread request and response handler
yield spawn(
this.duplexRequestHandler,
workerChannel,
mainThreadRequestChannel,
mainThreadResponseChannel,
);
yield spawn(
this.duplexResponseHandler,
workerRequestId,
workerChannel,
mainThreadResponseChannel,
);
// And post the first message to the worker // And post the first message to the worker
this._evaluationWorker.postMessage({ this._evaluationWorker.postMessage({
method, method,
@ -214,75 +204,27 @@ export class GracefulWorkerService {
// Returning these channels to the main thread so that they can listen and post on it // Returning these channels to the main thread so that they can listen and post on it
return { return {
responseChannel: mainThreadResponseChannel, isFinishedChannel: isFinishedChannel,
requestChannel: mainThreadRequestChannel,
}; };
} }
*duplexRequestHandler( *duplexResponseHandler(mainThreadResponseChannel: Channel<any>) {
workerChannel: Channel<any>,
requestChannel: Channel<any>,
responseChannel: Channel<any>,
) {
if (!this._evaluationWorker) return; if (!this._evaluationWorker) return;
try { try {
let keepAlive = true; const keepAlive = true;
while (keepAlive) {
// Wait for a message from the worker
const workerResponse: {
responseData: {
finished: unknown;
};
} = yield take(workerChannel);
const { responseData } = workerResponse;
// post that message to the request channel so the main thread can read it
requestChannel.put({ requestData: responseData });
// If we get a finished flag, the worker is requesting to end the request
if (responseData.finished) {
keepAlive = false;
// Relay the finished flag to the response channel as well
responseChannel.put({
finished: true,
});
}
}
} catch (e) {
log.error(e);
} finally {
// Cleanup
requestChannel.close();
}
}
*duplexResponseHandler(
workerRequestId: string,
workerChannel: Channel<any>,
responseChannel: Channel<any>,
) {
if (!this._evaluationWorker) return;
try {
let keepAlive = true;
while (keepAlive) { while (keepAlive) {
// Wait for the main thread to respond back after a request // Wait for the main thread to respond back after a request
const response: { finished: unknown } = yield take(responseChannel); const response: { finished: unknown; requestId: string } = yield take(
// If we get a finished flag, the worker is requesting to end the request mainThreadResponseChannel,
if (response.finished) { );
keepAlive = false;
continue;
}
// send response to worker // send response to worker
this._evaluationWorker.postMessage({ this._evaluationWorker.postMessage({
...response, ...response,
requestId: workerRequestId, requestId: response.requestId,
}); });
} }
} catch (e) { } catch (e) {
log.error(e); log.error(e);
} finally {
// clean up everything
responseChannel.close();
workerChannel.close();
this._channels.delete(workerRequestId);
} }
} }
@ -290,12 +232,28 @@ export class GracefulWorkerService {
if (!event || !event.data) { if (!event || !event.data) {
return; return;
} }
const { requestId, responseData, timeTaken } = event.data; const { promisified, requestId, responseData, timeTaken } = event.data;
const ch = this._channels.get(requestId); const ch = this._channels.get(requestId);
// Channel could have been deleted if the request gets cancelled before the WebWorker can respond. // Channel could have been deleted if the request gets cancelled before the WebWorker can respond.
// In that case, we want to drop the request. // In that case, we want to drop the request.
if (promisified) {
if (responseData.finished) {
if (ch) { if (ch) {
ch.put({ responseData, timeTaken }); ch.put({ requestData: responseData, timeTaken, requestId });
this._channels.delete(requestId);
}
} else {
this.mainThreadRequestChannel.put({
requestData: responseData,
timeTaken,
requestId,
mainThreadResponseChannel: this.mainThreadResponseChannel,
});
}
} else {
if (ch) {
ch.put({ responseData, timeTaken, requestId });
}
} }
} }
} }

View File

@ -122,6 +122,7 @@ describe("Add functions", () => {
expect(workerEventMock).lastCalledWith({ expect(workerEventMock).lastCalledWith({
type: "PROCESS_TRIGGER", type: "PROCESS_TRIGGER",
requestId: "EVAL_TRIGGER", requestId: "EVAL_TRIGGER",
promisified: true,
responseData: { responseData: {
errors: [], errors: [],
subRequestId: expect.stringContaining("EVAL_TRIGGER_"), subRequestId: expect.stringContaining("EVAL_TRIGGER_"),
@ -142,6 +143,7 @@ describe("Add functions", () => {
expect(workerEventMock).lastCalledWith({ expect(workerEventMock).lastCalledWith({
type: "PROCESS_TRIGGER", type: "PROCESS_TRIGGER",
requestId: "EVAL_TRIGGER", requestId: "EVAL_TRIGGER",
promisified: true,
responseData: { responseData: {
errors: [], errors: [],
subRequestId: expect.stringContaining("EVAL_TRIGGER_"), subRequestId: expect.stringContaining("EVAL_TRIGGER_"),
@ -165,6 +167,7 @@ describe("Add functions", () => {
expect(workerEventMock).lastCalledWith({ expect(workerEventMock).lastCalledWith({
type: "PROCESS_TRIGGER", type: "PROCESS_TRIGGER",
requestId: "EVAL_TRIGGER", requestId: "EVAL_TRIGGER",
promisified: true,
responseData: { responseData: {
errors: [], errors: [],
subRequestId: expect.stringContaining("EVAL_TRIGGER_"), subRequestId: expect.stringContaining("EVAL_TRIGGER_"),
@ -183,6 +186,7 @@ describe("Add functions", () => {
expect(workerEventMock).lastCalledWith({ expect(workerEventMock).lastCalledWith({
type: "PROCESS_TRIGGER", type: "PROCESS_TRIGGER",
requestId: "EVAL_TRIGGER", requestId: "EVAL_TRIGGER",
promisified: true,
responseData: { responseData: {
errors: [], errors: [],
subRequestId: expect.stringContaining("EVAL_TRIGGER_"), subRequestId: expect.stringContaining("EVAL_TRIGGER_"),
@ -202,6 +206,7 @@ describe("Add functions", () => {
expect(workerEventMock).lastCalledWith({ expect(workerEventMock).lastCalledWith({
type: "PROCESS_TRIGGER", type: "PROCESS_TRIGGER",
requestId: "EVAL_TRIGGER", requestId: "EVAL_TRIGGER",
promisified: true,
responseData: { responseData: {
errors: [], errors: [],
subRequestId: expect.stringContaining("EVAL_TRIGGER_"), subRequestId: expect.stringContaining("EVAL_TRIGGER_"),
@ -227,6 +232,7 @@ describe("Add functions", () => {
expect(workerEventMock).lastCalledWith({ expect(workerEventMock).lastCalledWith({
type: "PROCESS_TRIGGER", type: "PROCESS_TRIGGER",
requestId: "EVAL_TRIGGER", requestId: "EVAL_TRIGGER",
promisified: true,
responseData: { responseData: {
errors: [], errors: [],
subRequestId: expect.stringContaining("EVAL_TRIGGER_"), subRequestId: expect.stringContaining("EVAL_TRIGGER_"),
@ -249,6 +255,7 @@ describe("Add functions", () => {
expect(workerEventMock).lastCalledWith({ expect(workerEventMock).lastCalledWith({
type: "PROCESS_TRIGGER", type: "PROCESS_TRIGGER",
requestId: "EVAL_TRIGGER", requestId: "EVAL_TRIGGER",
promisified: true,
responseData: { responseData: {
errors: [], errors: [],
subRequestId: expect.stringContaining("EVAL_TRIGGER_"), subRequestId: expect.stringContaining("EVAL_TRIGGER_"),
@ -270,6 +277,7 @@ describe("Add functions", () => {
expect(workerEventMock).lastCalledWith({ expect(workerEventMock).lastCalledWith({
type: "PROCESS_TRIGGER", type: "PROCESS_TRIGGER",
requestId: "EVAL_TRIGGER", requestId: "EVAL_TRIGGER",
promisified: true,
responseData: { responseData: {
errors: [], errors: [],
subRequestId: expect.stringContaining("EVAL_TRIGGER_"), subRequestId: expect.stringContaining("EVAL_TRIGGER_"),
@ -289,6 +297,7 @@ describe("Add functions", () => {
expect(workerEventMock).lastCalledWith({ expect(workerEventMock).lastCalledWith({
type: "PROCESS_TRIGGER", type: "PROCESS_TRIGGER",
requestId: "EVAL_TRIGGER", requestId: "EVAL_TRIGGER",
promisified: true,
responseData: { responseData: {
errors: [], errors: [],
subRequestId: expect.stringContaining("EVAL_TRIGGER_"), subRequestId: expect.stringContaining("EVAL_TRIGGER_"),
@ -317,6 +326,7 @@ describe("Add functions", () => {
expect(workerEventMock).lastCalledWith({ expect(workerEventMock).lastCalledWith({
type: "PROCESS_TRIGGER", type: "PROCESS_TRIGGER",
requestId: "EVAL_TRIGGER", requestId: "EVAL_TRIGGER",
promisified: true,
responseData: { responseData: {
errors: [], errors: [],
subRequestId: expect.stringContaining("EVAL_TRIGGER_"), subRequestId: expect.stringContaining("EVAL_TRIGGER_"),
@ -342,6 +352,7 @@ describe("Add functions", () => {
expect(workerEventMock).lastCalledWith({ expect(workerEventMock).lastCalledWith({
type: "PROCESS_TRIGGER", type: "PROCESS_TRIGGER",
requestId: "EVAL_TRIGGER", requestId: "EVAL_TRIGGER",
promisified: true,
responseData: { responseData: {
errors: [], errors: [],
subRequestId: expect.stringContaining("EVAL_TRIGGER_"), subRequestId: expect.stringContaining("EVAL_TRIGGER_"),
@ -363,6 +374,7 @@ describe("Add functions", () => {
expect(workerEventMock).lastCalledWith({ expect(workerEventMock).lastCalledWith({
type: "PROCESS_TRIGGER", type: "PROCESS_TRIGGER",
requestId: "EVAL_TRIGGER", requestId: "EVAL_TRIGGER",
promisified: true,
responseData: { responseData: {
errors: [], errors: [],
subRequestId: expect.stringContaining("EVAL_TRIGGER_"), subRequestId: expect.stringContaining("EVAL_TRIGGER_"),
@ -387,6 +399,7 @@ describe("Add functions", () => {
expect(workerEventMock).lastCalledWith({ expect(workerEventMock).lastCalledWith({
type: "PROCESS_TRIGGER", type: "PROCESS_TRIGGER",
requestId: "EVAL_TRIGGER", requestId: "EVAL_TRIGGER",
promisified: true,
responseData: { responseData: {
errors: [], errors: [],
subRequestId: expect.stringContaining("EVAL_TRIGGER_"), subRequestId: expect.stringContaining("EVAL_TRIGGER_"),

View File

@ -39,6 +39,7 @@ describe("promise execution", () => {
expect(postMessageMock).toBeCalledWith({ expect(postMessageMock).toBeCalledWith({
requestId, requestId,
type: "PROCESS_TRIGGER", type: "PROCESS_TRIGGER",
promisified: true,
responseData: expect.objectContaining({ responseData: expect.objectContaining({
subRequestId: expect.stringContaining(`${requestId}_`), subRequestId: expect.stringContaining(`${requestId}_`),
trigger: { trigger: {
@ -116,6 +117,7 @@ describe("promise execution", () => {
method: "PROCESS_TRIGGER", method: "PROCESS_TRIGGER",
requestId, requestId,
success: true, success: true,
promisified: true,
}, },
}), }),
); );
@ -153,6 +155,7 @@ describe("promise execution", () => {
method: "PROCESS_TRIGGER", method: "PROCESS_TRIGGER",
requestId, requestId,
success: true, success: true,
promisified: true,
}, },
}), }),
); );
@ -164,6 +167,7 @@ describe("promise execution", () => {
method: "PROCESS_TRIGGER", method: "PROCESS_TRIGGER",
requestId, requestId,
success: false, success: false,
promisified: true,
}, },
}), }),
); );

View File

@ -43,6 +43,7 @@ export const promisifyAction = (
type: EVAL_WORKER_ACTIONS.PROCESS_TRIGGER, type: EVAL_WORKER_ACTIONS.PROCESS_TRIGGER,
responseData, responseData,
requestId: workerRequestIdCopy, requestId: workerRequestIdCopy,
promisified: true,
}); });
const processResponse = function(event: MessageEvent) { const processResponse = function(event: MessageEvent) {
const { data, method, requestId, success } = event.data; const { data, method, requestId, success } = event.data;
@ -99,6 +100,7 @@ export const completePromise = (requestId: string, result: EvalResult) => {
result, result,
}, },
requestId, requestId,
promisified: true,
}); });
}; };

View File

@ -195,6 +195,7 @@ describe("evaluateAsync", () => {
await evaluateAsync(js, {}, "TEST_REQUEST", {}); await evaluateAsync(js, {}, "TEST_REQUEST", {});
expect(self.postMessage).toBeCalledWith({ expect(self.postMessage).toBeCalledWith({
requestId: "TEST_REQUEST", requestId: "TEST_REQUEST",
promisified: true,
responseData: { responseData: {
finished: true, finished: true,
result: { errors: [], logs: [], result: 123, triggers: [] }, result: { errors: [], logs: [], result: 123, triggers: [] },
@ -209,6 +210,7 @@ describe("evaluateAsync", () => {
await evaluateAsync(js, {}, "TEST_REQUEST_1", {}); await evaluateAsync(js, {}, "TEST_REQUEST_1", {});
expect(self.postMessage).toBeCalledWith({ expect(self.postMessage).toBeCalledWith({
requestId: "TEST_REQUEST_1", requestId: "TEST_REQUEST_1",
promisified: true,
responseData: { responseData: {
finished: true, finished: true,
result: { result: {

View File

@ -63,6 +63,21 @@ export const EvaluationScripts: Record<EvaluationScriptType, string> = {
`, `,
}; };
const topLevelWorkerAPIs = Object.keys(self).reduce((acc, key: string) => {
acc[key] = true;
return acc;
}, {} as any);
function resetWorkerGlobalScope() {
for (const key of Object.keys(self)) {
if (topLevelWorkerAPIs[key]) continue;
if (key === "evaluationVersion") continue;
if (extraLibraries.find((lib) => lib.accessor === key)) continue;
// @ts-expect-error: Types are not available
delete self[key];
}
}
export const getScriptType = ( export const getScriptType = (
evalArgumentsExist = false, evalArgumentsExist = false,
isTriggerBased = false, isTriggerBased = false,
@ -232,6 +247,7 @@ export default function evaluateSync(
skipLogsOperations = false, skipLogsOperations = false,
): EvalResult { ): EvalResult {
return (function() { return (function() {
resetWorkerGlobalScope();
const errors: EvaluationError[] = []; const errors: EvaluationError[] = [];
let logs: LogObject[] = []; let logs: LogObject[] = [];
let result; let result;
@ -305,6 +321,7 @@ export async function evaluateAsync(
evalArguments?: Array<any>, evalArguments?: Array<any>,
) { ) {
return (async function() { return (async function() {
resetWorkerGlobalScope();
const errors: EvaluationError[] = []; const errors: EvaluationError[] = [];
let result; let result;
let logs; let logs;