dceky 1.1.8 → 1.1.9

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/README.md CHANGED
@@ -63,3 +63,70 @@ This will regenerate configuration files, typescript declarations, and other ky
63
63
  QA people and CI systems should start tests using `npm run ky:start` because that ensures that no files, dependencies, or files will be changed on run.
64
64
 
65
65
  But, developers should run tests using `npm run ky:dev` because each time the tests are run, ky is automatically set up again, ensuring that ky files are up-to-date and running smoothly.
66
+
67
+ ### Writing Your Own Custom Commands
68
+
69
+ Custom commands are called using Ky (e.g. `ky.myCustomCommand()`), and you define them in the `commands` folder generated when you first setup Ky.
70
+
71
+ Create a new file when creating a custom command, and this file will take the following structure:
72
+ (e.g. myCustomCommand.ts)
73
+ ```ts
74
+ /// <reference types="cypress" />
75
+
76
+ /*----------------------------------------*/
77
+ /* ---------------- Type ---------------- */
78
+ /*----------------------------------------*/
79
+
80
+ declare global {
81
+ namespace Cypress {
82
+ interface Chainable {
83
+ /**
84
+ * My custom command
85
+ * @author Your name here
86
+ * @param any params
87
+ * @returns what is returned
88
+ */
89
+ myCustomCommand(
90
+ /* params here */
91
+ ): Chainable</* your return type */>;
92
+ }
93
+ }
94
+ }
95
+
96
+ /*----------------------------------------*/
97
+ /* --------------- Command -------------- */
98
+ /*----------------------------------------*/
99
+
100
+ const myCustomCommand = () => {
101
+ Cypress.Commands.add('myCustomCommand', (/* Function Params */) => {
102
+ /* Function Body */
103
+ });
104
+ };
105
+
106
+ /*----------------------------------------*/
107
+ /* --------------- Export --------------- */
108
+ /*----------------------------------------*/
109
+
110
+ export default myCustomCommand;
111
+
112
+ ```
113
+
114
+ When you finish writing your command, run `npm run ky:setup`, which will let Ky initialize your command. You can now use your command in your tests!
115
+
116
+ All return types should be [Chainable](https://learn.cypress.io/cypress-fundamentals/command-chaining). For example, if your custom command returns a boolean, the return type should be `Chainable<boolean>`, and you would use it in a test like this:
117
+
118
+ ```ts
119
+ ky.myCustomCommand().then((result) => {
120
+ // result is typed as boolean here
121
+ });
122
+ ```
123
+
124
+ #### Create your own return value?
125
+
126
+ Any time you don't return the value directly from another ky or Cypress command (for example, returning a primitive value or an object that you create), make sure to wrap it (`ky.wrap()`) so it can be properly chained. For example:
127
+
128
+ ```ts
129
+ const myReturnValue = { hello: 'world' };
130
+
131
+ return ky.wrap(myReturnValue);
132
+ ```
@@ -10,7 +10,7 @@ const getId = () => {
10
10
  .get(selector)
11
11
  .invoke('attr', 'id')
12
12
  .then((attr) => {
13
- return attr;
13
+ return attr || '';
14
14
  }));
15
15
  });
16
16
  };
@@ -1 +1 @@
1
- {"version":3,"file":"getId.js","sourceRoot":"","sources":["../../../src/commands/getId.ts"],"names":[],"mappings":";AAAA,iCAAiC;;AAsBjC,4CAA4C;AAC5C,4CAA4C;AAC5C,4CAA4C;AAE5C,MAAM,KAAK,GAAG,GAAG,EAAE;IACjB,OAAO,CAAC,QAAQ,CAAC,GAAG,CAAC,OAAO,EAAE,CAAC,QAAgB,EAAE,EAAE;QACjD,OAAO,CACL,EAAE;aACC,GAAG,CAAC,QAAQ,CAAC;aACb,MAAM,CAAC,MAAM,EAAE,IAAI,CAAC;aACpB,IAAI,CAAC,CAAC,IAAI,EAAE,EAAE;YACb,OAAO,IAAI,CAAC;QACd,CAAC,CAAC,CACL,CAAC;IACJ,CAAC,CAAC,CAAC;AACL,CAAC,CAAC;AAEF,4CAA4C;AAC5C,4CAA4C;AAC5C,4CAA4C;AAE5C,kBAAe,KAAK,CAAC"}
1
+ {"version":3,"file":"getId.js","sourceRoot":"","sources":["../../../src/commands/getId.ts"],"names":[],"mappings":";AAAA,iCAAiC;;AAsBjC,4CAA4C;AAC5C,4CAA4C;AAC5C,4CAA4C;AAE5C,MAAM,KAAK,GAAG,GAAG,EAAE;IACjB,OAAO,CAAC,QAAQ,CAAC,GAAG,CAAC,OAAO,EAAE,CAAC,QAAgB,EAAE,EAAE;QACjD,OAAO,CACL,EAAE;aACC,GAAG,CAAC,QAAQ,CAAC;aACb,MAAM,CAAC,MAAM,EAAE,IAAI,CAAC;aACpB,IAAI,CAAC,CAAC,IAAI,EAAE,EAAE;YACb,OAAO,IAAI,IAAI,EAAE,CAAC;QACpB,CAAC,CAAC,CACL,CAAC;IACJ,CAAC,CAAC,CAAC;AACL,CAAC,CAAC;AAEF,4CAA4C;AAC5C,4CAA4C;AAC5C,4CAA4C;AAE5C,kBAAe,KAAK,CAAC"}
@@ -102,7 +102,7 @@ const launchAs = () => {
102
102
  });
