How to use this.sendDebuggerCommandFn method in Cypress

Best JavaScript code snippet using cypress

Run Cypress automation tests on LambdaTest cloud grid

Perform automation testing on 3000+ real desktop and mobile devices online.

cdp_automation.js

Source: cdp_automation.js Github

copy
1"use strict";
2/// <reference types='chrome'/>
3Object.defineProperty(exports, "__esModule", { value: true });
4exports.CdpAutomation = exports.isHostOnlyCookie = exports._cookieMatches = exports._domainIsWithinSuperdomain = exports.screencastOpts = void 0;
5const tslib_1 = require("tslib");
6const lodash_1 = (0, tslib_1.__importDefault)(require("lodash"));
7const bluebird_1 = (0, tslib_1.__importDefault)(require("bluebird"));
8const network_1 = require("../../../network");
9const debug_1 = (0, tslib_1.__importDefault)(require("debug"));
10const debugVerbose = (0, debug_1.default)('cypress-verbose:server:browsers:cdp_automation');
11function screencastOpts(everyNthFrame = Number(process.env.CYPRESS_EVERY_NTH_FRAME || 5)) {
12    return {
13        format: 'jpeg',
14        everyNthFrame,
15    };
16}
17exports.screencastOpts = screencastOpts;
18function convertSameSiteExtensionToCdp(str) {
19    return str ? ({
20        'no_restriction': 'None',
21        'lax': 'Lax',
22        'strict': 'Strict',
23    })[str] : str;
24}
25function convertSameSiteCdpToExtension(str) {
26    if (lodash_1.default.isUndefined(str)) {
27        return str;
28    }
29    if (str === 'None') {
30        return 'no_restriction';
31    }
32    return str.toLowerCase();
33}
34const _domainIsWithinSuperdomain = (domain, suffix) => {
35    const suffixParts = suffix.split('.').filter(lodash_1.default.identity);
36    const domainParts = domain.split('.').filter(lodash_1.default.identity);
37    return lodash_1.default.isEqual(suffixParts, domainParts.slice(domainParts.length - suffixParts.length));
38};
39exports._domainIsWithinSuperdomain = _domainIsWithinSuperdomain;
40const _cookieMatches = (cookie, filter) => {
41    if (filter.domain && !(cookie.domain && (0, exports._domainIsWithinSuperdomain)(cookie.domain, filter.domain))) {
42        return false;
43    }
44    if (filter.path && filter.path !== cookie.path) {
45        return false;
46    }
47    if (filter.name && filter.name !== cookie.name) {
48        return false;
49    }
50    return true;
51};
52exports._cookieMatches = _cookieMatches;
53// without this logic, a cookie being set on 'foo.com' will only be set for 'foo.com', not other subdomains
54function isHostOnlyCookie(cookie) {
55    if (cookie.domain[0] === '.')
56        return false;
57    const parsedDomain = network_1.cors.parseDomain(cookie.domain);
58    // make every cookie non-hostOnly
59    // unless it's a top-level domain (localhost, ...) or IP address
60    return parsedDomain && parsedDomain.tld !== cookie.domain;
61}
62exports.isHostOnlyCookie = isHostOnlyCookie;
63const normalizeGetCookieProps = (cookie) => {
64    if (cookie.expires === -1) {
65        // @ts-ignore
66        delete cookie.expires;
67    }
68    if (isHostOnlyCookie(cookie)) {
69        // @ts-ignore
70        cookie.hostOnly = true;
71    }
72    // @ts-ignore
73    cookie.sameSite = convertSameSiteCdpToExtension(cookie.sameSite);
74    // @ts-ignore
75    cookie.expirationDate = cookie.expires;
76    // @ts-ignore
77    delete cookie.expires;
78    // @ts-ignore
79    return cookie;
80};
81const normalizeGetCookies = (cookies) => {
82    return lodash_1.default.map(cookies, normalizeGetCookieProps);
83};
84const normalizeSetCookieProps = (cookie) => {
85    // this logic forms a SetCookie request that will be received by Chrome
86    // see MakeCookieFromProtocolValues for information on how this cookie data will be parsed
87    // @see https://cs.chromium.org/chromium/src/content/browser/devtools/protocol/network_handler.cc?l=246&rcl=786a9194459684dc7a6fded9cabfc0c9b9b37174
88    const setCookieRequest = (0, lodash_1.default)({
89        domain: cookie.domain,
90        path: cookie.path,
91        secure: cookie.secure,
92        httpOnly: cookie.httpOnly,
93        sameSite: convertSameSiteExtensionToCdp(cookie.sameSite),
94        expires: cookie.expirationDate,
95    })
96        // Network.setCookie will error on any undefined/null parameters
97        .omitBy(lodash_1.default.isNull)
98        .omitBy(lodash_1.default.isUndefined)
99        // set name and value at the end to get the correct typing
100        .extend({
101        name: cookie.name || '',
102        value: cookie.value || '',
103    })
104        .value();
105    // without this logic, a cookie being set on 'foo.com' will only be set for 'foo.com', not other subdomains
106    if (!cookie.hostOnly && isHostOnlyCookie(cookie)) {
107        setCookieRequest.domain = `.${cookie.domain}`;
108    }
109    if (cookie.hostOnly && !isHostOnlyCookie(cookie)) {
110        // @ts-ignore
111        delete cookie.hostOnly;
112    }
113    if (setCookieRequest.name.startsWith('__Host-')) {
114        setCookieRequest.url = `https://${cookie.domain}`;
115        delete setCookieRequest.domain;
116    }
117    return setCookieRequest;
118};
119const normalizeResourceType = (resourceType) => {
120    resourceType = resourceType ? resourceType.toLowerCase() : 'unknown';
121    if (validResourceTypes.includes(resourceType)) {
122        return resourceType;
123    }
124    if (resourceType === 'img') {
125        return 'image';
126    }
127    return ffToStandardResourceTypeMap[resourceType] || 'other';
128};
129// the intersection of what's valid in CDP and what's valid in FFCDP
130// Firefox: https://searchfox.org/mozilla-central/rev/98a9257ca2847fad9a19631ac76199474516b31e/remote/cdp/domains/parent/Network.jsm#22
131// CDP: https://chromedevtools.github.io/devtools-protocol/tot/Network/#type-ResourceType
132const validResourceTypes = ['fetch', 'xhr', 'websocket', 'stylesheet', 'script', 'image', 'font', 'cspviolationreport', 'ping', 'manifest', 'other'];
133const ffToStandardResourceTypeMap = {
134    'img': 'image',
135    'csp': 'cspviolationreport',
136    'webmanifest': 'manifest',
137};
138class CdpAutomation {
139    constructor(sendDebuggerCommandFn, onFn, automation) {
140        this.sendDebuggerCommandFn = sendDebuggerCommandFn;
141        this.automation = automation;
142        this.onNetworkRequestWillBeSent = (params) => {
143            var _a, _b;
144            debugVerbose('received networkRequestWillBeSent %o', params);
145            let url = params.request.url;
146            // in Firefox, the hash is incorrectly included in the URL: https://bugzilla.mozilla.org/show_bug.cgi?id=1715366
147            if (url.includes('#'))
148                url = url.slice(0, url.indexOf('#'));
149            // Firefox: https://searchfox.org/mozilla-central/rev/98a9257ca2847fad9a19631ac76199474516b31e/remote/cdp/domains/parent/Network.jsm#397
150            // Firefox lacks support for urlFragment and initiator, two nice-to-haves
151            const browserPreRequest = {
152                requestId: params.requestId,
153                method: params.request.method,
154                url,
155                headers: params.request.headers,
156                resourceType: normalizeResourceType(params.type),
157                originalResourceType: params.type,
158            };
159            (_b = (_a = this.automation).onBrowserPreRequest) === null || _b === void 0 ? void 0 : _b.call(_a, browserPreRequest);
160        };
161        this.onResponseReceived = (params) => {
162            var _a, _b;
163            const browserResponseReceived = {
164                requestId: params.requestId,
165                status: params.response.status,
166                headers: params.response.headers,
167            };
168            (_b = (_a = this.automation).onRequestEvent) === null || _b === void 0 ? void 0 : _b.call(_a, 'response:received', browserResponseReceived);
169        };
170        this.getAllCookies = (filter) => {
171            return this.sendDebuggerCommandFn('Network.getAllCookies')
172                .then((result) => {
173                return normalizeGetCookies(result.cookies)
174                    .filter((cookie) => {
175                    const matches = (0, exports._cookieMatches)(cookie, filter);
176                    debugVerbose('cookie matches filter? %o', { matches, cookie, filter });
177                    return matches;
178                });
179            });
180        };
181        this.getCookiesByUrl = (url) => {
182            return this.sendDebuggerCommandFn('Network.getCookies', {
183                urls: [url],
184            })
185                .then((result) => {
186                return normalizeGetCookies(result.cookies)
187                    .filter((cookie) => {
188                    return !(url.startsWith('http:') && cookie.secure);
189                });
190            });
191        };
192        this.getCookie = (filter) => {
193            return this.getAllCookies(filter)
194                .then((cookies) => {
195                return lodash_1.default.get(cookies, 0, null);
196            });
197        };
198        this.onRequest = (message, data) => {
199            let setCookie;
200            switch (message) {
201                case 'get:cookies':
202                    if (data.url) {
203                        return this.getCookiesByUrl(data.url);
204                    }
205                    return this.getAllCookies(data);
206                case 'get:cookie':
207                    return this.getCookie(data);
208                case 'set:cookie':
209                    setCookie = normalizeSetCookieProps(data);
210                    return this.sendDebuggerCommandFn('Network.setCookie', setCookie)
211                        .then((result) => {
212                        if (!result.success) {
213                            // i wish CDP provided some more detail here, but this is really it in v1.3
214                            // @see https://chromedevtools.github.io/devtools-protocol/tot/Network/#method-setCookie
215                            throw new Error(`Network.setCookie failed to set cookie: ${JSON.stringify(setCookie)}`);
216                        }
217                        return this.getCookie(data);
218                    });
219                case 'set:cookies':
220                    setCookie = data.map((cookie) => normalizeSetCookieProps(cookie));
221                    return this.sendDebuggerCommandFn('Network.clearBrowserCookies')
222                        .then(() => {
223                        return this.sendDebuggerCommandFn('Network.setCookies', { cookies: setCookie });
224                    });
225                case 'clear:cookie':
226                    return this.getCookie(data)
227                        // tap, so we can resolve with the value of the removed cookie
228                        // also, getting the cookie via CDP first will ensure that we send a cookie `domain` to CDP
229                        // that matches the cookie domain that is really stored
230                        .tap((cookieToBeCleared) => {
231                        if (!cookieToBeCleared) {
232                            return;
233                        }
234                        return this.sendDebuggerCommandFn('Network.deleteCookies', lodash_1.default.pick(cookieToBeCleared, 'name', 'domain'));
235                    });
236                case 'clear:cookies':
237                    return bluebird_1.default.mapSeries(data, (cookie) => (0, tslib_1.__awaiter)(this, void 0, void 0, function* () {
238                        // resolve with the value of the removed cookie
239                        // also, getting the cookie via CDP first will ensure that we send a cookie `domain` to CDP
240                        // that matches the cookie domain that is really stored
241                        const cookieToBeCleared = yield this.getCookie(cookie);
242                        if (!cookieToBeCleared)
243                            return;
244                        yield this.sendDebuggerCommandFn('Network.deleteCookies', lodash_1.default.pick(cookieToBeCleared, 'name', 'domain'));
245                        return cookieToBeCleared;
246                    }));
247                case 'is:automation:client:connected':
248                    return true;
249                case 'remote:debugger:protocol':
250                    return this.sendDebuggerCommandFn(data.command, data.params);
251                case 'take:screenshot':
252                    return this.sendDebuggerCommandFn('Page.captureScreenshot', { format: 'png' })
253                        .catch((err) => {
254                        throw new Error(`The browser responded with an error when Cypress attempted to take a screenshot.\n\nDetails:\n${err.message}`);
255                    })
256                        .then(({ data }) => {
257                        return `data:image/png;base64,${data}`;
258                    });
259                default:
260                    throw new Error(`No automation handler registered for: '${message}'`);
261            }
262        };
263        onFn('Network.requestWillBeSent', this.onNetworkRequestWillBeSent);
264        onFn('Network.responseReceived', this.onResponseReceived);
265        sendDebuggerCommandFn('Network.enable', {
266            maxTotalBufferSize: 0,
267            maxResourceBufferSize: 0,
268            maxPostDataSize: 0,
269        });
270    }
271}
272exports.CdpAutomation = CdpAutomation;
273
Full Screen

Accelerate Your Automation Test Cycles With LambdaTest

Leverage LambdaTest’s cloud-based platform to execute your automation tests in parallel and trim down your test execution time significantly. Your first 100 automation testing minutes are on us.

Try LambdaTest

Run JavaScript Tests on LambdaTest Cloud Grid

Execute automation tests with Cypress on a cloud-based Grid of 3000+ real browsers and operating systems for both web and mobile applications.

Test now for Free
LambdaTestX

We use cookies to give you the best experience. Cookies help to provide a more personalized experience and relevant advertising for you, and web analytics for us. Learn More in our Cookies policy, Privacy & Terms of service

Allow Cookie
Sarah

I hope you find the best code examples for your project.

If you want to accelerate automated browser testing, try LambdaTest. Your first 100 automation testing minutes are FREE.

Sarah Elson (Product & Growth Lead)