From cbcc609fa16d51bb7bce30207e2ef597497db1f9 Mon Sep 17 00:00:00 2001 From: Zev Isert Date: Fri, 19 Feb 2021 11:50:59 -0800 Subject: [PATCH] fix: return non-secure cookies with HTTPS URLs (#5507) Cookies have a "Secure" attribute which tells the browsers that a given cookie should only be sent via HTTPS. In it's absense "Secure" is falsy and these cookies should be sent with both HTTP and HTTPS requests. Playwright now returns only the "Non-Secure" cookies for HTTP URLs, and both "Secure" and "Non-Secure" cookies for HTTPS URLs. Fixes #5504 --- src/server/network.ts | 2 +- test/browsercontext-cookies.spec.ts | 57 +++++++++++++++++++++++++---- 2 files changed, 50 insertions(+), 9 deletions(-) diff --git a/src/server/network.ts b/src/server/network.ts index ba310865a9..bf594a7233 100644 --- a/src/server/network.ts +++ b/src/server/network.ts @@ -36,7 +36,7 @@ export function filterCookies(cookies: types.NetworkCookie[], urls: string[]): t continue; if (!parsedURL.pathname.startsWith(c.path)) continue; - if ((parsedURL.protocol === 'https:') !== c.secure) + if (parsedURL.protocol !== 'https:' && c.secure) continue; return true; } diff --git a/test/browsercontext-cookies.spec.ts b/test/browsercontext-cookies.spec.ts index ef46b36235..50057dfdb2 100644 --- a/test/browsercontext-cookies.spec.ts +++ b/test/browsercontext-cookies.spec.ts @@ -106,10 +106,9 @@ it('should get multiple cookies', async ({context, page, server}) => { document.cookie = 'password=1234'; return document.cookie.split('; ').sort().join('; '); }); - const cookies = await context.cookies(); - cookies.sort((a, b) => a.name.localeCompare(b.name)); + const cookies = new Set(await context.cookies()); expect(documentCookie).toBe('password=1234; username=John Doe'); - expect(cookies).toEqual([ + expect(cookies).toEqual(new Set([ { name: 'password', value: '1234', @@ -130,7 +129,7 @@ it('should get multiple cookies', async ({context, page, server}) => { secure: false, sameSite: 'None', }, - ]); + ])); }); it('should get cookies from multiple urls', async ({context}) => { @@ -147,9 +146,8 @@ it('should get cookies from multiple urls', async ({context}) => { name: 'birdo', value: 'tweets', }]); - const cookies = await context.cookies(['https://foo.com', 'https://baz.com']); - cookies.sort((a, b) => a.name.localeCompare(b.name)); - expect(cookies).toEqual([{ + const cookies = new Set(await context.cookies(['https://foo.com', 'https://baz.com'])); + expect(cookies).toEqual(new Set([{ name: 'birdo', value: 'tweets', domain: 'baz.com', @@ -167,7 +165,7 @@ it('should get cookies from multiple urls', async ({context}) => { httpOnly: false, secure: true, sameSite: 'None', - }]); + }])); }); it('should work with subdomain cookie', async ({context, page, server}) => { @@ -210,3 +208,46 @@ it('should not return cookies with empty value', async ({context, page, server}) expect(cookies.length).toBe(0); }); +it('should return secure cookies based on HTTP(S) protocol', async ({context}) => { + await context.addCookies([{ + url: 'https://foo.com', + name: 'doggo', + value: 'woofs', + secure: true + }, { + url: 'http://foo.com', + name: 'catto', + value: 'purrs', + secure: false + }]); + const cookies = new Set(await context.cookies('https://foo.com')); + expect(cookies).toEqual(new Set([{ + name: 'catto', + value: 'purrs', + domain: 'foo.com', + path: '/', + expires: -1, + httpOnly: false, + secure: false, + sameSite: 'None', + }, { + name: 'doggo', + value: 'woofs', + domain: 'foo.com', + path: '/', + expires: -1, + httpOnly: false, + secure: true, + sameSite: 'None', + }])); + expect(await context.cookies('http://foo.com/')).toEqual([{ + name: 'catto', + value: 'purrs', + domain: 'foo.com', + path: '/', + expires: -1, + httpOnly: false, + secure: false, + sameSite: 'None', + }]); +});