Skip to content

Commit

Permalink
chore: [#1693] Adds CookieSameSiteEnum and IVirtualServer as exports …
Browse files Browse the repository at this point in the history
…to the index file
  • Loading branch information
capricorn86 committed Jan 20, 2025
1 parent 4c0d4fc commit 7f1e378
Show file tree
Hide file tree
Showing 6 changed files with 118 additions and 65 deletions.
25 changes: 15 additions & 10 deletions packages/happy-dom/src/cookie/CookieContainer.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
import URL from '../url/URL.js';
import DefaultCookie from './DefaultCookie.js';
import ICookie from './ICookie.js';
import ICookieContainer from './ICookieContainer.js';
import CookieExpireUtility from './urilities/CookieExpireUtility.js';
Expand Down Expand Up @@ -29,18 +30,22 @@ export default class CookieContainer implements ICookieContainer {
}

for (const cookie of cookies) {
if (cookie?.key) {
// Remove existing cookie with same name, domain and path.
const index = indexMap[getKey(cookie)];
if (!cookie || !cookie.key || !cookie.originURL) {
throw new Error(
"Failed to execute 'addCookies' on 'CookieContainer': The properties 'key' and 'originURL' are required."
);
}

// Remove existing cookie with same name, domain and path.
const index = indexMap[getKey(cookie)];

if (index !== undefined) {
this.#cookies.splice(index, 1);
}
if (index !== undefined) {
this.#cookies.splice(index, 1);
}

if (!CookieExpireUtility.hasExpired(cookie)) {
indexMap[getKey(cookie)] = this.#cookies.length;
this.#cookies.push(cookie);
}
if (!CookieExpireUtility.hasExpired(cookie)) {
indexMap[getKey(cookie)] = this.#cookies.length;
this.#cookies.push(Object.assign(Object.assign({}, DefaultCookie, cookie)));
}
}
}
Expand Down
17 changes: 17 additions & 0 deletions packages/happy-dom/src/cookie/DefaultCookie.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
import CookieSameSiteEnum from './enums/CookieSameSiteEnum.js';
import ICookie from './ICookie.js';

export default <ICookie>{
// Required
key: null,
originURL: null,

// Optional
value: null,
domain: '',
path: '',
expires: null,
httpOnly: false,
secure: false,
sameSite: CookieSameSiteEnum.lax
};
6 changes: 3 additions & 3 deletions packages/happy-dom/src/cookie/ICookie.ts
Original file line number Diff line number Diff line change
Expand Up @@ -3,12 +3,12 @@ import CookieSameSiteEnum from './enums/CookieSameSiteEnum.js';
export default interface ICookie {
// Required
key: string;
value: string | null;
originURL: URL;

// Optional
domain?: string;
path?: string;
value?: string | null;
domain?: string | null;
path?: string | null;
expires?: Date | null;
httpOnly?: boolean;
secure?: boolean;
Expand Down
2 changes: 1 addition & 1 deletion packages/happy-dom/src/cookie/ICookieContainer.ts
Original file line number Diff line number Diff line change
Expand Up @@ -22,5 +22,5 @@ export default interface ICookieContainer {
* @param [httpOnly] "true" if only http cookies should be returned.
* @returns Cookies.
*/
getCookies(url: URL | null, httpOnly: boolean): ICookie[];
getCookies(url: URL | null, httpOnly?: boolean): ICookie[];
}
15 changes: 4 additions & 11 deletions packages/happy-dom/src/cookie/urilities/CookieStringUtility.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
import CookieSameSiteEnum from '../enums/CookieSameSiteEnum.js';
import URL from '../../url/URL.js';
import ICookie from '../ICookie.js';
import DefaultCookie from '../DefaultCookie.js';

/**
* Cookie string.
Expand All @@ -20,20 +21,12 @@ export default class CookieStringUtility {
const key = index !== -1 ? part.slice(0, index).trim() : part.trim();
const value = index !== -1 ? part.slice(index + 1).trim() : null;

const cookie: ICookie = {
const cookie: ICookie = Object.assign({}, DefaultCookie, {
// Required
key,
value,
originURL,

// Optional
domain: '',
path: '',
expires: null,
httpOnly: false,
secure: false,
sameSite: CookieSameSiteEnum.lax
};
originURL
});

// Invalid if key is empty.
if (!cookie.key) {
Expand Down
118 changes: 78 additions & 40 deletions packages/happy-dom/test/cookie/CookieContainer.test.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
import CookieContainer from '../../src/cookie/CookieContainer.js';
import CookieSameSiteEnum from '../../src/cookie/enums/CookieSameSiteEnum.js';
import ICookie from '../../src/cookie/ICookie.js';
import ICookieContainer from '../../src/cookie/ICookieContainer.js';
import CookieStringUtility from '../../src/cookie/urilities/CookieStringUtility.js';
Expand Down Expand Up @@ -151,13 +152,7 @@ describe('CookieContainer', () => {
const originURL = new URL('https://example.com/path/to/page/');
const targetURL = new URL('https://example.com/path/to/page/');

cookieContainer.addCookies([
<ICookie>CookieStringUtility.stringToCookie(originURL, `__secure-key=value`)
]);

expect(
CookieStringUtility.cookiesToString(cookieContainer.getCookies(targetURL, false))
).toBe('');
expect(CookieStringUtility.stringToCookie(originURL, `__secure-key=value`)).toBe(null);

cookieContainer.addCookies([
<ICookie>CookieStringUtility.stringToCookie(originURL, `__secure-key=value; Secure;`)
Expand All @@ -172,55 +167,98 @@ describe('CookieContainer', () => {
const originURL = new URL('https://example.com/path/to/page/');
const targetURL = new URL('https://example.com/path/to/page/');

cookieContainer.addCookies([
<ICookie>CookieStringUtility.stringToCookie(originURL, `__host-key=value`)
]);

expect(
CookieStringUtility.cookiesToString(cookieContainer.getCookies(targetURL, false))
).toBe('');
expect(CookieStringUtility.stringToCookie(originURL, `__host-key=value`)).toBe(null);

cookieContainer.addCookies([
<ICookie>CookieStringUtility.stringToCookie(originURL, `__host-key=value; Secure;`)
]);
expect(CookieStringUtility.stringToCookie(originURL, `__host-key=value; Secure;`)).toBe(null);

expect(
CookieStringUtility.cookiesToString(cookieContainer.getCookies(targetURL, false))
).toBe('');

cookieContainer.addCookies([
<ICookie>(
CookieStringUtility.stringToCookie(
originURL,
`__host-key=value; Secure; Path=/path/to/page/;`
)
CookieStringUtility.stringToCookie(
originURL,
`__host-key=value; Secure; Path=/path/to/page/;`
)
]);
).toBe(null);

expect(
CookieStringUtility.cookiesToString(cookieContainer.getCookies(targetURL, false))
).toBe('');
CookieStringUtility.stringToCookie(
originURL,
`__host-key=value; Secure; Domain=example.com; Path=/;`
)
).toBe(null);

cookieContainer.addCookies([
<ICookie>(
CookieStringUtility.stringToCookie(
originURL,
`__host-key=value; Secure; Domain=example.com; Path=/;`
)
)
<ICookie>CookieStringUtility.stringToCookie(originURL, `__host-key=value; Secure; Path=/;`)
]);

expect(
CookieStringUtility.cookiesToString(cookieContainer.getCookies(targetURL, false))
).toBe('');
).toBe('__host-key=value');
});

it('Throws an error if the cookie "key" is missing.', () => {
const originURL = new URL('https://example.com/path/to/page/');
expect(() => {
cookieContainer.addCookies([<ICookie>{ originURL }]);
}).toThrowError(
"Failed to execute 'addCookies' on 'CookieContainer': The properties 'key' and 'originURL' are required."
);
});

it('Throws an error if the cookie "originURL" is missing.', () => {
expect(() => {
cookieContainer.addCookies([<ICookie>{ key: 'key' }]);
}).toThrowError(
"Failed to execute 'addCookies' on 'CookieContainer': The properties 'key' and 'originURL' are required."
);
});
});

describe('getCookies()', () => {
it('Returns cookies.', () => {
const originURL = new URL('https://example.com/path/to/page/');
const expires = new Date(60 * 1000 + Date.now());

cookieContainer.addCookies([
<ICookie>CookieStringUtility.stringToCookie(originURL, `__host-key=value; Secure; Path=/;`)
{
key: 'key1',
originURL
},
{
key: 'key2',
originURL,
value: 'value2',
domain: 'example.com',
path: '/path/to/page/',
expires,
httpOnly: true,
secure: true,
sameSite: CookieSameSiteEnum.strict
}
]);

expect(
CookieStringUtility.cookiesToString(cookieContainer.getCookies(targetURL, false))
).toBe('__host-key=value');
expect(cookieContainer.getCookies(originURL)).toEqual([
{
key: 'key1',
originURL,
value: null,
domain: '',
path: '',
expires: null,
httpOnly: false,
secure: false,
sameSite: CookieSameSiteEnum.lax
},
{
key: 'key2',
originURL,
value: 'value2',
domain: 'example.com',
path: '/path/to/page/',
expires,
httpOnly: true,
secure: true,
sameSite: CookieSameSiteEnum.strict
}
]);
});
});
});

0 comments on commit 7f1e378

Please sign in to comment.