From 9daec25d47f927033a005dcef74bcf1407ae4f0c Mon Sep 17 00:00:00 2001 From: Matt Schile Date: Fri, 31 Mar 2023 14:36:53 -0600 Subject: [PATCH 1/8] chore: adding command log to protocol --- packages/app/src/runner/event-manager.ts | 2 + .../reporter/src/attempts/attempt-model.ts | 3 +- .../src/instruments/instrument-model.ts | 3 +- packages/server/lib/cloud/protocol.ts | 24 ++-- packages/server/lib/socket-base.ts | 4 + .../fixtures/cloud/protocol/test-protocol.js | 14 +- .../server/test/unit/cloud/protocol_spec.ts | 126 +++++++++++------- packages/types/src/protocol.ts | 4 + yarn.lock | 7 +- 9 files changed, 113 insertions(+), 74 deletions(-) diff --git a/packages/app/src/runner/event-manager.ts b/packages/app/src/runner/event-manager.ts index e6bbd85e00dc..032fbfb9a0a4 100644 --- a/packages/app/src/runner/event-manager.ts +++ b/packages/app/src/runner/event-manager.ts @@ -492,6 +492,7 @@ export class EventManager { this._interceptStudio(displayProps) this.reporterBus.emit('reporter:log:add', displayProps) + Cypress.backend('protocol:command:log:added', { ...displayProps, timestamp: displayProps.wallClockStartedAt }) }) Cypress.on('log:changed', (log) => { @@ -505,6 +506,7 @@ export class EventManager { this._interceptStudio(displayProps) this.reporterBus.emit('reporter:log:state:changed', displayProps) + Cypress.backend('protocol:command:log:changed', { ...displayProps, timestamp: new Date().toJSON() }) }) // TODO: MOVE BACK INTO useEventManager. Verify this works diff --git a/packages/reporter/src/attempts/attempt-model.ts b/packages/reporter/src/attempts/attempt-model.ts index 5c15dbfdecca..253f807f2192 100644 --- a/packages/reporter/src/attempts/attempt-model.ts +++ b/packages/reporter/src/attempts/attempt-model.ts @@ -107,8 +107,7 @@ export default class Attempt { addLog = (props: LogProps) => { switch (props.instrument) { case 'command': { - // @ts-ignore satisfied by CommandProps - if (props.sessionInfo) { + if ((props as CommandProps).sessionInfo) { this._addSession(props as unknown as SessionProps) // add sessionInstrumentPanel details } diff --git a/packages/reporter/src/instruments/instrument-model.ts b/packages/reporter/src/instruments/instrument-model.ts index 60fb91aa88c0..1b65f3c8aa8e 100644 --- a/packages/reporter/src/instruments/instrument-model.ts +++ b/packages/reporter/src/instruments/instrument-model.ts @@ -16,9 +16,8 @@ export interface InstrumentProps { displayName?: string name?: string message?: string - // agent / route / session - instrument panel log type // parent / child / system - command log type - type?: 'agent' | 'parent' | 'child' | 'system' | 'route' | 'session' + type?: 'parent' | 'child' | 'system' testCurrentRetry?: number state: TestState referencesAlias?: Alias diff --git a/packages/server/lib/cloud/protocol.ts b/packages/server/lib/cloud/protocol.ts index 820a7e387047..4d409edc2e18 100644 --- a/packages/server/lib/cloud/protocol.ts +++ b/packages/server/lib/cloud/protocol.ts @@ -57,8 +57,6 @@ class ProtocolManagerImpl implements ProtocolManager { return } - debug('connecting to browser for new spec') - await this.protocol?.connectToBrowser(cdpClient) } @@ -93,8 +91,6 @@ class ProtocolManagerImpl implements ProtocolManager { return } - debug('after spec') - this.protocol?.afterSpec() } @@ -103,8 +99,6 @@ class ProtocolManagerImpl implements ProtocolManager { return } - debug('before test %O', test) - this.protocol?.beforeTest(test) } @@ -113,10 +107,24 @@ class ProtocolManagerImpl implements ProtocolManager { return } - debug('after test %O', test) - this.protocol?.afterTest(test) } + + commandLogAdded (log: any) { + if (!this.protocolEnabled()) { + return + } + + this.protocol?.commandLogAdded(log) + } + + commandLogChanged (log: any): void { + if (!this.protocolEnabled()) { + return + } + + this.protocol?.commandLogChanged(log) + } } export default ProtocolManagerImpl diff --git a/packages/server/lib/socket-base.ts b/packages/server/lib/socket-base.ts index ea331d8d6151..0ec01ccaeff1 100644 --- a/packages/server/lib/socket-base.ts +++ b/packages/server/lib/socket-base.ts @@ -460,6 +460,10 @@ export class SocketBase { return this.protocolManager?.beforeTest(args[0]) case 'protocol:test:after:run': return this.protocolManager?.afterTest(args[0]) + case 'protocol:command:log:added': + return this.protocolManager?.commandLogAdded(args[0]) + case 'protocol:command:log:changed': + return this.protocolManager?.commandLogChanged(args[0]) default: throw new Error(`You requested a backend event we cannot handle: ${eventName}`) } diff --git a/packages/server/test/support/fixtures/cloud/protocol/test-protocol.js b/packages/server/test/support/fixtures/cloud/protocol/test-protocol.js index 029e4ed44615..1017e082150c 100644 --- a/packages/server/test/support/fixtures/cloud/protocol/test-protocol.js +++ b/packages/server/test/support/fixtures/cloud/protocol/test-protocol.js @@ -9,23 +9,19 @@ const AppCaptureProtocol = class { this.beforeSpec = this.beforeSpec.bind(this) this.afterSpec = this.afterSpec.bind(this) this.beforeTest = this.beforeTest.bind(this) + this.commandLogAdded = this.commandLogAdded.bind(this) + this.commandLogChanged = this.commandLogChanged.bind(this) } - connectToBrowser ({ - target, - host, - port, - }) { + connectToBrowser (cdpClient) { return Promise.resolve() } - addRunnables (runnables) {} - beforeSpec (spec) {} - afterSpec (spec) {} - beforeTest (test) {} + commandLogAdded (log) {} + commandLogChanged (log) {} } module.exports = { diff --git a/packages/server/test/unit/cloud/protocol_spec.ts b/packages/server/test/unit/cloud/protocol_spec.ts index 0cddcc340b71..87670b83ff7b 100644 --- a/packages/server/test/unit/cloud/protocol_spec.ts +++ b/packages/server/test/unit/cloud/protocol_spec.ts @@ -1,6 +1,7 @@ import { proxyquire } from '../../spec_helper' import path from 'path' import os from 'os' +import type { AppCaptureProtocolInterface, ProtocolManager as ProtocolManagerInterface } from '@packages/types' const mockDb = sinon.stub() const mockDatabase = sinon.stub().returns(mockDb) @@ -10,8 +11,17 @@ const { default: ProtocolManager } = proxyquire('../lib/cloud/protocol', { }) describe('lib/cloud/protocol', () => { - beforeEach(() => { + let protocolManager: ProtocolManagerInterface + let protocol: AppCaptureProtocolInterface + + beforeEach(async () => { process.env.CYPRESS_LOCAL_PROTOCOL_PATH = path.join(__dirname, '..', '..', 'support', 'fixtures', 'cloud', 'protocol', 'test-protocol.js') + + const protocolManager = new ProtocolManager() + + await protocolManager.setupProtocol() + + protocol = (protocolManager as any).protocol }) afterEach(() => { @@ -19,45 +29,21 @@ describe('lib/cloud/protocol', () => { }) it('should be able to setup the protocol', async () => { - const protocolManager = new ProtocolManager() - - await protocolManager.setupProtocol() - - const protocol = (protocolManager as any).protocol - expect(protocolManager.protocolEnabled()).to.be.true - expect(protocol.Debug).not.to.be.undefined + expect((protocol as any).Debug).not.to.be.undefined }) it('should be able to connect to the browser', async () => { - const protocolManager = new ProtocolManager() - - await protocolManager.setupProtocol() - - const protocol = (protocolManager as any).protocol + const mockCdpClient = sinon.stub() sinon.stub(protocol, 'connectToBrowser').resolves() - await protocolManager.connectToBrowser({ - target: 'target', - host: 'host', - port: 1234, - }) + await protocolManager.connectToBrowser(mockCdpClient as any) - expect(protocol.connectToBrowser).to.be.calledWith({ - target: 'target', - host: 'host', - port: 1234, - }) + expect(protocol.connectToBrowser).to.be.calledWith(mockCdpClient) }) it('should be able to initialize a new spec', async () => { - const protocolManager = new ProtocolManager() - - await protocolManager.setupProtocol() - - const protocol = (protocolManager as any).protocol - sinon.stub(protocol, 'beforeSpec') protocolManager.beforeSpec({ @@ -72,12 +58,6 @@ describe('lib/cloud/protocol', () => { }) it('should be able to initialize a new test', async () => { - const protocolManager = new ProtocolManager() - - await protocolManager.setupProtocol() - - const protocol = (protocolManager as any).protocol - sinon.stub(protocol, 'beforeTest') protocolManager.beforeTest({ @@ -94,12 +74,6 @@ describe('lib/cloud/protocol', () => { }) it('should be able to clean up after a spec', async () => { - const protocolManager = new ProtocolManager() - - await protocolManager.setupProtocol() - - const protocol = (protocolManager as any).protocol - sinon.stub(protocol, 'afterSpec') protocolManager.afterSpec() @@ -108,12 +82,6 @@ describe('lib/cloud/protocol', () => { }) it('should be able to add runnables', async () => { - const protocolManager = new ProtocolManager() - - await protocolManager.setupProtocol() - - const protocol = (protocolManager as any).protocol - sinon.stub(protocol, 'addRunnables') const rootRunnable = { @@ -135,4 +103,68 @@ describe('lib/cloud/protocol', () => { expect(protocol.addRunnables).to.be.calledWith(rootRunnable) }) + + it('should be able to add a command log', async () => { + sinon.stub(protocol, 'commandLogAdded') + + const log = { + id: 'log-https://example.cypress.io-17', + alias: 'getComment', + aliasType: 'route', + displayName: 'xhr', + event: true, + hookId: 'r4', + instrument: 'command', + message: '', + method: 'GET', + name: 'request', + renderProps: {}, + state: 'pending', + testId: 'r4', + timeout: 0, + type: 'parent', + url: 'https://jsonplaceholder.cypress.io/comments/1', + wallClockStartedAt: '2023-03-30T21:58:08.456Z', + testCurrentRetry: 0, + hasSnapshot: false, + hasConsoleProps: true, + timestamp: '2023-03-30T21:58:08.457Z', + } + + protocolManager.commandLogAdded(log) + + expect(protocol.commandLogAdded).to.be.calledWith(log) + }) + + it('should be able to change a command log', async () => { + sinon.stub(protocol, 'commandLogChanged') + + const log = { + id: 'log-https://example.cypress.io-17', + alias: 'getComment', + aliasType: 'route', + displayName: 'xhr', + event: true, + hookId: 'r4', + instrument: 'command', + message: '', + method: 'GET', + name: 'request', + renderProps: {}, + state: 'pending', + testId: 'r4', + timeout: 0, + type: 'parent', + url: 'https://jsonplaceholder.cypress.io/comments/1', + wallClockStartedAt: '2023-03-30T21:58:08.456Z', + testCurrentRetry: 0, + hasSnapshot: false, + hasConsoleProps: true, + timestamp: '2023-03-30T21:58:08.457Z', + } + + protocolManager.commandLogChanged(log) + + expect(protocol.commandLogChanged).to.be.calledWith(log) + }) }) diff --git a/packages/types/src/protocol.ts b/packages/types/src/protocol.ts index b0c75a9a4256..6b825dc92922 100644 --- a/packages/types/src/protocol.ts +++ b/packages/types/src/protocol.ts @@ -20,6 +20,8 @@ export interface AppCaptureProtocolInterface { afterSpec (): void beforeTest(test: Record): void afterTest(test: Record): void + commandLogAdded (log: any): void + commandLogChanged (log: any): void } export interface ProtocolManager { @@ -31,4 +33,6 @@ export interface ProtocolManager { afterSpec (): void beforeTest(test: Record): void afterTest(test: Record): void + commandLogAdded (log: any): void + commandLogChanged (log: any): void } diff --git a/yarn.lock b/yarn.lock index a30d01331611..71938879f2c1 100644 --- a/yarn.lock +++ b/yarn.lock @@ -20953,7 +20953,7 @@ minimist@1.2.0: resolved "https://registry.yarnpkg.com/minimist/-/minimist-1.2.0.tgz#a35008b20f41383eec1fb914f4cd5df79a264284" integrity sha1-o1AIsg9BOD7sH7kU9M1d95omQoQ= -minimist@1.2.8, minimist@^1.2.8: +minimist@1.2.8, minimist@^1.1.0, minimist@^1.1.1, minimist@^1.1.3, minimist@^1.2.0, minimist@^1.2.3, minimist@^1.2.5, minimist@^1.2.8: version "1.2.8" resolved "https://registry.yarnpkg.com/minimist/-/minimist-1.2.8.tgz#c1a464e7693302e082a075cee0c057741ac4772c" integrity sha512-2yyAR8qBkN3YuheJanUpWC5U3bb5osDywNB8RzDVlDwDHbocAJveqqj1u8+SVD7jkWT4yvsHCpWqqWqAxb0zCA== @@ -20963,11 +20963,6 @@ minimist@^0.2.1: resolved "https://registry.yarnpkg.com/minimist/-/minimist-0.2.1.tgz#827ba4e7593464e7c221e8c5bed930904ee2c455" integrity sha512-GY8fANSrTMfBVfInqJAY41QkOM+upUTytK1jZ0c8+3HdHrJxBJ3rF5i9moClXTE8uUSnUo8cAsCoxDXvSY4DHg== -minimist@^1.1.0, minimist@^1.1.1, minimist@^1.1.3, minimist@^1.2.0, minimist@^1.2.3, minimist@^1.2.5: - version "1.2.6" - resolved "https://registry.yarnpkg.com/minimist/-/minimist-1.2.6.tgz#8637a5b759ea0d6e98702cfb3a9283323c93af44" - integrity sha512-Jsjnk4bw3YJqYzbdyBiNsPWHPfO++UGG749Cxs6peCu5Xg4nrena6OVxOYxrQTqww0Jmwt+Ref8rggumkTLz9Q== - minipass-collect@^1.0.2: version "1.0.2" resolved "https://registry.yarnpkg.com/minipass-collect/-/minipass-collect-1.0.2.tgz#22b813bf745dc6edba2576b940022ad6edc8c617" From 352bc0251d2c37e5f79f88c6e9f4315195cd86d6 Mon Sep 17 00:00:00 2001 From: Matt Schile Date: Mon, 3 Apr 2023 09:19:55 -0600 Subject: [PATCH 2/8] adding timestamp separately --- packages/reporter/src/errors/err-model.ts | 1 - packages/server/lib/cloud/protocol.ts | 8 ++++---- packages/server/lib/socket-base.ts | 4 ++-- .../support/fixtures/cloud/protocol/test-protocol.js | 4 ++-- packages/server/test/unit/cloud/protocol_spec.ts | 10 ++++------ packages/types/src/protocol.ts | 8 ++++---- 6 files changed, 16 insertions(+), 19 deletions(-) diff --git a/packages/reporter/src/errors/err-model.ts b/packages/reporter/src/errors/err-model.ts index 22375ddcb013..9a99c609cb07 100644 --- a/packages/reporter/src/errors/err-model.ts +++ b/packages/reporter/src/errors/err-model.ts @@ -31,7 +31,6 @@ export interface ErrProps { docsUrl: string | string[] templateType: string codeFrame: CodeFrame - isRecovered: boolean } export default class Err { diff --git a/packages/server/lib/cloud/protocol.ts b/packages/server/lib/cloud/protocol.ts index 4d409edc2e18..0277f5493397 100644 --- a/packages/server/lib/cloud/protocol.ts +++ b/packages/server/lib/cloud/protocol.ts @@ -110,20 +110,20 @@ class ProtocolManagerImpl implements ProtocolManager { this.protocol?.afterTest(test) } - commandLogAdded (log: any) { + commandLogAdded (log: any, timestamp: string) { if (!this.protocolEnabled()) { return } - this.protocol?.commandLogAdded(log) + this.protocol?.commandLogAdded(log, timestamp) } - commandLogChanged (log: any): void { + commandLogChanged (log: any, timestamp: string): void { if (!this.protocolEnabled()) { return } - this.protocol?.commandLogChanged(log) + this.protocol?.commandLogChanged(log, timestamp) } } diff --git a/packages/server/lib/socket-base.ts b/packages/server/lib/socket-base.ts index 0ec01ccaeff1..df687cb3782b 100644 --- a/packages/server/lib/socket-base.ts +++ b/packages/server/lib/socket-base.ts @@ -461,9 +461,9 @@ export class SocketBase { case 'protocol:test:after:run': return this.protocolManager?.afterTest(args[0]) case 'protocol:command:log:added': - return this.protocolManager?.commandLogAdded(args[0]) + return this.protocolManager?.commandLogAdded(args[0], args[1]) case 'protocol:command:log:changed': - return this.protocolManager?.commandLogChanged(args[0]) + return this.protocolManager?.commandLogChanged(args[0], args[1]) default: throw new Error(`You requested a backend event we cannot handle: ${eventName}`) } diff --git a/packages/server/test/support/fixtures/cloud/protocol/test-protocol.js b/packages/server/test/support/fixtures/cloud/protocol/test-protocol.js index 1017e082150c..15ddbdbabaa7 100644 --- a/packages/server/test/support/fixtures/cloud/protocol/test-protocol.js +++ b/packages/server/test/support/fixtures/cloud/protocol/test-protocol.js @@ -20,8 +20,8 @@ const AppCaptureProtocol = class { beforeSpec (spec) {} afterSpec (spec) {} beforeTest (test) {} - commandLogAdded (log) {} - commandLogChanged (log) {} + commandLogAdded (log, timestamp) {} + commandLogChanged (log, timestamp) {} } module.exports = { diff --git a/packages/server/test/unit/cloud/protocol_spec.ts b/packages/server/test/unit/cloud/protocol_spec.ts index 87670b83ff7b..b7d951c6f738 100644 --- a/packages/server/test/unit/cloud/protocol_spec.ts +++ b/packages/server/test/unit/cloud/protocol_spec.ts @@ -128,12 +128,11 @@ describe('lib/cloud/protocol', () => { testCurrentRetry: 0, hasSnapshot: false, hasConsoleProps: true, - timestamp: '2023-03-30T21:58:08.457Z', } - protocolManager.commandLogAdded(log) + protocolManager.commandLogAdded(log, '2023-03-30T21:58:08.457Z') - expect(protocol.commandLogAdded).to.be.calledWith(log) + expect(protocol.commandLogAdded).to.be.calledWith(log, '2023-03-30T21:58:08.457Z') }) it('should be able to change a command log', async () => { @@ -160,11 +159,10 @@ describe('lib/cloud/protocol', () => { testCurrentRetry: 0, hasSnapshot: false, hasConsoleProps: true, - timestamp: '2023-03-30T21:58:08.457Z', } - protocolManager.commandLogChanged(log) + protocolManager.commandLogChanged(log, '2023-03-30T21:58:08.457Z') - expect(protocol.commandLogChanged).to.be.calledWith(log) + expect(protocol.commandLogChanged).to.be.calledWith(log, '2023-03-30T21:58:08.457Z') }) }) diff --git a/packages/types/src/protocol.ts b/packages/types/src/protocol.ts index 6b825dc92922..12a6cc7c189e 100644 --- a/packages/types/src/protocol.ts +++ b/packages/types/src/protocol.ts @@ -20,8 +20,8 @@ export interface AppCaptureProtocolInterface { afterSpec (): void beforeTest(test: Record): void afterTest(test: Record): void - commandLogAdded (log: any): void - commandLogChanged (log: any): void + commandLogAdded (log: any, timestamp: string): void + commandLogChanged (log: any, timestamp: string): void } export interface ProtocolManager { @@ -33,6 +33,6 @@ export interface ProtocolManager { afterSpec (): void beforeTest(test: Record): void afterTest(test: Record): void - commandLogAdded (log: any): void - commandLogChanged (log: any): void + commandLogAdded (log: any, timestamp: string): void + commandLogChanged (log: any, timestamp: string): void } From 1334a183f56cf831857746d66ce59c2584966d21 Mon Sep 17 00:00:00 2001 From: Matt Schile Date: Mon, 3 Apr 2023 17:45:38 -0600 Subject: [PATCH 3/8] Updating timestamp --- packages/app/src/runner/event-manager.ts | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/packages/app/src/runner/event-manager.ts b/packages/app/src/runner/event-manager.ts index 032fbfb9a0a4..bbc6d4b92d29 100644 --- a/packages/app/src/runner/event-manager.ts +++ b/packages/app/src/runner/event-manager.ts @@ -492,7 +492,7 @@ export class EventManager { this._interceptStudio(displayProps) this.reporterBus.emit('reporter:log:add', displayProps) - Cypress.backend('protocol:command:log:added', { ...displayProps, timestamp: displayProps.wallClockStartedAt }) + Cypress.backend('protocol:command:log:added', displayProps, new Date().toJSON()) }) Cypress.on('log:changed', (log) => { @@ -506,7 +506,7 @@ export class EventManager { this._interceptStudio(displayProps) this.reporterBus.emit('reporter:log:state:changed', displayProps) - Cypress.backend('protocol:command:log:changed', { ...displayProps, timestamp: new Date().toJSON() }) + Cypress.backend('protocol:command:log:changed', displayProps, new Date().toJSON()) }) // TODO: MOVE BACK INTO useEventManager. Verify this works From 36d7220d0769691ced2bf39a9326cc3545257f30 Mon Sep 17 00:00:00 2001 From: Matt Schile Date: Tue, 4 Apr 2023 00:30:57 -0600 Subject: [PATCH 4/8] fixing unit tests --- packages/server/test/unit/cloud/protocol_spec.ts | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) diff --git a/packages/server/test/unit/cloud/protocol_spec.ts b/packages/server/test/unit/cloud/protocol_spec.ts index b7d951c6f738..41941e24e888 100644 --- a/packages/server/test/unit/cloud/protocol_spec.ts +++ b/packages/server/test/unit/cloud/protocol_spec.ts @@ -17,7 +17,7 @@ describe('lib/cloud/protocol', () => { beforeEach(async () => { process.env.CYPRESS_LOCAL_PROTOCOL_PATH = path.join(__dirname, '..', '..', 'support', 'fixtures', 'cloud', 'protocol', 'test-protocol.js') - const protocolManager = new ProtocolManager() + protocolManager = new ProtocolManager() await protocolManager.setupProtocol() @@ -28,7 +28,7 @@ describe('lib/cloud/protocol', () => { delete process.env.CYPRESS_LOCAL_PROTOCOL_PATH }) - it('should be able to setup the protocol', async () => { + it('should be able to setup the protocol', () => { expect(protocolManager.protocolEnabled()).to.be.true expect((protocol as any).Debug).not.to.be.undefined }) @@ -43,7 +43,7 @@ describe('lib/cloud/protocol', () => { expect(protocol.connectToBrowser).to.be.calledWith(mockCdpClient) }) - it('should be able to initialize a new spec', async () => { + it('should be able to initialize a new spec', () => { sinon.stub(protocol, 'beforeSpec') protocolManager.beforeSpec({ @@ -57,7 +57,7 @@ describe('lib/cloud/protocol', () => { }) }) - it('should be able to initialize a new test', async () => { + it('should be able to initialize a new test', () => { sinon.stub(protocol, 'beforeTest') protocolManager.beforeTest({ @@ -73,7 +73,7 @@ describe('lib/cloud/protocol', () => { }) }) - it('should be able to clean up after a spec', async () => { + it('should be able to clean up after a spec', () => { sinon.stub(protocol, 'afterSpec') protocolManager.afterSpec() @@ -81,7 +81,7 @@ describe('lib/cloud/protocol', () => { expect(protocol.afterSpec).to.be.called }) - it('should be able to add runnables', async () => { + it('should be able to add runnables', () => { sinon.stub(protocol, 'addRunnables') const rootRunnable = { @@ -104,7 +104,7 @@ describe('lib/cloud/protocol', () => { expect(protocol.addRunnables).to.be.calledWith(rootRunnable) }) - it('should be able to add a command log', async () => { + it('should be able to add a command log', () => { sinon.stub(protocol, 'commandLogAdded') const log = { @@ -135,7 +135,7 @@ describe('lib/cloud/protocol', () => { expect(protocol.commandLogAdded).to.be.calledWith(log, '2023-03-30T21:58:08.457Z') }) - it('should be able to change a command log', async () => { + it('should be able to change a command log', () => { sinon.stub(protocol, 'commandLogChanged') const log = { From 65619a66cf4cd7a2cd187187441340c08857e7a0 Mon Sep 17 00:00:00 2001 From: Matt Schile Date: Tue, 4 Apr 2023 10:33:02 -0600 Subject: [PATCH 5/8] fixing tests --- packages/driver/cypress.config.ts | 2 +- .../driver/cypress/e2e/commands/exec.cy.js | 2 +- .../driver/cypress/e2e/commands/files.cy.js | 2 +- .../cypress/e2e/commands/fixtures.cy.js | 2 +- .../cypress/e2e/commands/navigation.cy.js | 36 +++++++++---------- .../cypress/e2e/commands/net_stubbing.cy.ts | 12 +++---- .../driver/cypress/e2e/commands/request.cy.js | 2 +- .../e2e/commands/sessions/sessions.cy.js | 4 +-- .../driver/cypress/e2e/commands/task.cy.js | 2 +- .../e2e/e2e/origin/commands/files.cy.ts | 4 +-- .../cypress/e2e/e2e/origin/patches.cy.ts | 18 +++++----- 11 files changed, 41 insertions(+), 45 deletions(-) diff --git a/packages/driver/cypress.config.ts b/packages/driver/cypress.config.ts index c1002a5d24f9..7c2cf3908f9c 100644 --- a/packages/driver/cypress.config.ts +++ b/packages/driver/cypress.config.ts @@ -2,7 +2,7 @@ import { defineConfig } from 'cypress' import { devServer as cypressWebpackDevServer } from '@cypress/webpack-dev-server' export default defineConfig({ - projectId: 'ypt4pf', + projectId: 'pezun9', experimentalStudio: true, experimentalMemoryManagement: true, experimentalWebKitSupport: true, diff --git a/packages/driver/cypress/e2e/commands/exec.cy.js b/packages/driver/cypress/e2e/commands/exec.cy.js index 0d20f786161f..4b3b2d664b7d 100644 --- a/packages/driver/cypress/e2e/commands/exec.cy.js +++ b/packages/driver/cypress/e2e/commands/exec.cy.js @@ -9,7 +9,7 @@ describe('src/cy/commands/exec', () => { }, () => { beforeEach(() => { // call through normally on everything - cy.stub(Cypress, 'backend').callThrough() + cy.stub(Cypress, 'backend').log(false).callThrough() }) it('triggers \'exec\' with the right options', () => { diff --git a/packages/driver/cypress/e2e/commands/files.cy.js b/packages/driver/cypress/e2e/commands/files.cy.js index 8002a1f05f37..7713187453c4 100644 --- a/packages/driver/cypress/e2e/commands/files.cy.js +++ b/packages/driver/cypress/e2e/commands/files.cy.js @@ -10,7 +10,7 @@ const okResponse = { describe('src/cy/commands/files', () => { beforeEach(() => { // call through normally on everything - cy.stub(Cypress, 'backend').callThrough() + cy.stub(Cypress, 'backend').log(false).callThrough() }) describe('#readFile', () => { diff --git a/packages/driver/cypress/e2e/commands/fixtures.cy.js b/packages/driver/cypress/e2e/commands/fixtures.cy.js index 0f6c8fddae2c..3995e9ffb6a8 100644 --- a/packages/driver/cypress/e2e/commands/fixtures.cy.js +++ b/packages/driver/cypress/e2e/commands/fixtures.cy.js @@ -13,7 +13,7 @@ describe('src/cy/commands/fixtures', () => { context('#fixture', () => { beforeEach(() => { // call through normally on everything - cy.stub(Cypress, 'backend').callThrough() + cy.stub(Cypress, 'backend').log(false).callThrough() }) it('triggers \'fixture\' on Cypress', () => { diff --git a/packages/driver/cypress/e2e/commands/navigation.cy.js b/packages/driver/cypress/e2e/commands/navigation.cy.js index 373acf1a9d64..0bf5d9c58dc8 100644 --- a/packages/driver/cypress/e2e/commands/navigation.cy.js +++ b/packages/driver/cypress/e2e/commands/navigation.cy.js @@ -680,7 +680,7 @@ describe('src/cy/commands/navigation', () => { }) it('calls resolve:url with http:// when localhost', () => { - const backend = cy.spy(Cypress, 'backend') + const backend = cy.spy(Cypress, 'backend').log(false) cy .visit('localhost:3500/timeout') @@ -720,7 +720,7 @@ describe('src/cy/commands/navigation', () => { }) it('strips username + password out of the url when provided', () => { - const backend = cy.spy(Cypress, 'backend') + const backend = cy.spy(Cypress, 'backend').log(false) cy .visit('http://cypress:password123@localhost:3500/timeout') @@ -730,7 +730,7 @@ describe('src/cy/commands/navigation', () => { }) it('passes auth options', () => { - const backend = cy.spy(Cypress, 'backend') + const backend = cy.spy(Cypress, 'backend').log(false) const auth = { username: 'cypress', @@ -926,7 +926,7 @@ describe('src/cy/commands/navigation', () => { done() } - cy.stub(Cypress, 'backend') + cy.stub(Cypress, 'backend').log(false) .withArgs('resolve:url') .resolves({ isOkStatusCode: true, @@ -957,7 +957,7 @@ describe('src/cy/commands/navigation', () => { .withArgs('http://localhost:4200/foo?bar=baz#/tests/integration/foo_spec.js') .callsFake(fn) - cy.stub(Cypress, 'backend') + cy.stub(Cypress, 'backend').log(false) .withArgs('resolve:url') .resolves({ isOkStatusCode: true, @@ -1123,7 +1123,7 @@ describe('src/cy/commands/navigation', () => { }) it('displays file attributes as consoleProps', () => { - cy.stub(Cypress, 'backend') + cy.stub(Cypress, 'backend').log(false) .withArgs('resolve:url') .resolves({ isOkStatusCode: true, @@ -1147,7 +1147,7 @@ describe('src/cy/commands/navigation', () => { }) it('displays http attributes as consoleProps', () => { - cy.stub(Cypress, 'backend') + cy.stub(Cypress, 'backend').log(false) .withArgs('resolve:url') .resolves({ isOkStatusCode: true, @@ -1170,7 +1170,7 @@ describe('src/cy/commands/navigation', () => { }) it('displays originalUrl http attributes as consoleProps', () => { - cy.stub(Cypress, 'backend') + cy.stub(Cypress, 'backend').log(false) .withArgs('resolve:url') .resolves({ isOkStatusCode: true, @@ -1194,7 +1194,7 @@ describe('src/cy/commands/navigation', () => { }) it('indicates redirects in the message', () => { - cy.stub(Cypress, 'backend') + cy.stub(Cypress, 'backend').log(false) .withArgs('resolve:url') .resolves({ isOkStatusCode: true, @@ -1281,7 +1281,7 @@ describe('src/cy/commands/navigation', () => { }) it('sets error command state', function (done) { - cy.stub(Cypress, 'backend') + cy.stub(Cypress, 'backend').log(false) .withArgs('resolve:url') .rejects(new Error) @@ -1298,7 +1298,7 @@ describe('src/cy/commands/navigation', () => { }) it('logs once on error', function (done) { - cy.stub(Cypress, 'backend') + cy.stub(Cypress, 'backend').log(false) .withArgs('resolve:url') .rejects(new Error) @@ -1338,7 +1338,7 @@ describe('src/cy/commands/navigation', () => { }) } - cy.stub(Cypress, 'backend') + cy.stub(Cypress, 'backend').log(false) .withArgs('resolve:url') .callsFake(fn) @@ -1442,7 +1442,7 @@ describe('src/cy/commands/navigation', () => { // dont log else we create an endless loop! const emit = cy.spy(Cypress, 'emit').log(false) - cy.stub(Cypress, 'backend') + cy.stub(Cypress, 'backend').log(false) .withArgs('resolve:url') .rejects(err1) @@ -1491,7 +1491,7 @@ describe('src/cy/commands/navigation', () => { obj.url = obj.originalUrl - cy.stub(Cypress, 'backend') + cy.stub(Cypress, 'backend').log(false) .withArgs('resolve:url') .resolves(obj) @@ -1540,7 +1540,7 @@ describe('src/cy/commands/navigation', () => { obj.url = obj.originalUrl - cy.stub(Cypress, 'backend') + cy.stub(Cypress, 'backend').log(false) .withArgs('resolve:url') .resolves(obj) @@ -1590,7 +1590,7 @@ describe('src/cy/commands/navigation', () => { obj.url = obj.originalUrl - cy.stub(Cypress, 'backend') + cy.stub(Cypress, 'backend').log(false) .withArgs('resolve:url', 'https://google.com/foo') .resolves(obj) @@ -1639,7 +1639,7 @@ describe('src/cy/commands/navigation', () => { obj.url = obj.originalUrl - cy.stub(Cypress, 'backend') + cy.stub(Cypress, 'backend').log(false) .withArgs('resolve:url', 'https://google.com/foo') .resolves(obj) @@ -1733,7 +1733,7 @@ describe('src/cy/commands/navigation', () => { obj.url = obj.originalUrl - cy.stub(Cypress, 'backend') + cy.stub(Cypress, 'backend').log(false) .withArgs('resolve:url', 'https://google.com/foo') .resolves(obj) diff --git a/packages/driver/cypress/e2e/commands/net_stubbing.cy.ts b/packages/driver/cypress/e2e/commands/net_stubbing.cy.ts index b469f0c68261..8dc9e051ea31 100644 --- a/packages/driver/cypress/e2e/commands/net_stubbing.cy.ts +++ b/packages/driver/cypress/e2e/commands/net_stubbing.cy.ts @@ -1381,8 +1381,7 @@ describe('network stubbing', { retries: 15 }, function () { // @see https://github.com/cypress-io/cypress/issues/19330 // @see https://github.com/cypress-io/cypress/issues/19344 it('load fixture as Buffer when encoding is null', function () { - // call through normally on everything - cy.spy(Cypress, 'backend') + cy.spy(Cypress, 'backend').log(false) cy.intercept('/fixtures/media/small.mp4', { fixture: 'media/small.mp4,null', @@ -1390,8 +1389,7 @@ describe('network stubbing', { retries: 15 }, function () { cy.visit('/fixtures/video.html') .then(() => { - // @ts-ignore .getCall is a Sinon spy command - expect(Cypress.backend.getCall(0)).to.be.calledWithMatch( + expect(Cypress.backend).to.be.calledWithMatch( 'net', 'route:added', { @@ -1407,8 +1405,7 @@ describe('network stubbing', { retries: 15 }, function () { }) it('load fixture with specified encoding', function () { - // call through normally on everything - cy.spy(Cypress, 'backend') + cy.spy(Cypress, 'backend').log(false) cy.intercept('non-existing-image.png', { headers: { 'content-type': 'image/jpeg' }, @@ -1417,8 +1414,7 @@ describe('network stubbing', { retries: 15 }, function () { cy.visit('/fixtures/img-embed.html') .then(() => { - // @ts-ignore .getCall is a Sinon spy command - expect(Cypress.backend.getCall(0)).to.be.calledWithMatch( + expect(Cypress.backend).to.be.calledWithMatch( 'net', 'route:added', { diff --git a/packages/driver/cypress/e2e/commands/request.cy.js b/packages/driver/cypress/e2e/commands/request.cy.js index e933b2956776..88f2025c5867 100644 --- a/packages/driver/cypress/e2e/commands/request.cy.js +++ b/packages/driver/cypress/e2e/commands/request.cy.js @@ -9,7 +9,7 @@ describe('src/cy/commands/request', () => { responseTimeout: RESPONSE_TIMEOUT, }, () => { beforeEach(() => { - cy.stub(Cypress, 'backend').callThrough() + cy.stub(Cypress, 'backend').log(false).callThrough() }) describe('argument signature', () => { diff --git a/packages/driver/cypress/e2e/commands/sessions/sessions.cy.js b/packages/driver/cypress/e2e/commands/sessions/sessions.cy.js index 23ebec5c2957..eed4e2da7fd0 100644 --- a/packages/driver/cypress/e2e/commands/sessions/sessions.cy.js +++ b/packages/driver/cypress/e2e/commands/sessions/sessions.cy.js @@ -77,7 +77,7 @@ describe('cy.session', { retries: 0 }, () => { }) it('resets rendered html origins before each run', async () => { - const backendSpy = cy.spy(Cypress, 'backend') + const backendSpy = cy.spy(Cypress, 'backend').log(false) await Cypress.action('runner:test:before:run:async', {}, Cypress.state('runnable')) @@ -806,7 +806,7 @@ describe('cy.session', { retries: 0 }, () => { }) it('does not reset rendered html origins before each run', async () => { - const backendSpy = cy.spy(Cypress, 'backend') + const backendSpy = cy.spy(Cypress, 'backend').log(false) await Cypress.action('runner:test:before:run:async', {}, Cypress.state('runnable')) diff --git a/packages/driver/cypress/e2e/commands/task.cy.js b/packages/driver/cypress/e2e/commands/task.cy.js index 85d92bdf69c0..23938fc80d51 100644 --- a/packages/driver/cypress/e2e/commands/task.cy.js +++ b/packages/driver/cypress/e2e/commands/task.cy.js @@ -6,7 +6,7 @@ describe('src/cy/commands/task', () => { taskTimeout: 2500, }, () => { beforeEach(() => { - cy.stub(Cypress, 'backend').callThrough() + cy.stub(Cypress, 'backend').log(false).callThrough() }) it('calls Cypress.backend(\'task\') with the right options', () => { diff --git a/packages/driver/cypress/e2e/e2e/origin/commands/files.cy.ts b/packages/driver/cypress/e2e/e2e/origin/commands/files.cy.ts index d708b9b9fc94..f0755e018989 100644 --- a/packages/driver/cypress/e2e/e2e/origin/commands/files.cy.ts +++ b/packages/driver/cypress/e2e/e2e/origin/commands/files.cy.ts @@ -28,7 +28,7 @@ context('cy.origin files', { browser: '!webkit' }, () => { cy.origin('http://www.foobar.com:3500', () => { const contents = JSON.stringify({ foo: 'bar' }) - cy.stub(Cypress, 'backend').resolves({ + cy.stub(Cypress, 'backend').log(false).resolves({ contents, filePath: 'foo.json', }) @@ -76,7 +76,7 @@ context('cy.origin files', { browser: '!webkit' }, () => { cy.origin('http://www.foobar.com:3500', () => { const contents = JSON.stringify({ foo: 'bar' }) - cy.stub(Cypress, 'backend').resolves({ + cy.stub(Cypress, 'backend').log(false).resolves({ contents, filePath: 'foo.json', }) diff --git a/packages/driver/cypress/e2e/e2e/origin/patches.cy.ts b/packages/driver/cypress/e2e/e2e/origin/patches.cy.ts index 650345a9f1d4..27f38fb57771 100644 --- a/packages/driver/cypress/e2e/e2e/origin/patches.cy.ts +++ b/packages/driver/cypress/e2e/e2e/origin/patches.cy.ts @@ -63,7 +63,7 @@ describe('src/cross-origin/patches', { browser: '!webkit', defaultCommandTimeout describe('from the AUT', () => { beforeEach(() => { cy.intercept('/test-request').as('testRequest') - cy.stub(Cypress, 'backend').callThrough() + cy.stub(Cypress, 'backend').log(false).callThrough() cy.visit('/fixtures/primary-origin.html') cy.get('a[data-cy="xhr-fetch-requests"]').click() @@ -184,7 +184,7 @@ describe('src/cross-origin/patches', { browser: '!webkit', defaultCommandTimeout describe('from the spec bridge', () => { beforeEach(() => { cy.intercept('/test-request').as('testRequest') - cy.stub(Cypress, 'backend').callThrough() + cy.stub(Cypress, 'backend').log(false).callThrough() cy.visit('/fixtures/primary-origin.html') cy.get('a[data-cy="xhr-fetch-requests"]').click() @@ -338,7 +338,7 @@ describe('src/cross-origin/patches', { browser: '!webkit', defaultCommandTimeout // manually remove the spec bridge iframe to ensure Cypress.state('window') is not already set window.top?.document.getElementById('Spec\ Bridge:\ foobar.com')?.remove() - cy.stub(Cypress, 'backend').callThrough() + cy.stub(Cypress, 'backend').log(false).callThrough() cy.visit('/fixtures/primary-origin.html') cy.get('a[data-cy="xhr-fetch-requests-onload"]').click() @@ -353,7 +353,7 @@ describe('src/cross-origin/patches', { browser: '!webkit', defaultCommandTimeout }) it('does not patch fetch in the spec window or the AUT if the AUT is on the primary', () => { - cy.stub(Cypress, 'backend').callThrough() + cy.stub(Cypress, 'backend').log(false).callThrough() cy.visit('fixtures/xhr-fetch-requests.html') cy.window().then((win) => { @@ -386,7 +386,7 @@ describe('src/cross-origin/patches', { browser: '!webkit', defaultCommandTimeout describe('from the AUT', () => { beforeEach(() => { cy.intercept('/test-request').as('testRequest') - cy.stub(Cypress, 'backend').callThrough() + cy.stub(Cypress, 'backend').log(false).callThrough() cy.visit('/fixtures/primary-origin.html') cy.get('a[data-cy="xhr-fetch-requests"]').click() @@ -460,9 +460,9 @@ describe('src/cross-origin/patches', { browser: '!webkit', defaultCommandTimeout describe('from the spec bridge', () => { beforeEach(() => { cy.intercept('/test-request').as('testRequest') - cy.stub(Cypress, 'backend').callThrough() + cy.stub(Cypress, 'backend').log(false).callThrough() cy.origin('http://www.foobar.com:3500', () => { - cy.stub(Cypress, 'backend').callThrough() + cy.stub(Cypress, 'backend').log(false).callThrough() }) cy.visit('/fixtures/primary-origin.html') @@ -566,7 +566,7 @@ describe('src/cross-origin/patches', { browser: '!webkit', defaultCommandTimeout // manually remove the spec bridge iframe to ensure Cypress.state('window') is not already set window.top?.document.getElementById('Spec\ Bridge:\ foobar.com')?.remove() - cy.stub(Cypress, 'backend').callThrough() + cy.stub(Cypress, 'backend').log(false).callThrough() cy.visit('/fixtures/primary-origin.html') cy.get('a[data-cy="xhr-fetch-requests-onload"]').click() @@ -581,7 +581,7 @@ describe('src/cross-origin/patches', { browser: '!webkit', defaultCommandTimeout }) it('does not patch xmlHttpRequest in the spec window or the AUT if the AUT is on the primary', () => { - cy.stub(Cypress, 'backend').callThrough() + cy.stub(Cypress, 'backend').log(false).callThrough() cy.visit('fixtures/xhr-fetch-requests.html') cy.window().then((win) => { From b92695be432d1133bf5dcc2639c2d80f64b7ddfe Mon Sep 17 00:00:00 2001 From: Matt Schile Date: Tue, 4 Apr 2023 10:53:16 -0600 Subject: [PATCH 6/8] revert projectId --- packages/driver/cypress.config.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/packages/driver/cypress.config.ts b/packages/driver/cypress.config.ts index 7c2cf3908f9c..c1002a5d24f9 100644 --- a/packages/driver/cypress.config.ts +++ b/packages/driver/cypress.config.ts @@ -2,7 +2,7 @@ import { defineConfig } from 'cypress' import { devServer as cypressWebpackDevServer } from '@cypress/webpack-dev-server' export default defineConfig({ - projectId: 'pezun9', + projectId: 'ypt4pf', experimentalStudio: true, experimentalMemoryManagement: true, experimentalWebKitSupport: true, From b7565760f76de8a044bc15152e1152bebd4c6c62 Mon Sep 17 00:00:00 2001 From: Matt Schile Date: Tue, 4 Apr 2023 14:20:57 -0600 Subject: [PATCH 7/8] fixing tests --- packages/driver/cypress/e2e/commands/exec.cy.js | 6 +++--- packages/driver/cypress/e2e/commands/task.cy.js | 6 +++--- 2 files changed, 6 insertions(+), 6 deletions(-) diff --git a/packages/driver/cypress/e2e/commands/exec.cy.js b/packages/driver/cypress/e2e/commands/exec.cy.js index 4b3b2d664b7d..10ff6ee077d8 100644 --- a/packages/driver/cypress/e2e/commands/exec.cy.js +++ b/packages/driver/cypress/e2e/commands/exec.cy.js @@ -188,7 +188,7 @@ describe('src/cy/commands/exec', () => { }) it('throws when the execution errors', function (done) { - Cypress.backend.rejects(new Error('exec failed')) + Cypress.backend.withArgs('exec').rejects(new Error('exec failed')) cy.on('fail', (err) => { const { lastLog } = this @@ -225,7 +225,7 @@ describe('src/cy/commands/exec', () => { }) it('logs once on error', function (done) { - Cypress.backend.rejects(new Error('exec failed')) + Cypress.backend.withArgs('exec').rejects(new Error('exec failed')) cy.on('fail', (err) => { const { lastLog } = this @@ -245,7 +245,7 @@ describe('src/cy/commands/exec', () => { err.timedOut = true - Cypress.backend.rejects(err) + Cypress.backend.withArgs('exec').rejects(err) cy.on('fail', (err) => { expect(err.message).to.include('`cy.exec(\'sleep 2\')` timed out after waiting `100ms`.') diff --git a/packages/driver/cypress/e2e/commands/task.cy.js b/packages/driver/cypress/e2e/commands/task.cy.js index 23938fc80d51..68cb1da86b66 100644 --- a/packages/driver/cypress/e2e/commands/task.cy.js +++ b/packages/driver/cypress/e2e/commands/task.cy.js @@ -184,7 +184,7 @@ describe('src/cy/commands/task', () => { }) it('throws when the task errors', function (done) { - Cypress.backend.rejects(new Error('task failed')) + Cypress.backend.withArgs('task').rejects(new Error('task failed')) cy.on('fail', (err) => { const { lastLog } = this @@ -237,7 +237,7 @@ describe('src/cy/commands/task', () => { }) it('logs once on error', function (done) { - Cypress.backend.rejects(new Error('task failed')) + Cypress.backend.withArgs('task').rejects(new Error('task failed')) cy.on('fail', (err) => { const { lastLog } = this @@ -257,7 +257,7 @@ describe('src/cy/commands/task', () => { err.timedOut = true - Cypress.backend.rejects(err) + Cypress.backend.withArgs('task').rejects(err) cy.on('fail', (err) => { expect(err.message).to.include('`cy.task(\'wait\')` timed out after waiting `100ms`.') From 202f8921cca9aa40d5ccd42c6bb7256b3a8c917e Mon Sep 17 00:00:00 2001 From: Matt Schile Date: Tue, 4 Apr 2023 14:58:28 -0600 Subject: [PATCH 8/8] more backend fixes --- packages/driver/cypress/e2e/commands/files.cy.js | 6 +++--- packages/driver/cypress/e2e/commands/fixtures.cy.js | 4 ++-- 2 files changed, 5 insertions(+), 5 deletions(-) diff --git a/packages/driver/cypress/e2e/commands/files.cy.js b/packages/driver/cypress/e2e/commands/files.cy.js index 7713187453c4..c97a23d95744 100644 --- a/packages/driver/cypress/e2e/commands/files.cy.js +++ b/packages/driver/cypress/e2e/commands/files.cy.js @@ -73,7 +73,7 @@ describe('src/cy/commands/files', () => { retries += 1 }) - Cypress.backend + Cypress.backend.withArgs('read:file') .onFirstCall() .rejects(err) .onSecondCall() @@ -91,7 +91,7 @@ describe('src/cy/commands/files', () => { retries += 1 }) - Cypress.backend + Cypress.backend.withArgs('read:file') .onFirstCall() .resolves({ contents: 'foobarbaz', @@ -243,7 +243,7 @@ describe('src/cy/commands/files', () => { cy.on('fail', (err) => { const { fileLog } = this - assertLogLength(this.logs, 3) + assertLogLength(this.logs, 2) expect(fileLog.get('error')).to.eq(err) expect(fileLog.get('state')).to.eq('failed') expect(err.message).to.eq(stripIndent`\ diff --git a/packages/driver/cypress/e2e/commands/fixtures.cy.js b/packages/driver/cypress/e2e/commands/fixtures.cy.js index 3995e9ffb6a8..7ae0bf999ac9 100644 --- a/packages/driver/cypress/e2e/commands/fixtures.cy.js +++ b/packages/driver/cypress/e2e/commands/fixtures.cy.js @@ -243,7 +243,7 @@ describe('src/cy/commands/fixtures', () => { }) }) .then(() => { - expect(Cypress.backend).to.be.calledTwice + expect(Cypress.backend.withArgs('get:fixture')).to.be.calledTwice }) }) @@ -261,7 +261,7 @@ describe('src/cy/commands/fixtures', () => { }) }) .then(() => { - expect(Cypress.backend).to.be.calledOnce + expect(Cypress.backend.withArgs('get:fixture')).to.be.calledOnce }) }) })