cypress 15.21.1 → 16.1.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/angular/README.md +4 -1
- package/angular/angular/README.md +4 -1
- package/angular/angular/dist/index.d.ts +3 -19
- package/angular/angular/dist/index.js +70 -84
- package/angular/angular/package.json +11 -12
- package/angular/dist/index.d.ts +3 -19
- package/angular/dist/index.js +70 -84
- package/angular/package.json +11 -12
- package/dist/bin/cypress +3 -3
- package/dist/{cli-_xePNEPj.js → cli-BUzHfIQ2.js} +1898 -1931
- package/dist/cli.js +3 -3
- package/dist/{cypress-DCSAOi2D.js → cypress-D0g_F_Y2.js} +2 -2
- package/dist/cypress.js +4 -4
- package/dist/exec/spawn.js +2 -2
- package/dist/exec/xvfb.js +1 -1
- package/dist/index.js +4 -4
- package/dist/{spawn-BkpC5qQ4.js → spawn-BNsy7yWl.js} +13 -13
- package/dist/{tap-BkTD6Abc.js → tap-E19yanov.js} +124 -94
- package/dist/{xvfb-BKRGwxlS.js → xvfb-CbW2_YXR.js} +1 -1
- package/mount-utils/dist/index.js +1 -1
- package/mount-utils/mount-utils/dist/index.js +1 -1
- package/mount-utils/mount-utils/package.json +5 -5
- package/mount-utils/package.json +5 -5
- package/package.json +5 -11
- package/react/dist/cypress-react.cjs.js +1 -1
- package/react/dist/cypress-react.esm-bundler.js +1 -1
- package/react/dist/index.d.ts +2 -1
- package/react/package.json +2 -2
- package/react/react/dist/cypress-react.cjs.js +1 -1
- package/react/react/dist/cypress-react.esm-bundler.js +1 -1
- package/react/react/dist/index.d.ts +2 -1
- package/react/react/package.json +2 -2
- package/svelte/dist/cypress-svelte.cjs.js +1 -1
- package/svelte/dist/cypress-svelte.esm-bundler.js +1 -1
- package/svelte/dist/index.d.ts +2 -1
- package/svelte/package.json +1 -1
- package/svelte/svelte/dist/cypress-svelte.cjs.js +1 -1
- package/svelte/svelte/dist/cypress-svelte.esm-bundler.js +1 -1
- package/svelte/svelte/dist/index.d.ts +2 -1
- package/svelte/svelte/package.json +1 -1
- package/types/cy-blob-util.d.ts +1 -1
- package/types/cy-minimatch.d.ts +1 -1
- package/types/cypress-eventemitter.d.ts +2 -2
- package/types/cypress-expect.d.ts +5 -0
- package/types/cypress-global-vars.d.ts +6 -0
- package/types/cypress.d.ts +69 -139
- package/vue/dist/cypress-vue.cjs.js +62 -66
- package/vue/dist/cypress-vue.esm-bundler.js +50 -54
- package/vue/dist/index.d.ts +120 -82
- package/vue/package.json +4 -4
- package/vue/vue/dist/cypress-vue.cjs.js +62 -66
- package/vue/vue/dist/cypress-vue.esm-bundler.js +50 -54
- package/vue/vue/dist/index.d.ts +120 -82
- package/vue/vue/package.json +4 -4
- package/angular-zoneless/README.md +0 -15
- package/angular-zoneless/angular-zoneless/README.md +0 -15
- package/angular-zoneless/angular-zoneless/dist/index.d.ts +0 -119
- package/angular-zoneless/angular-zoneless/dist/index.js +0 -482
- package/angular-zoneless/angular-zoneless/package.json +0 -74
- package/angular-zoneless/dist/index.d.ts +0 -119
- package/angular-zoneless/dist/index.js +0 -482
- package/angular-zoneless/package.json +0 -74
package/angular/README.md
CHANGED
|
@@ -6,7 +6,10 @@ Mount Angular components in the open source [Cypress.io](https://www.cypress.io/
|
|
|
6
6
|
|
|
7
7
|
## Requirements
|
|
8
8
|
|
|
9
|
-
- Angular
|
|
9
|
+
- Angular `>=21.0.0`
|
|
10
|
+
- `@cypress/angular@4` supports Angular 18 - 19
|
|
11
|
+
- `@cypress/angular@3` supports Angular 17
|
|
12
|
+
- `@cypress/angular@2` supports Angular 13 - 16
|
|
10
13
|
|
|
11
14
|
## Development
|
|
12
15
|
|
|
@@ -6,7 +6,10 @@ Mount Angular components in the open source [Cypress.io](https://www.cypress.io/
|
|
|
6
6
|
|
|
7
7
|
## Requirements
|
|
8
8
|
|
|
9
|
-
- Angular
|
|
9
|
+
- Angular `>=21.0.0`
|
|
10
|
+
- `@cypress/angular@4` supports Angular 18 - 19
|
|
11
|
+
- `@cypress/angular@3` supports Angular 17
|
|
12
|
+
- `@cypress/angular@2` supports Angular 13 - 16
|
|
10
13
|
|
|
11
14
|
## Development
|
|
12
15
|
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
/// <reference types="cypress" />
|
|
2
2
|
|
|
3
3
|
import { InputSignal, WritableSignal, Type } from '@angular/core';
|
|
4
|
-
import { TestModuleMetadata, ComponentFixture
|
|
4
|
+
import { TestComponentRenderer, TestModuleMetadata, ComponentFixture } from '@angular/core/testing';
|
|
5
5
|
|
|
6
6
|
/**
|
|
7
7
|
* Additional module configurations needed while mounting the component, like
|
|
@@ -11,23 +11,6 @@ import { TestModuleMetadata, ComponentFixture, TestComponentRenderer } from '@an
|
|
|
11
11
|
* @see https://angular.io/api/core/testing/TestModuleMetadata
|
|
12
12
|
*/
|
|
13
13
|
interface MountConfig<T> extends TestModuleMetadata {
|
|
14
|
-
/**
|
|
15
|
-
* @memberof MountConfig
|
|
16
|
-
* @description flag to automatically create a cy.spy() for every component @Output() property
|
|
17
|
-
* @example
|
|
18
|
-
* export class ButtonComponent {
|
|
19
|
-
* @Output clicked = new EventEmitter()
|
|
20
|
-
* }
|
|
21
|
-
*
|
|
22
|
-
* cy.mount(ButtonComponent, { autoSpyOutputs: true })
|
|
23
|
-
* cy.get('@clickedSpy).should('have.been.called')
|
|
24
|
-
*/
|
|
25
|
-
autoSpyOutputs?: boolean;
|
|
26
|
-
/**
|
|
27
|
-
* @memberof MountConfig
|
|
28
|
-
* @description flag defaulted to true to automatically detect changes in your components
|
|
29
|
-
*/
|
|
30
|
-
autoDetectChanges?: boolean;
|
|
31
14
|
/**
|
|
32
15
|
* @memberof MountConfig
|
|
33
16
|
* @example
|
|
@@ -133,4 +116,5 @@ declare function mount<T>(component: Type<T> | string, config?: MountConfig<T>):
|
|
|
133
116
|
*/
|
|
134
117
|
declare const createOutputSpy: <T>(alias: string) => any;
|
|
135
118
|
|
|
136
|
-
export { CypressTestComponentRenderer,
|
|
119
|
+
export { CypressTestComponentRenderer, createOutputSpy, mount };
|
|
120
|
+
export type { MountConfig, MountResponse };
|
|
@@ -5,53 +5,51 @@
|
|
|
5
5
|
* Released under the MIT License
|
|
6
6
|
*/
|
|
7
7
|
|
|
8
|
-
import 'zone.js';
|
|
9
|
-
import 'zone.js/testing';
|
|
10
8
|
import { CommonModule } from '@angular/common';
|
|
11
|
-
import { Injectable, Component, EventEmitter, ErrorHandler, SimpleChange } from '@angular/core';
|
|
9
|
+
import { Injectable, Component, EventEmitter, ErrorHandler, provideZonelessChangeDetection, SimpleChange } from '@angular/core';
|
|
12
10
|
import { toObservable } from '@angular/core/rxjs-interop';
|
|
13
11
|
import { getTestBed, TestComponentRenderer, TestBed } from '@angular/core/testing';
|
|
14
|
-
import {
|
|
12
|
+
import { BrowserTestingModule, platformBrowserTesting } from '@angular/platform-browser/testing';
|
|
15
13
|
|
|
16
|
-
/******************************************************************************
|
|
17
|
-
Copyright (c) Microsoft Corporation.
|
|
18
|
-
|
|
19
|
-
Permission to use, copy, modify, and/or distribute this software for any
|
|
20
|
-
purpose with or without fee is hereby granted.
|
|
21
|
-
|
|
22
|
-
THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH
|
|
23
|
-
REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
|
|
24
|
-
AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT,
|
|
25
|
-
INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM
|
|
26
|
-
LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR
|
|
27
|
-
OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
|
|
28
|
-
PERFORMANCE OF THIS SOFTWARE.
|
|
29
|
-
***************************************************************************** */
|
|
30
|
-
/* global Reflect, Promise, SuppressedError, Symbol, Iterator */
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
function __rest(s, e) {
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
}
|
|
44
|
-
|
|
45
|
-
function __decorate(decorators, target, key, desc) {
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
}
|
|
51
|
-
|
|
52
|
-
typeof SuppressedError === "function" ? SuppressedError : function (error, suppressed, message) {
|
|
53
|
-
|
|
54
|
-
|
|
14
|
+
/******************************************************************************
|
|
15
|
+
Copyright (c) Microsoft Corporation.
|
|
16
|
+
|
|
17
|
+
Permission to use, copy, modify, and/or distribute this software for any
|
|
18
|
+
purpose with or without fee is hereby granted.
|
|
19
|
+
|
|
20
|
+
THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH
|
|
21
|
+
REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
|
|
22
|
+
AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT,
|
|
23
|
+
INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM
|
|
24
|
+
LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR
|
|
25
|
+
OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
|
|
26
|
+
PERFORMANCE OF THIS SOFTWARE.
|
|
27
|
+
***************************************************************************** */
|
|
28
|
+
/* global Reflect, Promise, SuppressedError, Symbol, Iterator */
|
|
29
|
+
|
|
30
|
+
|
|
31
|
+
function __rest(s, e) {
|
|
32
|
+
var t = {};
|
|
33
|
+
for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p) && e.indexOf(p) < 0)
|
|
34
|
+
t[p] = s[p];
|
|
35
|
+
if (s != null && typeof Object.getOwnPropertySymbols === "function")
|
|
36
|
+
for (var i = 0, p = Object.getOwnPropertySymbols(s); i < p.length; i++) {
|
|
37
|
+
if (e.indexOf(p[i]) < 0 && Object.prototype.propertyIsEnumerable.call(s, p[i]))
|
|
38
|
+
t[p[i]] = s[p[i]];
|
|
39
|
+
}
|
|
40
|
+
return t;
|
|
41
|
+
}
|
|
42
|
+
|
|
43
|
+
function __decorate(decorators, target, key, desc) {
|
|
44
|
+
var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
|
|
45
|
+
if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
|
|
46
|
+
else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
|
|
47
|
+
return c > 3 && r && Object.defineProperty(target, key, r), r;
|
|
48
|
+
}
|
|
49
|
+
|
|
50
|
+
typeof SuppressedError === "function" ? SuppressedError : function (error, suppressed, message) {
|
|
51
|
+
var e = new Error(message);
|
|
52
|
+
return e.name = "SuppressedError", e.error = error, e.suppressed = suppressed, e;
|
|
55
53
|
};
|
|
56
54
|
|
|
57
55
|
const ROOT_SELECTOR = '[data-cy-root]';
|
|
@@ -92,15 +90,10 @@ function setupHooks(optionalCallback) {
|
|
|
92
90
|
});
|
|
93
91
|
// @ts-ignore
|
|
94
92
|
Cypress.on('test:before:after:run:async', () => {
|
|
95
|
-
optionalCallback
|
|
93
|
+
optionalCallback?.();
|
|
96
94
|
});
|
|
97
95
|
}
|
|
98
96
|
|
|
99
|
-
/**
|
|
100
|
-
* @hack fixes "Mocha has already been patched with Zone" error.
|
|
101
|
-
*/
|
|
102
|
-
// @ts-ignore
|
|
103
|
-
window.Mocha['__zone_patch__'] = false;
|
|
104
97
|
let activeFixture = null;
|
|
105
98
|
let activeInternalSubscriptions = [];
|
|
106
99
|
function cleanup() {
|
|
@@ -155,6 +148,9 @@ function bootstrapModule(component, config) {
|
|
|
155
148
|
provide: ErrorHandler,
|
|
156
149
|
useClass: CypressAngularErrorHandler,
|
|
157
150
|
});
|
|
151
|
+
// allow for zoneless change detection inside the testing module.
|
|
152
|
+
// @see https://angular.dev/guide/zoneless#using-zoneless-in-testbed
|
|
153
|
+
testModuleMetaData.providers.push(provideZonelessChangeDetection());
|
|
158
154
|
// check if the component is a standalone component
|
|
159
155
|
if ((_a = component.ɵcmp) === null || _a === void 0 ? void 0 : _a.standalone) {
|
|
160
156
|
testModuleMetaData.imports.push(component);
|
|
@@ -221,20 +217,11 @@ function createComponentFixture(component) {
|
|
|
221
217
|
* @param {Type<T>} component Angular component being mounted
|
|
222
218
|
* @param {MountConfig<T>} config MountConfig
|
|
223
219
|
|
|
224
|
-
* @returns {ComponentFixture<T
|
|
220
|
+
* @returns {Promise<ComponentFixture<T>>} ComponentFixture
|
|
225
221
|
*/
|
|
226
222
|
function setupFixture(component, config) {
|
|
227
223
|
const fixture = getTestBed().createComponent(component);
|
|
228
224
|
setupComponent(config, fixture);
|
|
229
|
-
fixture.whenStable().then(() => {
|
|
230
|
-
var _a;
|
|
231
|
-
fixture.autoDetectChanges((_a = config.autoDetectChanges) !== null && _a !== void 0 ? _a : true);
|
|
232
|
-
}).catch((e) => {
|
|
233
|
-
// If this promise does not settle in Angular 19 it is rejected
|
|
234
|
-
// https://github.com/angular/angular/blob/main/CHANGELOG.md#1900-2024-11-19
|
|
235
|
-
// eslint-disable-next-line no-console
|
|
236
|
-
console.error(e);
|
|
237
|
-
});
|
|
238
225
|
return fixture;
|
|
239
226
|
}
|
|
240
227
|
// Best known way to currently detect whether or not a function is a signal is if the signal symbol exists.
|
|
@@ -303,11 +290,6 @@ function detectAndRegisterOutputSpyToSignal(config, component, key, injector) {
|
|
|
303
290
|
// @ts-expect-error
|
|
304
291
|
config.componentProperties[expectedChangeKey];
|
|
305
292
|
}
|
|
306
|
-
// since spies do NOT make change handlers by default, similar to the Output() decorator, we need to create the spy and subscribe to the signal
|
|
307
|
-
if (!changeKeyIfExists && config.autoSpyOutputs) {
|
|
308
|
-
component[expectedChangeKey] = createOutputSpy(`${expectedChangeKey}Spy`);
|
|
309
|
-
changeKeyIfExists = true;
|
|
310
|
-
}
|
|
311
293
|
if (changeKeyIfExists) {
|
|
312
294
|
const componentValue = component[key];
|
|
313
295
|
// if the user passed in a change key or we created one due to config.autoSpyOutputs being set to true for a given signal,
|
|
@@ -365,14 +347,6 @@ function setupComponent(config, fixture) {
|
|
|
365
347
|
}
|
|
366
348
|
});
|
|
367
349
|
}
|
|
368
|
-
if (config.autoSpyOutputs) {
|
|
369
|
-
Object.keys(component).forEach((key) => {
|
|
370
|
-
const property = component[key];
|
|
371
|
-
if (property instanceof EventEmitter) {
|
|
372
|
-
component[key] = createOutputSpy(`${key}Spy`);
|
|
373
|
-
}
|
|
374
|
-
});
|
|
375
|
-
}
|
|
376
350
|
// Manually call ngOnChanges when mounting components using the class syntax.
|
|
377
351
|
// This is necessary because we are assigning input values to the class directly
|
|
378
352
|
// on mount and therefore the ngOnChanges() lifecycle is not triggered.
|
|
@@ -442,18 +416,30 @@ function mount(component, config = {}) {
|
|
|
442
416
|
cleanup();
|
|
443
417
|
}
|
|
444
418
|
const componentFixture = initTestBed(component, config);
|
|
445
|
-
|
|
446
|
-
|
|
447
|
-
|
|
448
|
-
|
|
449
|
-
|
|
450
|
-
|
|
451
|
-
|
|
452
|
-
|
|
453
|
-
|
|
454
|
-
|
|
419
|
+
let mountResponsePromiseResolver;
|
|
420
|
+
let mountResponsePromiseRejector;
|
|
421
|
+
let mountResponsePromise = new Promise((resolve, reject) => {
|
|
422
|
+
mountResponsePromiseResolver = resolve;
|
|
423
|
+
mountResponsePromiseRejector = reject;
|
|
424
|
+
});
|
|
425
|
+
const fixture = setupFixture(componentFixture, config);
|
|
426
|
+
activeFixture = fixture;
|
|
427
|
+
fixture.whenStable().then(() => {
|
|
428
|
+
const mountResponse = {
|
|
429
|
+
fixture,
|
|
430
|
+
component: fixture.componentInstance,
|
|
431
|
+
};
|
|
432
|
+
const logMessage = typeof component === 'string' ? 'Component' : componentFixture.name;
|
|
433
|
+
Cypress.log({
|
|
434
|
+
name: 'mount',
|
|
435
|
+
message: logMessage,
|
|
436
|
+
consoleProps: () => ({ result: mountResponse }),
|
|
437
|
+
});
|
|
438
|
+
mountResponsePromiseResolver(mountResponse);
|
|
439
|
+
}).catch((error) => {
|
|
440
|
+
mountResponsePromiseRejector(error);
|
|
455
441
|
});
|
|
456
|
-
return cy.wrap(
|
|
442
|
+
return cy.wrap(mountResponsePromise, { log: false });
|
|
457
443
|
}
|
|
458
444
|
/**
|
|
459
445
|
* Creates a new Event Emitter and then spies on it's `emit` method
|
|
@@ -485,7 +471,7 @@ const createOutputSpy = (alias) => {
|
|
|
485
471
|
return emitter;
|
|
486
472
|
};
|
|
487
473
|
// Only needs to run once, we reset before each test
|
|
488
|
-
getTestBed().initTestEnvironment(
|
|
474
|
+
getTestBed().initTestEnvironment(BrowserTestingModule, platformBrowserTesting(), {
|
|
489
475
|
teardown: { destroyAfterEach: false },
|
|
490
476
|
});
|
|
491
477
|
setupHooks(cleanup);
|
|
@@ -13,20 +13,18 @@
|
|
|
13
13
|
},
|
|
14
14
|
"dependencies": {},
|
|
15
15
|
"devDependencies": {
|
|
16
|
-
"@angular/common": "^
|
|
17
|
-
"@angular/core": "^
|
|
18
|
-
"@angular/platform-browser
|
|
16
|
+
"@angular/common": "^21.0.0",
|
|
17
|
+
"@angular/core": "^21.0.0",
|
|
18
|
+
"@angular/platform-browser": "^21.0.0",
|
|
19
19
|
"@cypress/mount-utils": "0.0.0-development",
|
|
20
|
-
"rollup": "^4.
|
|
21
|
-
"typescript": "~5.
|
|
22
|
-
"zone.js": "~0.14.6"
|
|
20
|
+
"rollup": "^4.60.2",
|
|
21
|
+
"typescript": "~5.9.2"
|
|
23
22
|
},
|
|
24
23
|
"peerDependencies": {
|
|
25
|
-
"@angular/common": ">=
|
|
26
|
-
"@angular/core": ">=
|
|
27
|
-
"@angular/platform-browser
|
|
28
|
-
"rxjs": ">=7.
|
|
29
|
-
"zone.js": ">=0.14.0"
|
|
24
|
+
"@angular/common": ">=21.0.0",
|
|
25
|
+
"@angular/core": ">=21.0.0",
|
|
26
|
+
"@angular/platform-browser": ">=21.0.0",
|
|
27
|
+
"rxjs": ">=7.8.0"
|
|
30
28
|
},
|
|
31
29
|
"files": [
|
|
32
30
|
"dist"
|
|
@@ -44,7 +42,8 @@
|
|
|
44
42
|
"cypress",
|
|
45
43
|
"cypress-io",
|
|
46
44
|
"test",
|
|
47
|
-
"testing"
|
|
45
|
+
"testing",
|
|
46
|
+
"zoneless"
|
|
48
47
|
],
|
|
49
48
|
"contributors": [
|
|
50
49
|
{
|
package/angular/dist/index.d.ts
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
/// <reference types="cypress" />
|
|
2
2
|
|
|
3
3
|
import { InputSignal, WritableSignal, Type } from '@angular/core';
|
|
4
|
-
import { TestModuleMetadata, ComponentFixture
|
|
4
|
+
import { TestComponentRenderer, TestModuleMetadata, ComponentFixture } from '@angular/core/testing';
|
|
5
5
|
|
|
6
6
|
/**
|
|
7
7
|
* Additional module configurations needed while mounting the component, like
|
|
@@ -11,23 +11,6 @@ import { TestModuleMetadata, ComponentFixture, TestComponentRenderer } from '@an
|
|
|
11
11
|
* @see https://angular.io/api/core/testing/TestModuleMetadata
|
|
12
12
|
*/
|
|
13
13
|
interface MountConfig<T> extends TestModuleMetadata {
|
|
14
|
-
/**
|
|
15
|
-
* @memberof MountConfig
|
|
16
|
-
* @description flag to automatically create a cy.spy() for every component @Output() property
|
|
17
|
-
* @example
|
|
18
|
-
* export class ButtonComponent {
|
|
19
|
-
* @Output clicked = new EventEmitter()
|
|
20
|
-
* }
|
|
21
|
-
*
|
|
22
|
-
* cy.mount(ButtonComponent, { autoSpyOutputs: true })
|
|
23
|
-
* cy.get('@clickedSpy).should('have.been.called')
|
|
24
|
-
*/
|
|
25
|
-
autoSpyOutputs?: boolean;
|
|
26
|
-
/**
|
|
27
|
-
* @memberof MountConfig
|
|
28
|
-
* @description flag defaulted to true to automatically detect changes in your components
|
|
29
|
-
*/
|
|
30
|
-
autoDetectChanges?: boolean;
|
|
31
14
|
/**
|
|
32
15
|
* @memberof MountConfig
|
|
33
16
|
* @example
|
|
@@ -133,4 +116,5 @@ declare function mount<T>(component: Type<T> | string, config?: MountConfig<T>):
|
|
|
133
116
|
*/
|
|
134
117
|
declare const createOutputSpy: <T>(alias: string) => any;
|
|
135
118
|
|
|
136
|
-
export { CypressTestComponentRenderer,
|
|
119
|
+
export { CypressTestComponentRenderer, createOutputSpy, mount };
|
|
120
|
+
export type { MountConfig, MountResponse };
|
package/angular/dist/index.js
CHANGED
|
@@ -5,53 +5,51 @@
|
|
|
5
5
|
* Released under the MIT License
|
|
6
6
|
*/
|
|
7
7
|
|
|
8
|
-
import 'zone.js';
|
|
9
|
-
import 'zone.js/testing';
|
|
10
8
|
import { CommonModule } from '@angular/common';
|
|
11
|
-
import { Injectable, Component, EventEmitter, ErrorHandler, SimpleChange } from '@angular/core';
|
|
9
|
+
import { Injectable, Component, EventEmitter, ErrorHandler, provideZonelessChangeDetection, SimpleChange } from '@angular/core';
|
|
12
10
|
import { toObservable } from '@angular/core/rxjs-interop';
|
|
13
11
|
import { getTestBed, TestComponentRenderer, TestBed } from '@angular/core/testing';
|
|
14
|
-
import {
|
|
12
|
+
import { BrowserTestingModule, platformBrowserTesting } from '@angular/platform-browser/testing';
|
|
15
13
|
|
|
16
|
-
/******************************************************************************
|
|
17
|
-
Copyright (c) Microsoft Corporation.
|
|
18
|
-
|
|
19
|
-
Permission to use, copy, modify, and/or distribute this software for any
|
|
20
|
-
purpose with or without fee is hereby granted.
|
|
21
|
-
|
|
22
|
-
THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH
|
|
23
|
-
REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
|
|
24
|
-
AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT,
|
|
25
|
-
INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM
|
|
26
|
-
LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR
|
|
27
|
-
OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
|
|
28
|
-
PERFORMANCE OF THIS SOFTWARE.
|
|
29
|
-
***************************************************************************** */
|
|
30
|
-
/* global Reflect, Promise, SuppressedError, Symbol, Iterator */
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
function __rest(s, e) {
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
}
|
|
44
|
-
|
|
45
|
-
function __decorate(decorators, target, key, desc) {
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
}
|
|
51
|
-
|
|
52
|
-
typeof SuppressedError === "function" ? SuppressedError : function (error, suppressed, message) {
|
|
53
|
-
|
|
54
|
-
|
|
14
|
+
/******************************************************************************
|
|
15
|
+
Copyright (c) Microsoft Corporation.
|
|
16
|
+
|
|
17
|
+
Permission to use, copy, modify, and/or distribute this software for any
|
|
18
|
+
purpose with or without fee is hereby granted.
|
|
19
|
+
|
|
20
|
+
THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH
|
|
21
|
+
REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
|
|
22
|
+
AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT,
|
|
23
|
+
INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM
|
|
24
|
+
LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR
|
|
25
|
+
OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
|
|
26
|
+
PERFORMANCE OF THIS SOFTWARE.
|
|
27
|
+
***************************************************************************** */
|
|
28
|
+
/* global Reflect, Promise, SuppressedError, Symbol, Iterator */
|
|
29
|
+
|
|
30
|
+
|
|
31
|
+
function __rest(s, e) {
|
|
32
|
+
var t = {};
|
|
33
|
+
for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p) && e.indexOf(p) < 0)
|
|
34
|
+
t[p] = s[p];
|
|
35
|
+
if (s != null && typeof Object.getOwnPropertySymbols === "function")
|
|
36
|
+
for (var i = 0, p = Object.getOwnPropertySymbols(s); i < p.length; i++) {
|
|
37
|
+
if (e.indexOf(p[i]) < 0 && Object.prototype.propertyIsEnumerable.call(s, p[i]))
|
|
38
|
+
t[p[i]] = s[p[i]];
|
|
39
|
+
}
|
|
40
|
+
return t;
|
|
41
|
+
}
|
|
42
|
+
|
|
43
|
+
function __decorate(decorators, target, key, desc) {
|
|
44
|
+
var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
|
|
45
|
+
if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
|
|
46
|
+
else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
|
|
47
|
+
return c > 3 && r && Object.defineProperty(target, key, r), r;
|
|
48
|
+
}
|
|
49
|
+
|
|
50
|
+
typeof SuppressedError === "function" ? SuppressedError : function (error, suppressed, message) {
|
|
51
|
+
var e = new Error(message);
|
|
52
|
+
return e.name = "SuppressedError", e.error = error, e.suppressed = suppressed, e;
|
|
55
53
|
};
|
|
56
54
|
|
|
57
55
|
const ROOT_SELECTOR = '[data-cy-root]';
|
|
@@ -92,15 +90,10 @@ function setupHooks(optionalCallback) {
|
|
|
92
90
|
});
|
|
93
91
|
// @ts-ignore
|
|
94
92
|
Cypress.on('test:before:after:run:async', () => {
|
|
95
|
-
optionalCallback
|
|
93
|
+
optionalCallback?.();
|
|
96
94
|
});
|
|
97
95
|
}
|
|
98
96
|
|
|
99
|
-
/**
|
|
100
|
-
* @hack fixes "Mocha has already been patched with Zone" error.
|
|
101
|
-
*/
|
|
102
|
-
// @ts-ignore
|
|
103
|
-
window.Mocha['__zone_patch__'] = false;
|
|
104
97
|
let activeFixture = null;
|
|
105
98
|
let activeInternalSubscriptions = [];
|
|
106
99
|
function cleanup() {
|
|
@@ -155,6 +148,9 @@ function bootstrapModule(component, config) {
|
|
|
155
148
|
provide: ErrorHandler,
|
|
156
149
|
useClass: CypressAngularErrorHandler,
|
|
157
150
|
});
|
|
151
|
+
// allow for zoneless change detection inside the testing module.
|
|
152
|
+
// @see https://angular.dev/guide/zoneless#using-zoneless-in-testbed
|
|
153
|
+
testModuleMetaData.providers.push(provideZonelessChangeDetection());
|
|
158
154
|
// check if the component is a standalone component
|
|
159
155
|
if ((_a = component.ɵcmp) === null || _a === void 0 ? void 0 : _a.standalone) {
|
|
160
156
|
testModuleMetaData.imports.push(component);
|
|
@@ -221,20 +217,11 @@ function createComponentFixture(component) {
|
|
|
221
217
|
* @param {Type<T>} component Angular component being mounted
|
|
222
218
|
* @param {MountConfig<T>} config MountConfig
|
|
223
219
|
|
|
224
|
-
* @returns {ComponentFixture<T
|
|
220
|
+
* @returns {Promise<ComponentFixture<T>>} ComponentFixture
|
|
225
221
|
*/
|
|
226
222
|
function setupFixture(component, config) {
|
|
227
223
|
const fixture = getTestBed().createComponent(component);
|
|
228
224
|
setupComponent(config, fixture);
|
|
229
|
-
fixture.whenStable().then(() => {
|
|
230
|
-
var _a;
|
|
231
|
-
fixture.autoDetectChanges((_a = config.autoDetectChanges) !== null && _a !== void 0 ? _a : true);
|
|
232
|
-
}).catch((e) => {
|
|
233
|
-
// If this promise does not settle in Angular 19 it is rejected
|
|
234
|
-
// https://github.com/angular/angular/blob/main/CHANGELOG.md#1900-2024-11-19
|
|
235
|
-
// eslint-disable-next-line no-console
|
|
236
|
-
console.error(e);
|
|
237
|
-
});
|
|
238
225
|
return fixture;
|
|
239
226
|
}
|
|
240
227
|
// Best known way to currently detect whether or not a function is a signal is if the signal symbol exists.
|
|
@@ -303,11 +290,6 @@ function detectAndRegisterOutputSpyToSignal(config, component, key, injector) {
|
|
|
303
290
|
// @ts-expect-error
|
|
304
291
|
config.componentProperties[expectedChangeKey];
|
|
305
292
|
}
|
|
306
|
-
// since spies do NOT make change handlers by default, similar to the Output() decorator, we need to create the spy and subscribe to the signal
|
|
307
|
-
if (!changeKeyIfExists && config.autoSpyOutputs) {
|
|
308
|
-
component[expectedChangeKey] = createOutputSpy(`${expectedChangeKey}Spy`);
|
|
309
|
-
changeKeyIfExists = true;
|
|
310
|
-
}
|
|
311
293
|
if (changeKeyIfExists) {
|
|
312
294
|
const componentValue = component[key];
|
|
313
295
|
// if the user passed in a change key or we created one due to config.autoSpyOutputs being set to true for a given signal,
|
|
@@ -365,14 +347,6 @@ function setupComponent(config, fixture) {
|
|
|
365
347
|
}
|
|
366
348
|
});
|
|
367
349
|
}
|
|
368
|
-
if (config.autoSpyOutputs) {
|
|
369
|
-
Object.keys(component).forEach((key) => {
|
|
370
|
-
const property = component[key];
|
|
371
|
-
if (property instanceof EventEmitter) {
|
|
372
|
-
component[key] = createOutputSpy(`${key}Spy`);
|
|
373
|
-
}
|
|
374
|
-
});
|
|
375
|
-
}
|
|
376
350
|
// Manually call ngOnChanges when mounting components using the class syntax.
|
|
377
351
|
// This is necessary because we are assigning input values to the class directly
|
|
378
352
|
// on mount and therefore the ngOnChanges() lifecycle is not triggered.
|
|
@@ -442,18 +416,30 @@ function mount(component, config = {}) {
|
|
|
442
416
|
cleanup();
|
|
443
417
|
}
|
|
444
418
|
const componentFixture = initTestBed(component, config);
|
|
445
|
-
|
|
446
|
-
|
|
447
|
-
|
|
448
|
-
|
|
449
|
-
|
|
450
|
-
|
|
451
|
-
|
|
452
|
-
|
|
453
|
-
|
|
454
|
-
|
|
419
|
+
let mountResponsePromiseResolver;
|
|
420
|
+
let mountResponsePromiseRejector;
|
|
421
|
+
let mountResponsePromise = new Promise((resolve, reject) => {
|
|
422
|
+
mountResponsePromiseResolver = resolve;
|
|
423
|
+
mountResponsePromiseRejector = reject;
|
|
424
|
+
});
|
|
425
|
+
const fixture = setupFixture(componentFixture, config);
|
|
426
|
+
activeFixture = fixture;
|
|
427
|
+
fixture.whenStable().then(() => {
|
|
428
|
+
const mountResponse = {
|
|
429
|
+
fixture,
|
|
430
|
+
component: fixture.componentInstance,
|
|
431
|
+
};
|
|
432
|
+
const logMessage = typeof component === 'string' ? 'Component' : componentFixture.name;
|
|
433
|
+
Cypress.log({
|
|
434
|
+
name: 'mount',
|
|
435
|
+
message: logMessage,
|
|
436
|
+
consoleProps: () => ({ result: mountResponse }),
|
|
437
|
+
});
|
|
438
|
+
mountResponsePromiseResolver(mountResponse);
|
|
439
|
+
}).catch((error) => {
|
|
440
|
+
mountResponsePromiseRejector(error);
|
|
455
441
|
});
|
|
456
|
-
return cy.wrap(
|
|
442
|
+
return cy.wrap(mountResponsePromise, { log: false });
|
|
457
443
|
}
|
|
458
444
|
/**
|
|
459
445
|
* Creates a new Event Emitter and then spies on it's `emit` method
|
|
@@ -485,7 +471,7 @@ const createOutputSpy = (alias) => {
|
|
|
485
471
|
return emitter;
|
|
486
472
|
};
|
|
487
473
|
// Only needs to run once, we reset before each test
|
|
488
|
-
getTestBed().initTestEnvironment(
|
|
474
|
+
getTestBed().initTestEnvironment(BrowserTestingModule, platformBrowserTesting(), {
|
|
489
475
|
teardown: { destroyAfterEach: false },
|
|
490
476
|
});
|
|
491
477
|
setupHooks(cleanup);
|
package/angular/package.json
CHANGED
|
@@ -13,20 +13,18 @@
|
|
|
13
13
|
},
|
|
14
14
|
"dependencies": {},
|
|
15
15
|
"devDependencies": {
|
|
16
|
-
"@angular/common": "^
|
|
17
|
-
"@angular/core": "^
|
|
18
|
-
"@angular/platform-browser
|
|
16
|
+
"@angular/common": "^21.0.0",
|
|
17
|
+
"@angular/core": "^21.0.0",
|
|
18
|
+
"@angular/platform-browser": "^21.0.0",
|
|
19
19
|
"@cypress/mount-utils": "0.0.0-development",
|
|
20
|
-
"rollup": "^4.
|
|
21
|
-
"typescript": "~5.
|
|
22
|
-
"zone.js": "~0.14.6"
|
|
20
|
+
"rollup": "^4.60.2",
|
|
21
|
+
"typescript": "~5.9.2"
|
|
23
22
|
},
|
|
24
23
|
"peerDependencies": {
|
|
25
|
-
"@angular/common": ">=
|
|
26
|
-
"@angular/core": ">=
|
|
27
|
-
"@angular/platform-browser
|
|
28
|
-
"rxjs": ">=7.
|
|
29
|
-
"zone.js": ">=0.14.0"
|
|
24
|
+
"@angular/common": ">=21.0.0",
|
|
25
|
+
"@angular/core": ">=21.0.0",
|
|
26
|
+
"@angular/platform-browser": ">=21.0.0",
|
|
27
|
+
"rxjs": ">=7.8.0"
|
|
30
28
|
},
|
|
31
29
|
"files": [
|
|
32
30
|
"dist"
|
|
@@ -44,7 +42,8 @@
|
|
|
44
42
|
"cypress",
|
|
45
43
|
"cypress-io",
|
|
46
44
|
"test",
|
|
47
|
-
"testing"
|
|
45
|
+
"testing",
|
|
46
|
+
"zoneless"
|
|
48
47
|
],
|
|
49
48
|
"contributors": [
|
|
50
49
|
{
|
package/dist/bin/cypress
CHANGED
|
@@ -1,8 +1,8 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
2
|
'use strict';
|
|
3
3
|
|
|
4
|
-
var cli = require('../cli-
|
|
5
|
-
require('../xvfb-
|
|
4
|
+
var cli = require('../cli-BUzHfIQ2.js');
|
|
5
|
+
require('../xvfb-CbW2_YXR.js');
|
|
6
6
|
require('os');
|
|
7
7
|
require('bluebird');
|
|
8
8
|
require('@cypress/xvfb');
|
|
@@ -32,7 +32,7 @@ require('commander');
|
|
|
32
32
|
require('cli-table3');
|
|
33
33
|
require('dayjs');
|
|
34
34
|
require('dayjs/plugin/relativeTime');
|
|
35
|
-
require('../spawn-
|
|
35
|
+
require('../spawn-BNsy7yWl.js');
|
|
36
36
|
require('child_process');
|
|
37
37
|
require('listr2');
|
|
38
38
|
require('readline');
|