From 3592682c6167efb204ced899e6d279239106db14 Mon Sep 17 00:00:00 2001 From: Richard Macklin <1863540+rmacklin@users.noreply.github.com> Date: Mon, 16 Sep 2024 03:41:40 -0700 Subject: [PATCH] feat(plugin): make plugin a "no-op" in unsupported browsers (#460) Previously the plugin would throw an error when it was running in an unsupported browser. This was not great for plugin consumers who run their cypress tests in both supported and unsupported browsers and are fine with only having HAR recording in supported browsers: It forced them to conditionally enable this plugin. To address this, we're changing the plugin to do nothing except `warn` that HAR recording is not supported when running in an unsupported browser. relates-to: https://github.com/NeuraLegion/cypress-har-generator/issues/5#issuecomment-1987030824 --- src/Plugin.spec.ts | 59 ++++++++++++++++++++++++++++++++++++++++++---- src/Plugin.ts | 24 +++++++++++++++---- 2 files changed, 73 insertions(+), 10 deletions(-) diff --git a/src/Plugin.spec.ts b/src/Plugin.spec.ts index 78a3f73..51162fc 100644 --- a/src/Plugin.spec.ts +++ b/src/Plugin.spec.ts @@ -193,15 +193,17 @@ describe('Plugin', () => { expect(result).not.toContain(expectedArgs); }); - it('should throw an error if an unsupported browser family is used', () => { + it('should log a warning if an unsupported browser family is used', () => { // arrange const args = ['--flag1', '--flag2']; // act - const act = () => plugin.ensureBrowserFlags(firefox, args); + plugin.ensureBrowserFlags(firefox, args); // assert - expect(act).toThrowError( - `An unsupported browser family was used: ${firefox.name}` - ); + verify( + loggerMock.warn( + `HAR recording is not supported in this browser: ${firefox.name}` + ) + ).once(); }); it('should throw an error when Electron is used and switches are missed', () => { @@ -236,6 +238,8 @@ describe('Plugin', () => { } as SaveOptions; it('should log an error message when the connection is corrupted', async () => { + // arrange + plugin.ensureBrowserFlags(chrome, []); // act await plugin.saveHar(options); // assert @@ -400,6 +404,19 @@ describe('Plugin', () => { verify(harExporterMock.end()).once(); verify(fileManagerMock.removeFile(tempFilePath)).once(); }); + + it('should be a no-op if an unsupported browser family is used', async () => { + // arrange + plugin.ensureBrowserFlags(firefox, []); + await plugin.recordHar({ + rootDir: '/' + }); + + // act + await plugin.saveHar(options); + // assert + verify(fileManagerMock.createFolder(options.outDir)).never(); + }); }); describe('recordHar', () => { @@ -493,6 +510,26 @@ describe('Plugin', () => { // assert verify(harExporterMock.write(request)).never(); }); + + it('should be a no-op if an unsupported browser family is used', async () => { + const request = new NetworkRequest( + '1', + 'https://example.com', + 'https://example.com', + '1' + ); + when(harExporterFactoryMock.create(anything())).thenResolve( + resolvableInstance(harExporterMock) + ); + when(networkObserverMock.subscribe(anyFunction())).thenCall(callback => + callback(request) + ); + plugin.ensureBrowserFlags(firefox, []); + // act + await plugin.recordHar(options); + // assert + verify(harExporterMock.write(request)).never(); + }); }); describe('disposeOfHar', () => { @@ -539,5 +576,17 @@ describe('Plugin', () => { // assert verify(networkObserverMock.unsubscribe()).never(); }); + + it('should be a no-op if an unsupported browser family is used', async () => { + // arrange + plugin.ensureBrowserFlags(firefox, []); + await plugin.recordHar({ + rootDir: '/' + }); + // act + await plugin.disposeOfHar(); + // assert + verify(harExporterMock.end()).never(); + }); }); }); diff --git a/src/Plugin.ts b/src/Plugin.ts index 4a4a4e7..82caccf 100644 --- a/src/Plugin.ts +++ b/src/Plugin.ts @@ -44,6 +44,7 @@ export class Plugin { private networkObservable?: Observer; private addr?: Addr; private _connection?: Connection; + private supported?: boolean; constructor( private readonly logger: Logger, @@ -57,9 +58,10 @@ export class Plugin { browser: Cypress.Browser, args: string[] ): string[] { - if (!this.isSupportedBrowser(browser)) { - throw new Error( - `An unsupported browser family was used: ${browser.name}` + this.supported = this.isSupportedBrowser(browser); + if (!this.supported) { + this.logger.warn( + `HAR recording is not supported in this browser: ${browser.name}` ); } @@ -77,14 +79,18 @@ export class Plugin { } public async recordHar(options: RecordOptions): Promise { - await this.closeConnection(); - if (!this.addr) { throw new Error( `Please call the 'ensureBrowserFlags' before attempting to start the recording.` ); } + if (!this.supported) { + return; + } + + await this.closeConnection(); + this.exporter = await this.exporterFactory.create(options); this._connection = this.connectionFactory.create({ ...this.addr, @@ -99,6 +105,10 @@ export class Plugin { } public async saveHar(options: SaveOptions): Promise { + if (!this.supported) { + return; + } + const filePath = join(options.outDir, options.fileName); if (!this._connection) { @@ -130,6 +140,10 @@ export class Plugin { } public async disposeOfHar(): Promise { + if (!this.supported) { + return; + } + await this.networkObservable?.unsubscribe(); delete this.networkObservable;