Skip to content

Commit 967a2c1

Browse files
committed
test(wtr): mock LWC to validate sanitizeAttribute
We can't mock individual methods of ESM modules in the browser, so we use WTR's import map plugin to redirect all "lwc" imports to a mock file. The mock file is mostly a re-export.
1 parent 50dffb0 commit 967a2c1

File tree

6 files changed

+33
-19
lines changed

6 files changed

+33
-19
lines changed

packages/@lwc/integration-karma/test/api/sanitizeAttribute/index.spec.js

Lines changed: 5 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -36,11 +36,10 @@ const scenarios = [
3636

3737
scenarios.forEach(({ type, attrName, tagName, Ctor }) => {
3838
describe(`${type} ${attrName}`, () => {
39-
const originalSanitizeAttribute = LWC.sanitizeAttribute;
40-
39+
// Spy is created in a mock file and injected with the import map plugin
40+
const sanitizeAttributeSpy = LWC.sanitizeAttribute;
4141
afterEach(() => {
42-
// Reset original sanitizer after each test.
43-
LWC.sanitizeAttribute = originalSanitizeAttribute;
42+
sanitizeAttributeSpy.mockReset();
4443
});
4544

4645
it('uses the original passthrough sanitizer when not overridden', () => {
@@ -52,8 +51,6 @@ scenarios.forEach(({ type, attrName, tagName, Ctor }) => {
5251
});
5352

5453
it('receives the right parameters', () => {
55-
spyOn(LWC, 'sanitizeAttribute');
56-
5754
const elm = createElement(tagName, { is: Ctor });
5855
document.body.appendChild(elm);
5956

@@ -66,7 +63,7 @@ scenarios.forEach(({ type, attrName, tagName, Ctor }) => {
6663
});
6764

6865
it('replace the original attribute value with a string', () => {
69-
spyOn(LWC, 'sanitizeAttribute').and.returnValue('/bar');
66+
sanitizeAttributeSpy.mockReturnValue('/bar');
7067

7168
const elm = createElement(tagName, { is: Ctor });
7269
document.body.appendChild(elm);
@@ -76,7 +73,7 @@ scenarios.forEach(({ type, attrName, tagName, Ctor }) => {
7673
});
7774

7875
it('replace the original attribute value with undefined', () => {
79-
spyOn(LWC, 'sanitizeAttribute').and.returnValue(undefined);
76+
sanitizeAttributeSpy.mockReturnValue(undefined);
8077

8178
const elm = createElement(tagName, { is: Ctor });
8279
document.body.appendChild(elm);
@@ -105,8 +102,6 @@ booleanTrueScenarios.forEach(({ attrName, tagName, Ctor }) => {
105102
describe(attrName, () => {
106103
// For boolean literals (e.g. `<use xlink:href>`), there is no reason to sanitize since it's empty
107104
it('does not sanitize when used as a boolean-true attribute', () => {
108-
spyOn(LWC, 'sanitizeAttribute');
109-
110105
const elm = createElement(tagName, { is: Ctor });
111106
document.body.appendChild(elm);
112107

packages/@lwc/integration-not-karma/configs/base.mjs

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
11
import { join } from 'node:path';
22
import { LWC_VERSION } from '@lwc/shared';
3+
import { importMapsPlugin } from '@web/dev-server-import-maps';
34
import * as options from '../helpers/options.mjs';
45

56
const pluck = (obj, keys) => Object.fromEntries(keys.map((k) => [k, obj[k]]));
@@ -31,6 +32,7 @@ export default {
3132
nodeResolve: true,
3233
rootDir: join(import.meta.dirname, '..'),
3334
plugins: [
35+
importMapsPlugin({ inject: { importMap: { imports: { lwc: './mocks/lwc.mjs' } } } }),
3436
{
3537
resolveImport({ source }) {
3638
if (source === 'test-utils') {

packages/@lwc/integration-not-karma/configs/integration.mjs

Lines changed: 0 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -8,21 +8,12 @@ export default {
88
// FIXME: These tests are just symlinks to integration-karma for now so the git diff smaller
99
'test/**/*.spec.js',
1010

11-
// Cannot reassign properties of module
12-
'!test/api/sanitizeAttribute/index.spec.js',
13-
1411
// Hacky nonsense highly tailored to Karma
1512
'!test/custom-elements-registry/index.spec.js',
1613

1714
// Logging mismatches
1815
'!test/component/LightningElement.addEventListener/index.spec.js',
1916

20-
// Needs clean <head>
21-
'!test/light-dom/multiple-templates/index.spec.js',
22-
'!test/light-dom/style-global/index.spec.js',
23-
'!test/misc/clean-dom/index.spec.js',
24-
'!test/swapping/styles/index.spec.js',
25-
2617
// Implement objectContaining / arrayWithExactContents
2718
'!test/profiler/mutation-logging/index.spec.js',
2819
],
Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,6 @@
1+
// IMPORTANT: we must use @lwc/engine-dom instead of lwc in order to avoid circular imports
2+
import { sanitizeAttribute as _sanitizeAttribute } from '@lwc/engine-dom';
3+
import { fn } from '@vitest/spy';
4+
5+
export * from '@lwc/engine-dom';
6+
export const sanitizeAttribute = fn(_sanitizeAttribute);

packages/@lwc/integration-not-karma/package.json

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,7 @@
1515
"@lwc/synthetic-shadow": "8.21.1",
1616
"@types/chai": "^5.2.2",
1717
"@types/jasmine": "^5.1.8",
18+
"@web/dev-server-import-maps": "^0.2.1",
1819
"@web/dev-server-rollup": "^0.6.4",
1920
"@web/test-runner": "^0.20.2",
2021
"chai": "^5.2.1"

yarn.lock

Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1879,6 +1879,11 @@
18791879
resolved "https://registry.yarnpkg.com/@humanwhocodes/retry/-/retry-0.4.2.tgz#1860473de7dfa1546767448f333db80cb0ff2161"
18801880
integrity sha512-xeO57FpIu4p1Ri3Jq/EXq4ClRm86dVF2z/+kvFnyqVYRavTZmaFaUBbWCOuuTh0o/g7DSsk6kc2vrS4Vl5oPOQ==
18811881

1882+
"@import-maps/resolve@^1.0.1":
1883+
version "1.0.1"
1884+
resolved "https://registry.yarnpkg.com/@import-maps/resolve/-/resolve-1.0.1.tgz#1e9fcadcf23aa0822256a329aabca241879d37c9"
1885+
integrity sha512-tWZNBIS1CoekcwlMuyG2mr0a1Wo5lb5lEHwwWvZo+5GLgr3e9LLDTtmgtCWEwBpXMkxn9D+2W9j2FY6eZQq0tA==
1886+
18821887
"@inquirer/checkbox@^4.1.9":
18831888
version "4.1.9"
18841889
resolved "https://registry.yarnpkg.com/@inquirer/checkbox/-/checkbox-4.1.9.tgz#431c65a3a1fd289be8102034ece15c91dda1ceec"
@@ -2177,9 +2182,11 @@
21772182

21782183
"@lwc/eslint-plugin-lwc-internal@link:./scripts/eslint-plugin":
21792184
version "0.0.0"
2185+
uid ""
21802186

21812187
"@lwc/test-utils-lwc-internals@link:./scripts/test-utils":
21822188
version "0.0.0"
2189+
uid ""
21832190

21842191
"@napi-rs/wasm-runtime@0.2.4":
21852192
version "0.2.4"
@@ -4260,6 +4267,18 @@
42604267
picomatch "^2.2.2"
42614268
ws "^7.5.10"
42624269

4270+
"@web/dev-server-import-maps@^0.2.1":
4271+
version "0.2.1"
4272+
resolved "https://registry.yarnpkg.com/@web/dev-server-import-maps/-/dev-server-import-maps-0.2.1.tgz#4b3ab65bb256b7852a1abfe9cdf1b7b129d3d0fa"
4273+
integrity sha512-iGM7s4qenmTDUWC2iV0HoQ1NR5lAyRxVHOpWzTsFH/TnUZzP+YuL6QIFtB2v2v7URfhGL2l2WPIibmliToITcg==
4274+
dependencies:
4275+
"@import-maps/resolve" "^1.0.1"
4276+
"@types/parse5" "^6.0.1"
4277+
"@web/dev-server-core" "^0.7.2"
4278+
"@web/parse5-utils" "^2.1.0"
4279+
parse5 "^6.0.1"
4280+
picomatch "^2.2.2"
4281+
42634282
"@web/dev-server-rollup@^0.6.1", "@web/dev-server-rollup@^0.6.4":
42644283
version "0.6.4"
42654284
resolved "https://registry.yarnpkg.com/@web/dev-server-rollup/-/dev-server-rollup-0.6.4.tgz#d0a4f69e4a659d2b79f172e86236cea6c872e81c"

0 commit comments

Comments
 (0)