103
103
  // Launch via the sessionless launch URL
104
104
  const launchURL = sessionlessLaunchInfo.url;
105
- cy.request(launchURL).then((response) => {
105
+ cy.sendRequest({ url: launchURL }).then((response) => {
106
106
  const { action, fields } = (0, getFormData_1.default)({ html: response.body });
107
107
  cy.visit({
108
108
  url: action,
@@ -1 +1 @@
1
- {"version":3,"file":"launchAs.js","sourceRoot":"","sources":["../../../src/commands/launchAs.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"launchAs.js","sourceRoot":"","sources":["../../../src/commands/launchAs.ts"],"names":[],"mappings":"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"}
@@ -33,7 +33,7 @@ const logIntoPorta = () => {
33
33
  }
34
34
  const htmlHeaders = { accept: 'text/html' };
35
35
  // Request 1: GET Cirrus Identity discovery page
36
- cy.request({
36
+ cy.sendRequest({
37
37
  url: LOGIN_PAGE,
38
38
  followRedirect: true,
39
39
  failOnStatusCode: false,
@@ -46,7 +46,7 @@ const logIntoPorta = () => {
46
46
  }
47
47
  const idpUrl = `${IDP_BASE_URL}${btnMatch[1]}`;
48
48
  // Request 2: GET HarvardKey IdP login page
49
- cy.request({
49
+ cy.sendRequest({
50
50
  url: idpUrl,
51
51
  followRedirect: true,
52
52
  failOnStatusCode: false,
@@ -58,7 +58,7 @@ const logIntoPorta = () => {
58
58
  throw new Error('Could not find login form action on HarvardKey page');
59
59
  }
60
60
  // Request 3: POST credentials to HarvardKey login form
61
- cy.request({
61
+ cy.sendRequest({
62
62
  method: loginMethod,
63
63
  url: loginFormUrl,
64
64
  form: true,
@@ -74,7 +74,7 @@ const logIntoPorta = () => {
74
74
  throw new Error('Could not find SAML form in login response');
75
75
  }
76
76
  // Request 4: POST SAML assertion to ACS
77
- return cy.request({
77
+ cy.sendRequest({
78
78
  method: samlMethod,
79
79
  url: samlFormUrl,
80
80
  form: true,
@@ -1 +1 @@
1
- {"version":3,"file":"logIntoPorta.js","sourceRoot":"","sources":["../../../src/commands/logIntoPorta.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"logIntoPorta.js","sourceRoot":"","sources":["../../../src/commands/logIntoPorta.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,23 @@
1
+ declare global {
2
+ namespace Cypress {
3
+ interface Chainable {
4
+ /**
5
+ * Send an HTTP request. For full documentation,
6
+ * see {@link https://docs.cypress.io/api/commands/request}
7
+ * and scroll down to the "Options" section
8
+ * @author Yuen Ler Chow
9
+ * @param options object containing all arguments
10
+ * @param options.url the URL to send the request to (required)
11
+ * @param options.method the HTTP method to use (default: "GET")
12
+ * @param [options.body] the body to send with the request
13
+ * @param [options.headers] any additional headers to send with the request
14
+ * @return chainable response (same shape as `cy.request`)
15
+ */
16
+ sendRequest(options: Partial<Cypress.RequestOptions> & {
17
+ url: string;
18
+ }): Chainable<Cypress.Response<any>>;
19
+ }
20
+ }
21
+ }
22
+ declare const sendRequest: () => void;
23
+ export default sendRequest;
@@ -0,0 +1,104 @@
1
+ "use strict";
2
+ /// <reference types="cypress" />
3
+ var __importDefault = (this && this.__importDefault) || function (mod) {
4
+ return (mod && mod.__esModule) ? mod : { "default": mod };
5
+ };
6
+ Object.defineProperty(exports, "__esModule", { value: true });
7
+ /**
8
+ * Wraps `cy.request` to handle two Cypress-on-WebKit (Playwright) cookie bugs:
9
+ *
10
+ * 1. **Outbound cookies are dropped.** WebKit's `cy.request` stores
11
+ * `Set-Cookie` responses in the jar but does NOT auto-attach them
12
+ * to subsequent `cy.request` calls. We work around this by reading
13
+ * the jar before the request and explicitly setting the `Cookie`
14
+ * header.
15
+ *
16
+ * 2. **Domain cookies are downgraded to host-only.** When a response
17
+ * sets a cookie with `Domain=example.com`, WebKit stores it as a
18
+ * host-only cookie on `example.com` instead of a domain cookie on
19
+ * `.example.com`, so it is never sent to subdomains. We work
20
+ * around this by parsing the `Set-Cookie` headers from the
21
+ * response (and any redirect hops) with `set-cookie-parser` and
22
+ * re-planting any cookie that had an explicit `Domain=` attribute
23
+ * as a leading-dot domain cookie via `cy.setCookie`.
24
+ *
25
+ * On Chrome and other browsers, both workarounds are effectively no-ops, so this is safe
26
+ * to use everywhere.
27
+ */
28
+ const set_cookie_parser_1 = __importDefault(require("set-cookie-parser"));
29
+ /*----------------------------------------*/
30
+ /* -------------- Helpers -------------- */
31
+ /*----------------------------------------*/
32
+ /**
33
+ * Build a `Cookie:` request header value from Cypress's cookie jar for the
34
+ * given URL's host. Skips RFC 6265 path matching since virtually no real
35
+ * server cares about cookie path scoping on incoming requests.
36
+ *
37
+ * @param url full request URL whose host drives cookie selection
38
+ * @return chainable cookie header string ("" if no cookies stored for the host)
39
+ */
40
+ const buildCookieHeader = (url) => {
41
+ const host = new URL(url).hostname;
42
+ return cy.getCookies({ domain: host }).then((cookies) => {
43
+ return cy.wrap(cookies.map((c) => { return `${c.name}=${c.value}`; }).join('; '), { log: false });
44
+ });
45
+ };
46
+ /**
47
+ * Walk the response (plus all redirect hops) and re-plant any cookie whose
48
+ * `Set-Cookie` carried an explicit `Domain=` attribute as a domain cookie
49
+ * with a leading dot. Fixes WebKit's "domain cookie downgraded to host-only"
50
+ * bug. Cookies without an explicit `Domain=` attribute are left alone.
51
+ *
52
+ * @param response the response yielded by `cy.request`
53
+ */
54
+ const replantDomainCookies = (response) => {
55
+ var _a;
56
+ const redirectHops = (_a = response.allRequestResponses) !== null && _a !== void 0 ? _a : [{ 'Response Headers': response.headers }];
57
+ redirectHops.forEach((redirectHop) => {
58
+ var _a;
59
+ const setCookieHeader = (_a = redirectHop['Response Headers']) === null || _a === void 0 ? void 0 : _a['set-cookie'];
60
+ if (!setCookieHeader)
61
+ return;
62
+ set_cookie_parser_1.default.parse(setCookieHeader, { decodeValues: false }).forEach((cookie) => {
63
+ var _a, _b, _c, _d, _e, _f;
64
+ // Only re-plant cookies that explicitly declared a Domain attribute;
65
+ // host-only cookies (no Domain) must stay host-only.
66
+ if (!cookie.domain)
67
+ return;
68
+ // Translate HTTP-wire SameSite values into the strings cy.setCookie expects.
69
+ const sameSiteMap = {
70
+ lax: 'lax',
71
+ strict: 'strict',
72
+ none: 'no_restriction',
73
+ };
74
+ cy.setCookie(cookie.name, cookie.value, {
75
+ domain: cookie.domain.startsWith('.') ? cookie.domain : `.${cookie.domain}`,
76
+ path: (_a = cookie.path) !== null && _a !== void 0 ? _a : '/',
77
+ secure: (_b = cookie.secure) !== null && _b !== void 0 ? _b : false,
78
+ httpOnly: (_c = cookie.httpOnly) !== null && _c !== void 0 ? _c : false,
79
+ sameSite: (_f = sameSiteMap[(_e = (_d = cookie.sameSite) === null || _d === void 0 ? void 0 : _d.toLowerCase()) !== null && _e !== void 0 ? _e : '']) !== null && _f !== void 0 ? _f : 'lax',
80
+ log: false,
81
+ });
82
+ });
83
+ });
84
+ };
85
+ /*----------------------------------------*/
86
+ /* --------------- Command -------------- */
87
+ /*----------------------------------------*/
88
+ const sendRequest = () => {
89
+ Cypress.Commands.add('sendRequest', (options) => {
90
+ return buildCookieHeader(options.url).then((cookieHeader) => {
91
+ var _a;
92
+ const mergedHeaders = Object.assign(Object.assign({}, ((_a = options.headers) !== null && _a !== void 0 ? _a : {})), (cookieHeader ? { cookie: cookieHeader } : {}));
93
+ return cy.request(Object.assign(Object.assign({}, options), { headers: mergedHeaders })).then((response) => {
94
+ replantDomainCookies(response);
95
+ return cy.wrap(response, { log: false });
96
+ });
97
+ });
98
+ });
99
+ };
100
+ /*----------------------------------------*/
101
+ /* --------------- Export --------------- */
102
+ /*----------------------------------------*/
103
+ exports.default = sendRequest;
104
+ //# sourceMappingURL=sendRequest.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"sendRequest.js","sourceRoot":"","sources":["../../../src/commands/sendRequest.ts"],"names":[],"mappings":"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"}
@@ -86,8 +86,12 @@ const generateReportHomepage = (reports, outputDir) => {
86
86
  screenshots.push({ href, name: rel });
87
87
  });
88
88
  }
89
+ const allTestsPassed = (typeof report.totalTests === 'number'
90
+ && typeof report.passedTests === 'number'
91
+ && report.passedTests === report.totalTests);
89
92
  return Object.assign(Object.assign({}, report), { relativeReportPath,
90
- screenshots });
93
+ screenshots,
94
+ allTestsPassed });
91
95
  });
92
96
  // Group by profile
93
97
  const reportsByProfile = {};
@@ -98,9 +102,9 @@ const generateReportHomepage = (reports, outputDir) => {
98
102
  reportsByProfile[report.profileName].push(report);
99
103
  });
100
104
  // Calculate summary stats
101
- const totalRuns = reports.length;
102
- const passedRuns = reports.filter((r) => { return r.success; }).length;
103
- const failedRuns = reports.filter((r) => { return !r.success; }).length;
105
+ const totalRuns = templateReports.length;
106
+ const passedRuns = templateReports.filter((r) => { return r.allTestsPassed; }).length;
107
+ const failedRuns = totalRuns - passedRuns;
104
108
  const profileCount = Object.keys(reportsByProfile).length;
105
109
  // Load and render EJS template
106
110
  const templatePath = path_1.default.join(__dirname, 'reportHomepage.ejs');
@@ -1 +1 @@
1
- {"version":3,"file":"generateReportHomepage.js","sourceRoot":"","sources":["../../../start/helpers/generateReportHomepage.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"generateReportHomepage.js","sourceRoot":"","sources":["../../../start/helpers/generateReportHomepage.ts"],"names":[],"mappings":"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"}
@@ -179,10 +179,20 @@
179
179
  background: #115293;
180
180
  border-color: #115293;
181
181
  }
182
+ .screenshots-header {
183
+ margin-top: 0.875rem;
184
+ font-weight: 600;
185
+ }
182
186
  .screenshot-list {
183
- list-style: none;
184
- padding-left: 0;
185
- margin-top: 0.5rem;
187
+ padding-left: 1.25rem;
188
+ padding-right: 0.5rem;
189
+ }
190
+ .screenshot-list li {
191
+ padding-bottom: 0.5rem;
192
+ overflow-wrap: anywhere;
193
+ }
194
+ .screenshot-list a {
195
+ color: #1976d2;
186
196
  }
187
197
  .no-report {
188
198
  color: #999;
@@ -240,10 +250,10 @@
240
250
  <h2 class="profile-title">📋 Profile: <%= profileName %></h2>
241
251
  <div class="report-grid">
242
252
  <% profileReports.forEach((report) => { %>
243
- <div class="report-card <%= report.success ? 'success' : 'failed' %>">
253
+ <div class="report-card <%= report.allTestsPassed ? 'success' : 'failed' %>">
244
254
  <div class="browser-name">🌐 <%= report.browser %></div>
245
- <span class="status <%= report.success ? 'success' : 'failed' %>">
246
- <%= report.success ? 'Passed' : 'Failed' %>
255
+ <span class="status <%= report.allTestsPassed ? 'success' : 'failed' %>">
256
+ <%= report.allTestsPassed ? 'Passed' : 'Failed' %>
247
257
  </span>
248
258
  <% if (report.totalTests !== undefined && report.passedTests !== undefined) { %>
249
259
  <div class="timestamp"><%= report.passedTests %>/<%= report.totalTests %> tests passing</div>
@@ -255,9 +265,10 @@
255
265
  <p class="no-report">Report not available</p>
256
266
  <% } %>
257
267
  <% if (report.screenshots && report.screenshots.length > 0) { %>
268
+ <div class="screenshots-header">📸 Screenshots from failed tests</div>
258
269
  <ul class="screenshot-list">
259
270
  <% report.screenshots.forEach((screenshot) => { %>
260
- <li><a href="<%= screenshot.href %>" class="report-link" target="_blank"><%= screenshot.name %></a></li>
271
+ <li><a href="<%= screenshot.href %>" target="_blank"><%= screenshot.name %></a></li>
261
272
  <% }) %>
262
273
  </ul>
263
274
  <% } %>
@@ -65,7 +65,7 @@ const runCypressHeadless = (opts) => {
65
65
  '--threads',
66
66
  numThreads.toString(),
67
67
  '-d',
68
- 'cypress/e2e/**/*',
68
+ "'cypress/e2e/**/*.ky.ts'",
69
69
  '-m',
70
70
  'false',
71
71
  '-a',
@@ -1 +1 @@
1
- {"version":3,"file":"runCypressHeadless.js","sourceRoot":"","sources":["../../../start/helpers/runCypressHeadless.ts"],"names":[],"mappings":";AAAA,+BAA+B;;;;;AAE/B,cAAc;AACd,iDAAsC;AACtC,gDAAwB;AACxB,4CAAoB;AAEpB,iBAAiB;AACjB,gEAAwC;AACxC,sFAA8D;AAC9D,kEAA0C;AAC1C,8EAAsD;AAKtD,mBAAmB;AACnB,uGAA+E;AAE/E;;;;;;;;;GASG;AACH,MAAM,kBAAkB,GAAG,CAAC,IAK3B,EAAsB,EAAE;IACvB,MAAM,EACJ,WAAW,EACX,OAAO,EACP,SAAS,EACT,UAAU,GAAG,mCAAyB,GACvC,GAAG,IAAI,CAAC;IAET,OAAO,IAAI,OAAO,CAAC,CAAC,OAAO,EAAE,MAAM,EAAE,EAAE;QACrC,MAAM,IAAI,GAAG,IAAA,qBAAW,GAAE,CAAC;QAE3B,iCAAiC;QACjC,IAAI,CAAC,YAAE,CAAC,UAAU,CAAC,SAAS,CAAC,EAAE,CAAC;YAC9B,YAAE,CAAC,SAAS,CAAC,SAAS,EAAE,EAAE,SAAS,EAAE,IAAI,EAAE,CAAC,CAAC;QAC/C,CAAC;QAED,2DAA2D;QAC3D,MAAM,QAAQ,GAAG,cAAI,CAAC,IAAI,CAAC,SAAS,EAAE,GAAG,WAAW,IAAI,OAAO,EAAE,CAAC,CAAC;QACnE,IAAI,CAAC,YAAE,CAAC,UAAU,CAAC,QAAQ,CAAC,EAAE,CAAC;YAC7B,YAAE,CAAC,SAAS,CAAC,QAAQ,EAAE,EAAE,SAAS,EAAE,IAAI,EAAE,CAAC,CAAC;QAC9C,CAAC;QAED,yCAAyC;QACzC,MAAM,mBAAmB,GAAG,cAAI,CAAC,IAAI,CAAC,QAAQ,EAAE,aAAa,CAAC,CAAC;QAC/D,IAAI,CAAC,YAAE,CAAC,UAAU,CAAC,mBAAmB,CAAC,EAAE,CAAC;YACxC,YAAE,CAAC,SAAS,CAAC,mBAAmB,EAAE,EAAE,SAAS,EAAE,IAAI,EAAE,CAAC,CAAC;QACzD,CAAC;QAED,MAAM,GAAG,mCACJ,OAAO,CAAC,GAAG,KACd,eAAe,EAAE,WAAW,EAC5B,OAAO,EAAE,OAAO,GACjB,CAAC;QAEF,OAAO,CAAC,GAAG,CAAC,mCAAmC,WAAW,MAAM,OAAO,EAAE,CAAC,CAAC;QAC3E,OAAO,CAAC,GAAG,CAAC,WAAW,QAAQ,IAAI,CAAC,CAAC;QAErC,qDAAqD;QACrD,MAAM,kBAAkB,GAAG,cAAI,CAAC,IAAI,CAAC,QAAQ,EAAE,sBAAsB,CAAC,CAAC;QACvE,MAAM,cAAc,GAAG,IAAA,gCAAsB,EAAC;YAC5C,UAAU,EAAE,SAAS;YACrB,WAAW;YACX,WAAW,EAAE,OAAO;SACrB,CAAC,CAAC;QACH,YAAE,CAAC,aAAa,CAAC,kBAAkB,EAAE,IAAI,CAAC,SAAS,CAAC,cAAc,EAAE,IAAI,EAAE,CAAC,CAAC,CAAC,CAAC;QAE9E,0EAA0E;QAC1E,MAAM,iBAAiB,GAAG,wBAAwB,OAAO,+BAA+B,mBAAmB,qEAAqE,kBAAkB,EAAE,CAAC;QAErM,OAAO,CAAC,GAAG,CAAC,yBAAyB,kBAAkB,EAAE,CAAC,CAAC;QAC3D,OAAO,CAAC,GAAG,CAAC,yBAAyB,cAAI,CAAC,IAAI,CAAC,QAAQ,EAAE,kBAAkB,CAAC,EAAE,CAAC,CAAC;QAEhF,MAAM,IAAI,GAAG;YACX,kBAAkB;YAClB,IAAI;YACJ,oBAAoB;YACpB,WAAW;YACX,UAAU,CAAC,QAAQ,EAAE;YACrB,IAAI;YACJ,kBAAkB;YAClB,IAAI;YACJ,OAAO;YACP,IAAI;YACJ,kCAAkC;YAClC,KAAK,iBAAiB,IAAI;SAC3B,CAAC;QAEF,MAAM,cAAc,GAAG,IAAA,qBAAK,EAAC,KAAK,EAAE,IAAI,EAAE;YACxC,GAAG,EAAE,IAAI;YACT,GAAG;YACH,KAAK,EAAE,SAAS;YAChB,KAAK,EAAE,IAAI;SACZ,CAAC,CAAC;QAEH,cAAc,CAAC,EAAE,CAAC,OAAO,EAAE,CAAC,IAAI,EAAE,EAAE;YAClC,MAAM,OAAO,GAAG,IAAI,KAAK,CAAC,CAAC;YAE3B,oEAAoE;YACpE,IAAI,eAAe,GAAG,IAAI,CAAC;YAC3B,IAAI,CAAC;gBACH,0DAA0D;gBAC1D,IAAA,sBAAY,EAAC;oBACX,UAAU,EAAE,SAAS;oBACrB,WAAW;oBACX,WAAW,EAAE,OAAO;iBACrB,CAAC,CAAC;gBAEH,0FAA0F;gBAC1F,IAAA,4BAAkB,EAAC;oBACjB,UAAU,EAAE,SAAS;oBACrB,WAAW;oBACX,WAAW,EAAE,OAAO;iBACrB,CAAC,CAAC;YACL,CAAC;YAAC,OAAO,WAAW,EAAE,CAAC;gBACrB,OAAO,CAAC,KAAK,CAAC,qCAAqC,WAAW,MAAM,OAAO,GAAG,EAAE,WAAW,CAAC,CAAC;gBAC7F,eAAe,GAAG,KAAK,CAAC;YAC1B,CAAC;YAED,6EAA6E;YAC7E,MAAM,UAAU,GAAG,cAAI,CAAC,IAAI,CAC1B,SAAS,EACT,GAAG,WAAW,IAAI,OAAO,EAAE,EAC3B,QAAQ,EACR,kBAAkB,CACnB,CAAC;YAEF,MAAM,MAAM,GAAc;gBACxB,WAAW;gBACX,OAAO;gBACP,OAAO,EAAE,OAAO,IAAI,eAAe;gBACnC,SAAS,EAAE,QAAQ;gBACnB,UAAU,EAAE,eAAe,CAAC,CAAC,CAAC,UAAU,CAAC,CAAC,CAAC,SAAS;aACrD,CAAC;YAEF,IAAI,OAAO,IAAI,eAAe,EAAE,CAAC;gBAC/B,OAAO,CAAC,GAAG,CAAC,kBAAkB,WAAW,MAAM,OAAO,EAAE,CAAC,CAAC;YAC5D,CAAC;iBAAM,IAAI,CAAC,eAAe,EAAE,CAAC;gBAC5B,OAAO,CAAC,GAAG,CAAC,gDAAgD,WAAW,MAAM,OAAO,EAAE,CAAC,CAAC;YAC1F,CAAC;iBAAM,CAAC;gBACN,OAAO,CAAC,GAAG,CAAC,eAAe,WAAW,MAAM,OAAO,gBAAgB,IAAI,GAAG,CAAC,CAAC;YAC9E,CAAC;YAED,OAAO,CAAC,MAAM,CAAC,CAAC;QAClB,CAAC,CAAC,CAAC;QAEH,cAAc,CAAC,EAAE,CAAC,OAAO,EAAE,CAAC,KAAK,EAAE,EAAE;YACnC,MAAM,CAAC,KAAK,CAAC,CAAC;QAChB,CAAC,CAAC,CAAC;IACL,CAAC,CAAC,CAAC;AACL,CAAC,CAAC;AAEF,kBAAe,kBAAkB,CAAC"}
1
+ {"version":3,"file":"runCypressHeadless.js","sourceRoot":"","sources":["../../../start/helpers/runCypressHeadless.ts"],"names":[],"mappings":"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"}
@@ -8,5 +8,6 @@ import ScreenshotInfo from './ScreenshotInfo';
8
8
  type TemplateReportInfo = ReportInfo & {
9
9
  relativeReportPath: string | null;
10
10
  screenshots: ScreenshotInfo[];
11
+ allTestsPassed: boolean;
11
12
  };
12
13
  export default TemplateReportInfo;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "dceky",
3
- "version": "1.1.8",
3
+ "version": "1.1.9",
4
4
  "description": "Cypress toolkit for Harvard DCE",
5
5
  "main": "./lib/src/index.js",
6
6
  "types": "./lib/src/index.d.ts",
@@ -37,7 +37,8 @@
37
37
  "cypress-iframe": "^1.0.1",
38
38
  "deepmerge": "4.3.1",
39
39
  "ejs": "^3.1.10",
40
- "prompt-sync": "^4.2.0"
40
+ "prompt-sync": "^4.2.0",
41
+ "set-cookie-parser": "^3.1.0"
41
42
  },
42
43
  "devDependencies": {
43
44
  "@types/deepmerge": "2.1.0",
@@ -31,7 +31,7 @@ const getId = () => {
31
31
  .get(selector)
32
32
  .invoke('attr', 'id')
33
33
  .then((attr) => {
34
- return attr;
34
+ return attr || '';
35
35
  })
36
36
  );
37
37
  });
@@ -157,7 +157,7 @@ const launchAs = () => {
157
157
 
158
158
  // Launch via the sessionless launch URL
159
159
  const launchURL = sessionlessLaunchInfo.url;
160
- cy.request(launchURL).then((response) => {
160
+ cy.sendRequest({ url: launchURL }).then((response) => {
161
161
  const { action, fields } = getFormData({ html: response.body });
162
162
  cy.visit({
163
163
  url: action,
@@ -69,7 +69,7 @@ const logIntoPorta = () => {
69
69
  const htmlHeaders = { accept: 'text/html' };
70
70
 
71
71
  // Request 1: GET Cirrus Identity discovery page
72
- cy.request({
72
+ cy.sendRequest({
73
73
  url: LOGIN_PAGE,
74
74
  followRedirect: true,
75
75
  failOnStatusCode: false,
@@ -86,7 +86,7 @@ const logIntoPorta = () => {
86
86
  const idpUrl = `${IDP_BASE_URL}${btnMatch[1]}`;
87
87
 
88
88
  // Request 2: GET HarvardKey IdP login page
89
- cy.request({
89
+ cy.sendRequest({
90
90
  url: idpUrl,
91
91
  followRedirect: true,
92
92
  failOnStatusCode: false,
@@ -103,7 +103,7 @@ const logIntoPorta = () => {
103
103
  }
104
104
 
105
105
  // Request 3: POST credentials to HarvardKey login form
106
- cy.request({
106
+ cy.sendRequest({
107
107
  method: loginMethod,
108
108
  url: loginFormUrl,
109
109
  form: true,
@@ -127,7 +127,7 @@ const logIntoPorta = () => {
127
127
  }
128
128
 
129
129
  // Request 4: POST SAML assertion to ACS
130
- return cy.request({
130
+ cy.sendRequest({
131
131
  method: samlMethod,
132
132
  url: samlFormUrl,
133
133
  form: true,
@@ -0,0 +1,139 @@
1
+ /// <reference types="cypress" />
2
+
3
+ /**
4
+ * Wraps `cy.request` to handle two Cypress-on-WebKit (Playwright) cookie bugs:
5
+ *
6
+ * 1. **Outbound cookies are dropped.** WebKit's `cy.request` stores
7
+ * `Set-Cookie` responses in the jar but does NOT auto-attach them
8
+ * to subsequent `cy.request` calls. We work around this by reading
9
+ * the jar before the request and explicitly setting the `Cookie`
10
+ * header.
11
+ *
12
+ * 2. **Domain cookies are downgraded to host-only.** When a response
13
+ * sets a cookie with `Domain=example.com`, WebKit stores it as a
14
+ * host-only cookie on `example.com` instead of a domain cookie on
15
+ * `.example.com`, so it is never sent to subdomains. We work
16
+ * around this by parsing the `Set-Cookie` headers from the
17
+ * response (and any redirect hops) with `set-cookie-parser` and
18
+ * re-planting any cookie that had an explicit `Domain=` attribute
19
+ * as a leading-dot domain cookie via `cy.setCookie`.
20
+ *
21
+ * On Chrome and other browsers, both workarounds are effectively no-ops, so this is safe
22
+ * to use everywhere.
23
+ */
24
+
25
+ import setCookieParser from 'set-cookie-parser';
26
+
27
+ /*----------------------------------------*/
28
+ /* ---------------- Type ---------------- */
29
+ /*----------------------------------------*/
30
+
31
+ declare global {
32
+ namespace Cypress {
33
+ interface Chainable {
34
+ /**
35
+ * Send an HTTP request. For full documentation,
36
+ * see {@link https://docs.cypress.io/api/commands/request}
37
+ * and scroll down to the "Options" section
38
+ * @author Yuen Ler Chow
39
+ * @param options object containing all arguments
40
+ * @param options.url the URL to send the request to (required)
41
+ * @param options.method the HTTP method to use (default: "GET")
42
+ * @param [options.body] the body to send with the request
43
+ * @param [options.headers] any additional headers to send with the request
44
+ * @return chainable response (same shape as `cy.request`)
45
+ */
46
+ sendRequest(
47
+ options: Partial<Cypress.RequestOptions> & { url: string },
48
+ ): Chainable<Cypress.Response<any>>;
49
+ }
50
+ }
51
+ }
52
+
53
+ /*----------------------------------------*/
54
+ /* -------------- Helpers -------------- */
55
+ /*----------------------------------------*/
56
+
57
+ /**
58
+ * Build a `Cookie:` request header value from Cypress's cookie jar for the
59
+ * given URL's host. Skips RFC 6265 path matching since virtually no real
60
+ * server cares about cookie path scoping on incoming requests.
61
+ *
62
+ * @param url full request URL whose host drives cookie selection
63
+ * @return chainable cookie header string ("" if no cookies stored for the host)
64
+ */
65
+ const buildCookieHeader = (url: string): Cypress.Chainable<string> => {
66
+ const host = new URL(url).hostname;
67
+ return cy.getCookies({ domain: host }).then((cookies) => {
68
+ return cy.wrap(
69
+ cookies.map((c) => { return `${c.name}=${c.value}`; }).join('; '),
70
+ { log: false },
71
+ );
72
+ });
73
+ };
74
+
75
+ /**
76
+ * Walk the response (plus all redirect hops) and re-plant any cookie whose
77
+ * `Set-Cookie` carried an explicit `Domain=` attribute as a domain cookie
78
+ * with a leading dot. Fixes WebKit's "domain cookie downgraded to host-only"
79
+ * bug. Cookies without an explicit `Domain=` attribute are left alone.
80
+ *
81
+ * @param response the response yielded by `cy.request`
82
+ */
83
+ const replantDomainCookies = (response: Cypress.Response<any>) => {
84
+ const redirectHops = response.allRequestResponses ?? [{ 'Response Headers': response.headers }];
85
+ redirectHops.forEach((redirectHop) => {
86
+ const setCookieHeader = (redirectHop as any)['Response Headers']?.['set-cookie'];
87
+ if (!setCookieHeader) return;
88
+ setCookieParser.parse(setCookieHeader, { decodeValues: false }).forEach((cookie) => {
89
+ // Only re-plant cookies that explicitly declared a Domain attribute;
90
+ // host-only cookies (no Domain) must stay host-only.
91
+ if (!cookie.domain) return;
92
+ // Translate HTTP-wire SameSite values into the strings cy.setCookie expects.
93
+ const sameSiteMap: { [key: string]: 'lax' | 'strict' | 'no_restriction' } = {
94
+ lax: 'lax',
95
+ strict: 'strict',
96
+ none: 'no_restriction',
97
+ };
98
+ cy.setCookie(cookie.name, cookie.value, {
99
+ domain: cookie.domain.startsWith('.') ? cookie.domain : `.${cookie.domain}`,
100
+ path: cookie.path ?? '/',
101
+ secure: cookie.secure ?? false,
102
+ httpOnly: cookie.httpOnly ?? false,
103
+ sameSite: sameSiteMap[cookie.sameSite?.toLowerCase() ?? ''] ?? 'lax',
104
+ log: false,
105
+ });
106
+ });
107
+ });
108
+ };
109
+
110
+ /*----------------------------------------*/
111
+ /* --------------- Command -------------- */
112
+ /*----------------------------------------*/
113
+
114
+ const sendRequest = () => {
115
+ Cypress.Commands.add(
116
+ 'sendRequest',
117
+ (options) => {
118
+ return buildCookieHeader(options.url).then((cookieHeader) => {
119
+ const mergedHeaders = {
120
+ ...(options.headers ?? {}),
121
+ ...(cookieHeader ? { cookie: cookieHeader } : {}),
122
+ };
123
+ return cy.request({
124
+ ...options,
125
+ headers: mergedHeaders,
126
+ }).then((response) => {
127
+ replantDomainCookies(response);
128
+ return cy.wrap(response, { log: false });
129
+ });
130
+ });
131
+ },
132
+ );
133
+ };
134
+
135
+ /*----------------------------------------*/
136
+ /* --------------- Export --------------- */
137
+ /*----------------------------------------*/
138
+
139
+ export default sendRequest;
@@ -104,10 +104,17 @@ const generateReportHomepage = (
104
104
  });
105
105
  }
106
106
 
107
+ const allTestsPassed = (
108
+ typeof report.totalTests === 'number'
109
+ && typeof report.passedTests === 'number'
110
+ && report.passedTests === report.totalTests
111
+ );
112
+
107
113
  return {
108
114
  ...report,
109
115
  relativeReportPath,
110
116
  screenshots,
117
+ allTestsPassed,
111
118
  };
112
119
  });
113
120
 
@@ -121,9 +128,9 @@ const generateReportHomepage = (
121
128
  });
122
129
 
123
130
  // Calculate summary stats
124
- const totalRuns = reports.length;
125
- const passedRuns = reports.filter((r) => { return r.success; }).length;
126
- const failedRuns = reports.filter((r) => { return !r.success; }).length;
131
+ const totalRuns = templateReports.length;
132
+ const passedRuns = templateReports.filter((r) => { return r.allTestsPassed; }).length;
133
+ const failedRuns = totalRuns - passedRuns;
127
134
  const profileCount = Object.keys(reportsByProfile).length;
128
135
 
129
136
  // Load and render EJS template
@@ -179,10 +179,20 @@
179
179
  background: #115293;
180
180
  border-color: #115293;
181
181
  }
182
+ .screenshots-header {
183
+ margin-top: 0.875rem;
184
+ font-weight: 600;
185
+ }
182
186
  .screenshot-list {
183
- list-style: none;
184
- padding-left: 0;
185
- margin-top: 0.5rem;
187
+ padding-left: 1.25rem;
188
+ padding-right: 0.5rem;
189
+ }
190
+ .screenshot-list li {
191
+ padding-bottom: 0.5rem;
192
+ overflow-wrap: anywhere;
193
+ }
194
+ .screenshot-list a {
195
+ color: #1976d2;
186
196
  }
187
197
  .no-report {
188
198
  color: #999;
@@ -240,10 +250,10 @@
240
250
  <h2 class="profile-title">📋 Profile: <%= profileName %></h2>
241
251
  <div class="report-grid">
242
252
  <% profileReports.forEach((report) => { %>
243
- <div class="report-card <%= report.success ? 'success' : 'failed' %>">
253
+ <div class="report-card <%= report.allTestsPassed ? 'success' : 'failed' %>">
244
254
  <div class="browser-name">🌐 <%= report.browser %></div>
245
- <span class="status <%= report.success ? 'success' : 'failed' %>">
246
- <%= report.success ? 'Passed' : 'Failed' %>
255
+ <span class="status <%= report.allTestsPassed ? 'success' : 'failed' %>">
256
+ <%= report.allTestsPassed ? 'Passed' : 'Failed' %>
247
257
  </span>
248
258
  <% if (report.totalTests !== undefined && report.passedTests !== undefined) { %>
249
259
  <div class="timestamp"><%= report.passedTests %>/<%= report.totalTests %> tests passing</div>
@@ -255,9 +265,10 @@
255
265
  <p class="no-report">Report not available</p>
256
266
  <% } %>
257
267
  <% if (report.screenshots && report.screenshots.length > 0) { %>
268
+ <div class="screenshots-header">📸 Screenshots from failed tests</div>
258
269
  <ul class="screenshot-list">
259
270
  <% report.screenshots.forEach((screenshot) => { %>
260
- <li><a href="<%= screenshot.href %>" class="report-link" target="_blank"><%= screenshot.name %></a></li>
271
+ <li><a href="<%= screenshot.href %>" target="_blank"><%= screenshot.name %></a></li>
261
272
  <% }) %>
262
273
  </ul>
263
274
  <% } %>
@@ -91,7 +91,7 @@ const runCypressHeadless = (opts: {
91
91
  '--threads',
92
92
  numThreads.toString(),
93
93
  '-d',
94
- 'cypress/e2e/**/*',
94
+ "'cypress/e2e/**/*.ky.ts'",
95
95
  '-m',
96
96
  'false',
97
97
  '-a',
@@ -9,7 +9,8 @@ type ReportInfo = {
9
9
  browser: string;
10
10
  // Path to the generated HTML report file
11
11
  reportPath: string;
12
- // True if the test run was successful
12
+ // True if the cypress-parallel process completed cleanly and the report was
13
+ // generated. This does NOT mean every test passed.
13
14
  success: boolean;
14
15
  // Human-readable timestamp of when the report was generated
15
16
  timestamp: string;
@@ -11,6 +11,8 @@ type TemplateReportInfo = ReportInfo & {
11
11
  relativeReportPath: string | null;
12
12
  // List of screenshots captured during this test run
13
13
  screenshots: ScreenshotInfo[];
14
+ // True if every test in the merged Mochawesome report passed
15
+ allTestsPassed: boolean;
14
16
  };
15
17
 
16
18
  export default TemplateReportInfo;