@stencil/core 4.43.5 → 5.0.0-alpha.10
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/bin/stencil.mjs +2 -0
- package/dist/app-data/index.d.ts +2 -0
- package/dist/app-data/index.js +104 -0
- package/dist/app-globals/index.d.ts +5 -0
- package/dist/app-globals/index.js +5 -0
- package/dist/chunk-z9aeyW2b.mjs +15 -0
- package/dist/client-aTQ7xHxx.mjs +4678 -0
- package/dist/compiler/index.d.mts +192 -0
- package/dist/compiler/index.mjs +3 -0
- package/dist/compiler/utils/index.d.mts +2 -0
- package/dist/compiler/utils/index.mjs +3 -0
- package/dist/compiler-lTINDSgw.mjs +23136 -0
- package/{internal → dist/declarations}/stencil-ext-modules.d.ts +8 -8
- package/dist/declarations/stencil-public-compiler.d.ts +4374 -0
- package/dist/declarations/stencil-public-compiler.js +51 -0
- package/dist/declarations/stencil-public-docs.d.ts +505 -0
- package/dist/declarations/stencil-public-runtime.d.ts +1982 -0
- package/dist/declarations/stencil-public-runtime.js +0 -0
- package/dist/index-BvkyxSY6.d.mts +205 -0
- package/dist/index-vY35H18z.d.mts +6525 -0
- package/dist/index-xAkMgLX_.d.ts +1942 -0
- package/{internal/stencil-core/index.d.ts → dist/index.d.mts} +11 -4
- package/dist/index.mjs +2 -0
- package/dist/jsx-runtime.d.mts +18 -0
- package/dist/jsx-runtime.mjs +2 -0
- package/dist/mock-doc.d.mts +1 -0
- package/dist/mock-doc.mjs +2 -0
- package/dist/node--akYC-sG.mjs +1937 -0
- package/dist/regular-expression-CFVJOTUh.mjs +508 -0
- package/dist/runtime/client/lazy.js +4930 -0
- package/dist/runtime/client/runtime.d.ts +2386 -0
- package/dist/runtime/client/runtime.js +4924 -0
- package/dist/runtime/index.d.ts +211 -0
- package/dist/runtime/index.js +4795 -0
- package/dist/runtime/server/index.d.mts +1179 -0
- package/dist/runtime/server/index.mjs +5140 -0
- package/dist/runtime/server/runner.d.mts +319 -0
- package/dist/runtime/server/runner.mjs +13642 -0
- package/dist/signals/index.d.ts +47 -0
- package/dist/signals/index.js +199 -0
- package/dist/sys/node/index.d.mts +32 -0
- package/dist/sys/node/index.mjs +2 -0
- package/dist/sys/node/worker.d.mts +1 -0
- package/dist/sys/node/worker.mjs +48 -0
- package/dist/testing/index.d.mts +303 -0
- package/dist/testing/index.mjs +1477 -0
- package/dist/validation-ByxKj8bC.mjs +1458 -0
- package/package.json +108 -228
- package/bin/stencil +0 -57
- package/cli/config-flags.d.ts +0 -132
- package/cli/index.cjs +0 -6041
- package/cli/index.d.ts +0 -19
- package/cli/index.js +0 -6034
- package/cli/package.json +0 -14
- package/compiler/lib.d.ts +0 -22
- package/compiler/lib.decorators.d.ts +0 -384
- package/compiler/lib.decorators.legacy.d.ts +0 -22
- package/compiler/lib.dom.asynciterable.d.ts +0 -41
- package/compiler/lib.dom.d.ts +0 -29610
- package/compiler/lib.dom.iterable.d.ts +0 -493
- package/compiler/lib.es2015.collection.d.ts +0 -147
- package/compiler/lib.es2015.core.d.ts +0 -597
- package/compiler/lib.es2015.d.ts +0 -28
- package/compiler/lib.es2015.generator.d.ts +0 -77
- package/compiler/lib.es2015.iterable.d.ts +0 -605
- package/compiler/lib.es2015.promise.d.ts +0 -81
- package/compiler/lib.es2015.proxy.d.ts +0 -128
- package/compiler/lib.es2015.reflect.d.ts +0 -144
- package/compiler/lib.es2015.symbol.d.ts +0 -46
- package/compiler/lib.es2015.symbol.wellknown.d.ts +0 -326
- package/compiler/lib.es2016.array.include.d.ts +0 -116
- package/compiler/lib.es2016.d.ts +0 -21
- package/compiler/lib.es2016.full.d.ts +0 -23
- package/compiler/lib.es2016.intl.d.ts +0 -31
- package/compiler/lib.es2017.arraybuffer.d.ts +0 -21
- package/compiler/lib.es2017.d.ts +0 -26
- package/compiler/lib.es2017.date.d.ts +0 -31
- package/compiler/lib.es2017.full.d.ts +0 -23
- package/compiler/lib.es2017.intl.d.ts +0 -44
- package/compiler/lib.es2017.object.d.ts +0 -49
- package/compiler/lib.es2017.sharedmemory.d.ts +0 -135
- package/compiler/lib.es2017.string.d.ts +0 -45
- package/compiler/lib.es2017.typedarrays.d.ts +0 -53
- package/compiler/lib.es2018.asyncgenerator.d.ts +0 -77
- package/compiler/lib.es2018.asynciterable.d.ts +0 -53
- package/compiler/lib.es2018.d.ts +0 -24
- package/compiler/lib.es2018.full.d.ts +0 -24
- package/compiler/lib.es2018.intl.d.ts +0 -83
- package/compiler/lib.es2018.promise.d.ts +0 -30
- package/compiler/lib.es2018.regexp.d.ts +0 -37
- package/compiler/lib.es2019.array.d.ts +0 -79
- package/compiler/lib.es2019.d.ts +0 -24
- package/compiler/lib.es2019.full.d.ts +0 -24
- package/compiler/lib.es2019.intl.d.ts +0 -23
- package/compiler/lib.es2019.object.d.ts +0 -33
- package/compiler/lib.es2019.string.d.ts +0 -37
- package/compiler/lib.es2019.symbol.d.ts +0 -24
- package/compiler/lib.es2020.bigint.d.ts +0 -765
- package/compiler/lib.es2020.d.ts +0 -27
- package/compiler/lib.es2020.date.d.ts +0 -42
- package/compiler/lib.es2020.full.d.ts +0 -24
- package/compiler/lib.es2020.intl.d.ts +0 -474
- package/compiler/lib.es2020.number.d.ts +0 -28
- package/compiler/lib.es2020.promise.d.ts +0 -47
- package/compiler/lib.es2020.sharedmemory.d.ts +0 -99
- package/compiler/lib.es2020.string.d.ts +0 -44
- package/compiler/lib.es2020.symbol.wellknown.d.ts +0 -41
- package/compiler/lib.es2021.d.ts +0 -23
- package/compiler/lib.es2021.full.d.ts +0 -24
- package/compiler/lib.es2021.intl.d.ts +0 -166
- package/compiler/lib.es2021.promise.d.ts +0 -48
- package/compiler/lib.es2021.string.d.ts +0 -33
- package/compiler/lib.es2021.weakref.d.ts +0 -78
- package/compiler/lib.es2022.array.d.ts +0 -121
- package/compiler/lib.es2022.d.ts +0 -25
- package/compiler/lib.es2022.error.d.ts +0 -75
- package/compiler/lib.es2022.full.d.ts +0 -24
- package/compiler/lib.es2022.intl.d.ts +0 -121
- package/compiler/lib.es2022.object.d.ts +0 -26
- package/compiler/lib.es2022.regexp.d.ts +0 -39
- package/compiler/lib.es2022.string.d.ts +0 -25
- package/compiler/lib.es2023.array.d.ts +0 -924
- package/compiler/lib.es2023.collection.d.ts +0 -21
- package/compiler/lib.es2023.d.ts +0 -22
- package/compiler/lib.es2023.full.d.ts +0 -24
- package/compiler/lib.es2023.intl.d.ts +0 -56
- package/compiler/lib.es2024.arraybuffer.d.ts +0 -65
- package/compiler/lib.es2024.collection.d.ts +0 -29
- package/compiler/lib.es2024.d.ts +0 -26
- package/compiler/lib.es2024.full.d.ts +0 -24
- package/compiler/lib.es2024.object.d.ts +0 -29
- package/compiler/lib.es2024.promise.d.ts +0 -35
- package/compiler/lib.es2024.regexp.d.ts +0 -25
- package/compiler/lib.es2024.sharedmemory.d.ts +0 -68
- package/compiler/lib.es2024.string.d.ts +0 -29
- package/compiler/lib.es5.d.ts +0 -4594
- package/compiler/lib.es6.d.ts +0 -23
- package/compiler/lib.esnext.array.d.ts +0 -35
- package/compiler/lib.esnext.collection.d.ts +0 -96
- package/compiler/lib.esnext.d.ts +0 -27
- package/compiler/lib.esnext.decorators.d.ts +0 -28
- package/compiler/lib.esnext.disposable.d.ts +0 -193
- package/compiler/lib.esnext.float16.d.ts +0 -443
- package/compiler/lib.esnext.full.d.ts +0 -24
- package/compiler/lib.esnext.intl.d.ts +0 -21
- package/compiler/lib.esnext.iterator.d.ts +0 -148
- package/compiler/lib.esnext.promise.d.ts +0 -34
- package/compiler/lib.scripthost.d.ts +0 -322
- package/compiler/lib.webworker.asynciterable.d.ts +0 -41
- package/compiler/lib.webworker.d.ts +0 -9894
- package/compiler/lib.webworker.importscripts.d.ts +0 -23
- package/compiler/lib.webworker.iterable.d.ts +0 -287
- package/compiler/package.json +0 -8
- package/compiler/stencil.d.ts +0 -73
- package/compiler/stencil.js +0 -288221
- package/compiler/sys/in-memory-fs.d.ts +0 -227
- package/compiler/transpile.d.ts +0 -32
- package/dev-server/client/app-error.d.ts +0 -20
- package/dev-server/client/events.d.ts +0 -6
- package/dev-server/client/hmr-components.d.ts +0 -12
- package/dev-server/client/hmr-external-styles.d.ts +0 -1
- package/dev-server/client/hmr-images.d.ts +0 -1
- package/dev-server/client/hmr-inline-styles.d.ts +0 -1
- package/dev-server/client/hmr-util.d.ts +0 -39
- package/dev-server/client/hmr-window.d.ts +0 -10
- package/dev-server/client/index.d.ts +0 -6
- package/dev-server/client/index.js +0 -793
- package/dev-server/client/logger.d.ts +0 -6
- package/dev-server/client/package.json +0 -8
- package/dev-server/client/progress.d.ts +0 -3
- package/dev-server/client/status.d.ts +0 -4
- package/dev-server/client/test/hmr-util.spec.d.ts +0 -1
- package/dev-server/client/test/status.spec.d.ts +0 -1
- package/dev-server/connector.html +0 -6
- package/dev-server/index.d.ts +0 -3
- package/dev-server/index.js +0 -247
- package/dev-server/package.json +0 -8
- package/dev-server/server-process.js +0 -12304
- package/dev-server/server-worker-thread.js +0 -39
- package/dev-server/static/favicon.ico +0 -0
- package/dev-server/templates/directory-index.html +0 -176
- package/dev-server/templates/initial-load.html +0 -168
- package/dev-server/visualstudio.vbs +0 -82
- package/dev-server/xdg-open +0 -1066
- package/internal/app-data/index.cjs +0 -119
- package/internal/app-data/index.d.ts +0 -26
- package/internal/app-data/index.js +0 -92
- package/internal/app-data/package.json +0 -15
- package/internal/app-globals/index.d.ts +0 -2
- package/internal/app-globals/index.js +0 -14
- package/internal/app-globals/package.json +0 -14
- package/internal/child_process.d.ts +0 -7
- package/internal/client/index.js +0 -4777
- package/internal/client/package.json +0 -10
- package/internal/client/patch-browser.js +0 -45
- package/internal/client/polyfills/core-js.js +0 -11
- package/internal/client/polyfills/dom.js +0 -79
- package/internal/client/polyfills/es5-html-element.js +0 -1
- package/internal/client/polyfills/index.js +0 -34
- package/internal/client/polyfills/system.js +0 -6
- package/internal/client/shadow-css.js +0 -414
- package/internal/hydrate/index.js +0 -6915
- package/internal/hydrate/package.json +0 -7
- package/internal/hydrate/runner.d.ts +0 -287
- package/internal/hydrate/runner.js +0 -18173
- package/internal/index.d.ts +0 -4
- package/internal/index.js +0 -2
- package/internal/package.json +0 -9
- package/internal/stencil-core/index.cjs +0 -1
- package/internal/stencil-core/index.js +0 -18
- package/internal/stencil-core/jsx-dev-runtime.cjs +0 -7
- package/internal/stencil-core/jsx-dev-runtime.d.ts +0 -41
- package/internal/stencil-core/jsx-dev-runtime.js +0 -2
- package/internal/stencil-core/jsx-runtime.cjs +0 -8
- package/internal/stencil-core/jsx-runtime.d.ts +0 -40
- package/internal/stencil-core/jsx-runtime.js +0 -2
- package/internal/stencil-private.d.ts +0 -2549
- package/internal/stencil-public-compiler.d.ts +0 -2922
- package/internal/stencil-public-docs.d.ts +0 -472
- package/internal/stencil-public-runtime.d.ts +0 -1861
- package/internal/testing/index.js +0 -6779
- package/internal/testing/jsx-dev-runtime.d.ts +0 -2
- package/internal/testing/jsx-dev-runtime.js +0 -8
- package/internal/testing/jsx-runtime.d.ts +0 -2
- package/internal/testing/jsx-runtime.js +0 -9
- package/internal/testing/package.json +0 -7
- package/internal/utils/index.d.ts +0 -1
- package/internal/utils/result.d.ts +0 -112
- package/mock-doc/index.cjs +0 -10163
- package/mock-doc/index.d.ts +0 -1172
- package/mock-doc/index.js +0 -10142
- package/mock-doc/package.json +0 -15
- package/readme.md +0 -94
- package/screenshot/compare/assets/favicon.ico +0 -0
- package/screenshot/compare/assets/logo.png +0 -0
- package/screenshot/compare/build/app.css +0 -1
- package/screenshot/compare/build/app.esm.js +0 -1
- package/screenshot/compare/build/app.js +0 -33
- package/screenshot/compare/build/p-081b0641.js +0 -1
- package/screenshot/compare/build/p-227a1e18.entry.js +0 -1
- package/screenshot/compare/build/p-2c298727.entry.js +0 -1
- package/screenshot/compare/build/p-5479268c.entry.js +0 -1
- package/screenshot/compare/build/p-573ec8a4.entry.js +0 -1
- package/screenshot/compare/build/p-6ba08604.entry.js +0 -1
- package/screenshot/compare/build/p-6bc63295.entry.js +0 -1
- package/screenshot/compare/build/p-7a3759fd.entry.js +0 -1
- package/screenshot/compare/build/p-7b4e3ba7.js +0 -1
- package/screenshot/compare/build/p-988eb362.css +0 -1
- package/screenshot/compare/build/p-9b6a9315.js +0 -1
- package/screenshot/compare/build/p-b4cc611c.entry.js +0 -1
- package/screenshot/compare/build/p-d1bf53f5.entry.js +0 -1
- package/screenshot/compare/build/p-e2efe0df.js +0 -1
- package/screenshot/compare/build/p-e8ca6d97.entry.js +0 -1
- package/screenshot/compare/build/p-ec2f13e0.entry.js +0 -1
- package/screenshot/compare/build/p-f0b99977.entry.js +0 -1
- package/screenshot/compare/build/p-f4745c2f.entry.js +0 -1
- package/screenshot/compare/build/p-fbbae598.js +0 -1
- package/screenshot/compare/host.config.json +0 -15
- package/screenshot/compare/index.html +0 -1
- package/screenshot/compare/manifest.json +0 -13
- package/screenshot/connector-base.d.ts +0 -42
- package/screenshot/connector-local.d.ts +0 -7
- package/screenshot/connector.js +0 -2
- package/screenshot/index.d.ts +0 -3
- package/screenshot/index.js +0 -2642
- package/screenshot/local-connector.js +0 -2
- package/screenshot/package.json +0 -15
- package/screenshot/pixel-match.d.ts +0 -1
- package/screenshot/pixel-match.js +0 -2315
- package/screenshot/screenshot-compare.d.ts +0 -20
- package/screenshot/screenshot-fs.d.ts +0 -14
- package/sys/node/460.node-fetch.js +0 -451
- package/sys/node/autoprefixer.js +0 -9
- package/sys/node/glob.js +0 -1
- package/sys/node/graceful-fs.js +0 -1
- package/sys/node/index.d.ts +0 -39
- package/sys/node/index.js +0 -62
- package/sys/node/node-fetch.js +0 -12
- package/sys/node/package.json +0 -8
- package/sys/node/prompts.js +0 -1
- package/sys/node/worker.js +0 -4
- package/testing/index.d.ts +0 -9
- package/testing/index.js +0 -13276
- package/testing/jest/jest-27-and-under/jest-config.d.ts +0 -16
- package/testing/jest/jest-27-and-under/jest-environment.d.ts +0 -2
- package/testing/jest/jest-27-and-under/jest-facade.d.ts +0 -155
- package/testing/jest/jest-27-and-under/jest-preprocessor.d.ts +0 -59
- package/testing/jest/jest-27-and-under/jest-preset.d.ts +0 -3
- package/testing/jest/jest-27-and-under/jest-runner.d.ts +0 -11
- package/testing/jest/jest-27-and-under/jest-screenshot.d.ts +0 -2
- package/testing/jest/jest-27-and-under/jest-serializer.d.ts +0 -4
- package/testing/jest/jest-27-and-under/jest-setup-test-framework.d.ts +0 -9
- package/testing/jest/jest-27-and-under/matchers/attributes.d.ts +0 -14
- package/testing/jest/jest-27-and-under/matchers/class-list.d.ts +0 -12
- package/testing/jest/jest-27-and-under/matchers/events.d.ts +0 -25
- package/testing/jest/jest-27-and-under/matchers/html.d.ts +0 -13
- package/testing/jest/jest-27-and-under/matchers/index.d.ts +0 -24
- package/testing/jest/jest-27-and-under/matchers/screenshot.d.ts +0 -5
- package/testing/jest/jest-27-and-under/matchers/text.d.ts +0 -4
- package/testing/jest/jest-27-and-under/test/jest-config.spec.d.ts +0 -1
- package/testing/jest/jest-27-and-under/test/jest-preprocessor.spec.d.ts +0 -1
- package/testing/jest/jest-27-and-under/test/jest-runner.spec.d.ts +0 -1
- package/testing/jest/jest-27-and-under/test/jest-serializer.spec.d.ts +0 -1
- package/testing/jest/jest-27-and-under/test/jest-setup-test-framework.spec.d.ts +0 -1
- package/testing/jest/jest-28/jest-config.d.ts +0 -16
- package/testing/jest/jest-28/jest-environment.d.ts +0 -2
- package/testing/jest/jest-28/jest-facade.d.ts +0 -134
- package/testing/jest/jest-28/jest-preprocessor.d.ts +0 -35
- package/testing/jest/jest-28/jest-preset.d.ts +0 -3
- package/testing/jest/jest-28/jest-runner.d.ts +0 -11
- package/testing/jest/jest-28/jest-screenshot.d.ts +0 -2
- package/testing/jest/jest-28/jest-serializer.d.ts +0 -4
- package/testing/jest/jest-28/jest-setup-test-framework.d.ts +0 -9
- package/testing/jest/jest-28/matchers/attributes.d.ts +0 -14
- package/testing/jest/jest-28/matchers/class-list.d.ts +0 -12
- package/testing/jest/jest-28/matchers/events.d.ts +0 -25
- package/testing/jest/jest-28/matchers/html.d.ts +0 -13
- package/testing/jest/jest-28/matchers/index.d.ts +0 -24
- package/testing/jest/jest-28/matchers/screenshot.d.ts +0 -5
- package/testing/jest/jest-28/matchers/text.d.ts +0 -4
- package/testing/jest/jest-28/test/jest-config.spec.d.ts +0 -1
- package/testing/jest/jest-28/test/jest-preprocessor.spec.d.ts +0 -1
- package/testing/jest/jest-28/test/jest-runner.spec.d.ts +0 -1
- package/testing/jest/jest-28/test/jest-serializer.spec.d.ts +0 -1
- package/testing/jest/jest-28/test/jest-setup-test-framework.spec.d.ts +0 -1
- package/testing/jest/jest-29/jest-config.d.ts +0 -16
- package/testing/jest/jest-29/jest-environment.d.ts +0 -2
- package/testing/jest/jest-29/jest-facade.d.ts +0 -136
- package/testing/jest/jest-29/jest-preprocessor.d.ts +0 -35
- package/testing/jest/jest-29/jest-preset.d.ts +0 -3
- package/testing/jest/jest-29/jest-runner.d.ts +0 -11
- package/testing/jest/jest-29/jest-screenshot.d.ts +0 -2
- package/testing/jest/jest-29/jest-serializer.d.ts +0 -4
- package/testing/jest/jest-29/jest-setup-test-framework.d.ts +0 -9
- package/testing/jest/jest-29/matchers/attributes.d.ts +0 -14
- package/testing/jest/jest-29/matchers/class-list.d.ts +0 -12
- package/testing/jest/jest-29/matchers/events.d.ts +0 -25
- package/testing/jest/jest-29/matchers/html.d.ts +0 -13
- package/testing/jest/jest-29/matchers/index.d.ts +0 -24
- package/testing/jest/jest-29/matchers/screenshot.d.ts +0 -5
- package/testing/jest/jest-29/matchers/text.d.ts +0 -4
- package/testing/jest/jest-29/test/jest-config.spec.d.ts +0 -1
- package/testing/jest/jest-29/test/jest-preprocessor.spec.d.ts +0 -1
- package/testing/jest/jest-29/test/jest-runner.spec.d.ts +0 -1
- package/testing/jest/jest-29/test/jest-serializer.spec.d.ts +0 -1
- package/testing/jest/jest-29/test/jest-setup-test-framework.spec.d.ts +0 -1
- package/testing/jest/jest-apis.d.ts +0 -86
- package/testing/jest/jest-facade.d.ts +0 -74
- package/testing/jest/jest-stencil-connector.d.ts +0 -65
- package/testing/jest/test/jest-stencil-connector.spec.d.ts +0 -1
- package/testing/jest-environment.js +0 -3
- package/testing/jest-preprocessor.js +0 -3
- package/testing/jest-preset.js +0 -2
- package/testing/jest-runner.js +0 -3
- package/testing/jest-setuptestframework.js +0 -3
- package/testing/mock-fetch.d.ts +0 -11
- package/testing/mocks.d.ts +0 -56
- package/testing/package.json +0 -8
- package/testing/puppeteer/index.d.ts +0 -2
- package/testing/puppeteer/puppeteer-browser.d.ts +0 -6
- package/testing/puppeteer/puppeteer-declarations.d.ts +0 -414
- package/testing/puppeteer/puppeteer-element.d.ts +0 -67
- package/testing/puppeteer/puppeteer-emulate.d.ts +0 -2
- package/testing/puppeteer/puppeteer-events.d.ts +0 -21
- package/testing/puppeteer/puppeteer-page.d.ts +0 -2
- package/testing/puppeteer/puppeteer-screenshot.d.ts +0 -27
- package/testing/puppeteer/test/puppeteer-screenshot.spec.d.ts +0 -1
- package/testing/reset-build-conditionals.d.ts +0 -12
- package/testing/spec-page.d.ts +0 -7
- package/testing/test/testing-utils.spec.d.ts +0 -1
- package/testing/test-transpile.d.ts +0 -2
- package/testing/testing-logger.d.ts +0 -26
- package/testing/testing-sys.d.ts +0 -6
- package/testing/testing-utils.d.ts +0 -80
- package/testing/testing.d.ts +0 -2
- /package/{screenshot/compare/build/index.esm.js → dist/declarations/stencil-public-docs.js} +0 -0
|
@@ -0,0 +1,1477 @@
|
|
|
1
|
+
import { A as HYDRATE_ID, C as setAssetPath, D as DEFAULT_DOC_DATA, F as reWireGetterSetter, M as STENCIL_DOC_DATA, P as getHostRef$1, S as getAssetPath, X as Env, Y as BUILD, _ as insertBefore, b as getElement, c as Fragment, g as getRenderingRef, h as forceUpdate, j as NODE_TYPE, k as HYDRATE_CHILD_ID, l as bootstrapLazy, m as h, p as Host, s as Mixin, u as getMode, v as renderVdom, y as createEvent } from "../client-aTQ7xHxx.mjs";
|
|
2
|
+
import { L as EVENT_FLAGS, h as noop, w as CMP_FLAGS } from "../regular-expression-CFVJOTUh.mjs";
|
|
3
|
+
import { _ as getBuildFeatures, c as createWorkerContext, g as BuildContext, h as Cache, i as createSystem, o as loadConfig, p as createInMemoryFs, s as createCompiler } from "../compiler-lTINDSgw.mjs";
|
|
4
|
+
import { wt as formatLazyBundleRuntimeMeta } from "../validation-ByxKj8bC.mjs";
|
|
5
|
+
import { o as buildEvents } from "../node--akYC-sG.mjs";
|
|
6
|
+
import fs from "node:fs";
|
|
7
|
+
import path from "node:path";
|
|
8
|
+
import { fileURLToPath } from "node:url";
|
|
9
|
+
import path$1 from "path";
|
|
10
|
+
import { MockWindow, setupGlobal } from "@stencil/mock-doc";
|
|
11
|
+
import { createHash } from "crypto";
|
|
12
|
+
import { afterAll, vi } from "vitest";
|
|
13
|
+
//#region src/testing/testing-logger.ts
|
|
14
|
+
var TestingLogger = class {
|
|
15
|
+
isEnabled = false;
|
|
16
|
+
enable() {
|
|
17
|
+
this.isEnabled = true;
|
|
18
|
+
}
|
|
19
|
+
setLevel(_level) {}
|
|
20
|
+
getLevel() {
|
|
21
|
+
return "info";
|
|
22
|
+
}
|
|
23
|
+
enableColors(_useColors) {}
|
|
24
|
+
emoji(_) {
|
|
25
|
+
return "";
|
|
26
|
+
}
|
|
27
|
+
info(...msg) {
|
|
28
|
+
if (this.isEnabled) console.log(...msg);
|
|
29
|
+
}
|
|
30
|
+
warn(...msg) {
|
|
31
|
+
if (this.isEnabled) console.warn(...msg);
|
|
32
|
+
}
|
|
33
|
+
error(...msg) {
|
|
34
|
+
if (this.isEnabled) console.error(...msg);
|
|
35
|
+
}
|
|
36
|
+
debug(...msg) {
|
|
37
|
+
if (this.isEnabled) console.log(...msg);
|
|
38
|
+
}
|
|
39
|
+
color(_msg, _color) {}
|
|
40
|
+
red(msg) {
|
|
41
|
+
return msg;
|
|
42
|
+
}
|
|
43
|
+
green(msg) {
|
|
44
|
+
return msg;
|
|
45
|
+
}
|
|
46
|
+
yellow(msg) {
|
|
47
|
+
return msg;
|
|
48
|
+
}
|
|
49
|
+
blue(msg) {
|
|
50
|
+
return msg;
|
|
51
|
+
}
|
|
52
|
+
magenta(msg) {
|
|
53
|
+
return msg;
|
|
54
|
+
}
|
|
55
|
+
cyan(msg) {
|
|
56
|
+
return msg;
|
|
57
|
+
}
|
|
58
|
+
gray(msg) {
|
|
59
|
+
return msg;
|
|
60
|
+
}
|
|
61
|
+
bold(msg) {
|
|
62
|
+
return msg;
|
|
63
|
+
}
|
|
64
|
+
dim(msg) {
|
|
65
|
+
return msg;
|
|
66
|
+
}
|
|
67
|
+
bgRed(msg) {
|
|
68
|
+
return msg;
|
|
69
|
+
}
|
|
70
|
+
createTimeSpan(_startMsg, _debug = false) {
|
|
71
|
+
return {
|
|
72
|
+
duration() {
|
|
73
|
+
return 0;
|
|
74
|
+
},
|
|
75
|
+
finish() {
|
|
76
|
+
return 0;
|
|
77
|
+
}
|
|
78
|
+
};
|
|
79
|
+
}
|
|
80
|
+
printDiagnostics(_diagnostics) {}
|
|
81
|
+
};
|
|
82
|
+
//#endregion
|
|
83
|
+
//#region src/testing/testing-sys.ts
|
|
84
|
+
function isTestingSystem(sys) {
|
|
85
|
+
return "diskReads" in sys && "diskWrites" in sys;
|
|
86
|
+
}
|
|
87
|
+
const createTestingSystem = () => {
|
|
88
|
+
let diskReads = 0;
|
|
89
|
+
let diskWrites = 0;
|
|
90
|
+
const sys = createSystem();
|
|
91
|
+
sys.platformPath = path$1;
|
|
92
|
+
sys.generateContentHash = (content, length) => {
|
|
93
|
+
let hash = createHash("sha1").update(content).digest("hex").toLowerCase();
|
|
94
|
+
if (typeof length === "number") hash = hash.slice(0, length);
|
|
95
|
+
return Promise.resolve(hash);
|
|
96
|
+
};
|
|
97
|
+
const wrapRead = (fn) => {
|
|
98
|
+
const orgFn = fn;
|
|
99
|
+
return (...args) => {
|
|
100
|
+
diskReads++;
|
|
101
|
+
return orgFn.apply(orgFn, args);
|
|
102
|
+
};
|
|
103
|
+
};
|
|
104
|
+
const wrapWrite = (fn) => {
|
|
105
|
+
const orgFn = fn;
|
|
106
|
+
return (...args) => {
|
|
107
|
+
diskWrites++;
|
|
108
|
+
return orgFn.apply(orgFn, args);
|
|
109
|
+
};
|
|
110
|
+
};
|
|
111
|
+
sys.access = wrapRead(sys.access);
|
|
112
|
+
sys.accessSync = wrapRead(sys.accessSync);
|
|
113
|
+
sys.homeDir = wrapRead(sys.homeDir);
|
|
114
|
+
sys.readFile = wrapRead(sys.readFile);
|
|
115
|
+
sys.readFileSync = wrapRead(sys.readFileSync);
|
|
116
|
+
sys.readDir = wrapRead(sys.readDir);
|
|
117
|
+
sys.readDirSync = wrapRead(sys.readDirSync);
|
|
118
|
+
sys.stat = wrapRead(sys.stat);
|
|
119
|
+
sys.statSync = wrapRead(sys.statSync);
|
|
120
|
+
sys.copyFile = wrapWrite(sys.copyFile);
|
|
121
|
+
sys.createDir = wrapWrite(sys.createDir);
|
|
122
|
+
sys.createDirSync = wrapWrite(sys.createDirSync);
|
|
123
|
+
sys.removeFile = wrapWrite(sys.removeFile);
|
|
124
|
+
sys.removeFileSync = wrapWrite(sys.removeFileSync);
|
|
125
|
+
sys.writeFile = wrapWrite(sys.writeFile);
|
|
126
|
+
sys.writeFileSync = wrapWrite(sys.writeFileSync);
|
|
127
|
+
sys.getCompilerExecutingPath = () => "bin/stencil.js";
|
|
128
|
+
Object.defineProperties(sys, {
|
|
129
|
+
diskReads: {
|
|
130
|
+
get() {
|
|
131
|
+
return diskReads;
|
|
132
|
+
},
|
|
133
|
+
set(val) {
|
|
134
|
+
diskReads = val;
|
|
135
|
+
}
|
|
136
|
+
},
|
|
137
|
+
diskWrites: {
|
|
138
|
+
get() {
|
|
139
|
+
return diskWrites;
|
|
140
|
+
},
|
|
141
|
+
set(val) {
|
|
142
|
+
diskWrites = val;
|
|
143
|
+
}
|
|
144
|
+
}
|
|
145
|
+
});
|
|
146
|
+
if (!isTestingSystem(sys)) throw new Error("could not generate TestingSystem");
|
|
147
|
+
return sys;
|
|
148
|
+
};
|
|
149
|
+
//#endregion
|
|
150
|
+
//#region src/testing/mocks.ts
|
|
151
|
+
/**
|
|
152
|
+
* Generates a stub {@link d.ComponentCompilerMeta}. This function uses sensible defaults for the initial stub. However,
|
|
153
|
+
* any field in the object may be overridden via the `overrides` argument.
|
|
154
|
+
* @param overrides a partial implementation of `ComponentCompilerMeta`. Any provided fields will override the
|
|
155
|
+
* defaults provided by this function.
|
|
156
|
+
* @returns the stubbed `ComponentCompilerMeta`
|
|
157
|
+
*/
|
|
158
|
+
const mockComponentMeta = (overrides = {}) => ({
|
|
159
|
+
assetsDirs: [],
|
|
160
|
+
attachInternalsMemberName: null,
|
|
161
|
+
attachInternalsCustomStates: [],
|
|
162
|
+
componentClassName: "StubCmp",
|
|
163
|
+
dependencies: [],
|
|
164
|
+
dependents: [],
|
|
165
|
+
deserializers: [],
|
|
166
|
+
directDependencies: [],
|
|
167
|
+
directDependents: [],
|
|
168
|
+
docs: {
|
|
169
|
+
text: "docs",
|
|
170
|
+
tags: []
|
|
171
|
+
},
|
|
172
|
+
doesExtend: false,
|
|
173
|
+
elementRef: "",
|
|
174
|
+
encapsulation: "none",
|
|
175
|
+
events: [],
|
|
176
|
+
excludeFromCollection: false,
|
|
177
|
+
formAssociated: false,
|
|
178
|
+
hasAttribute: false,
|
|
179
|
+
hasAttributeChangedCallbackFn: false,
|
|
180
|
+
hasComponentDidLoadFn: false,
|
|
181
|
+
hasComponentDidRenderFn: false,
|
|
182
|
+
hasComponentDidUpdateFn: false,
|
|
183
|
+
hasComponentShouldUpdateFn: false,
|
|
184
|
+
hasComponentWillLoadFn: false,
|
|
185
|
+
hasComponentWillRenderFn: false,
|
|
186
|
+
hasComponentWillUpdateFn: false,
|
|
187
|
+
hasConnectedCallbackFn: false,
|
|
188
|
+
hasDeserializer: false,
|
|
189
|
+
hasDisconnectedCallbackFn: false,
|
|
190
|
+
hasElement: false,
|
|
191
|
+
hasEvent: false,
|
|
192
|
+
hasLifecycle: false,
|
|
193
|
+
hasListener: false,
|
|
194
|
+
hasListenerTarget: false,
|
|
195
|
+
hasListenerTargetBody: false,
|
|
196
|
+
hasListenerTargetDocument: false,
|
|
197
|
+
hasListenerTargetWindow: false,
|
|
198
|
+
hasMember: false,
|
|
199
|
+
hasMethod: false,
|
|
200
|
+
hasMode: false,
|
|
201
|
+
hasModernPropertyDecls: false,
|
|
202
|
+
hasPatchAll: false,
|
|
203
|
+
hasPatchChildren: false,
|
|
204
|
+
hasPatchClone: false,
|
|
205
|
+
hasPatchInsert: false,
|
|
206
|
+
hasProp: false,
|
|
207
|
+
hasPropBoolean: false,
|
|
208
|
+
hasPropMutable: false,
|
|
209
|
+
hasPropNumber: false,
|
|
210
|
+
hasPropString: false,
|
|
211
|
+
hasReflect: false,
|
|
212
|
+
hasRenderFn: false,
|
|
213
|
+
hasSerializer: false,
|
|
214
|
+
hasSlot: false,
|
|
215
|
+
hasState: false,
|
|
216
|
+
hasStyle: false,
|
|
217
|
+
hasVdomAttribute: false,
|
|
218
|
+
hasVdomClass: false,
|
|
219
|
+
hasVdomFunctional: false,
|
|
220
|
+
hasVdomKey: false,
|
|
221
|
+
hasVdomListener: false,
|
|
222
|
+
hasVdomPropOrAttr: false,
|
|
223
|
+
hasVdomRef: false,
|
|
224
|
+
hasVdomRender: false,
|
|
225
|
+
hasVdomStyle: false,
|
|
226
|
+
hasVdomText: false,
|
|
227
|
+
hasVdomXlink: false,
|
|
228
|
+
hasSignalsImport: false,
|
|
229
|
+
hasWatchCallback: false,
|
|
230
|
+
htmlAttrNames: [],
|
|
231
|
+
htmlParts: [],
|
|
232
|
+
htmlTagNames: [],
|
|
233
|
+
internal: false,
|
|
234
|
+
isCollectionDependency: false,
|
|
235
|
+
isPlain: false,
|
|
236
|
+
isUpdateable: false,
|
|
237
|
+
jsFilePath: "/some/stubbed/path/my-component.js",
|
|
238
|
+
listeners: [],
|
|
239
|
+
methods: [],
|
|
240
|
+
patches: null,
|
|
241
|
+
potentialCmpRefs: [],
|
|
242
|
+
properties: [],
|
|
243
|
+
serializers: [],
|
|
244
|
+
shadowDelegatesFocus: false,
|
|
245
|
+
shadowMode: null,
|
|
246
|
+
slotAssignment: null,
|
|
247
|
+
sourceFilePath: "/some/stubbed/path/my-component.tsx",
|
|
248
|
+
sourceMapPath: "/some/stubbed/path/my-component.js.map",
|
|
249
|
+
states: [],
|
|
250
|
+
styleDocs: [],
|
|
251
|
+
styles: [],
|
|
252
|
+
globalStyles: [],
|
|
253
|
+
tagName: "stub-cmp",
|
|
254
|
+
virtualProperties: [],
|
|
255
|
+
watchers: [],
|
|
256
|
+
...overrides
|
|
257
|
+
});
|
|
258
|
+
/**
|
|
259
|
+
* Creates a mock instance of an internal, validated Stencil configuration object
|
|
260
|
+
* the caller
|
|
261
|
+
* @param overrides a partial implementation of `ValidatedConfig`. Any provided fields will override the defaults
|
|
262
|
+
* provided by this function.
|
|
263
|
+
* @returns the mock Stencil configuration
|
|
264
|
+
*/
|
|
265
|
+
function mockValidatedConfig(overrides = {}) {
|
|
266
|
+
const baseConfig = mockConfig(overrides);
|
|
267
|
+
const rootDir = path.resolve("/");
|
|
268
|
+
return {
|
|
269
|
+
...baseConfig,
|
|
270
|
+
cacheDir: ".stencil",
|
|
271
|
+
devMode: true,
|
|
272
|
+
devServer: {},
|
|
273
|
+
compat: {},
|
|
274
|
+
fsNamespace: "testing",
|
|
275
|
+
hydratedFlag: null,
|
|
276
|
+
logLevel: "info",
|
|
277
|
+
logger: mockLogger(),
|
|
278
|
+
minifyCss: false,
|
|
279
|
+
minifyJs: false,
|
|
280
|
+
namespace: "Testing",
|
|
281
|
+
outputTargets: baseConfig.outputTargets ?? [],
|
|
282
|
+
packageJsonFilePath: path.join(rootDir, "package.json"),
|
|
283
|
+
rootDir,
|
|
284
|
+
sourceMap: true,
|
|
285
|
+
srcDir: "/src",
|
|
286
|
+
srcIndexHtml: "src/index.html",
|
|
287
|
+
suppressReservedPublicNameWarnings: false,
|
|
288
|
+
suppressReservedEventNameWarnings: false,
|
|
289
|
+
sys: createTestingSystem(),
|
|
290
|
+
transformAliasedImportPaths: true,
|
|
291
|
+
rolldownConfig: {},
|
|
292
|
+
...overrides
|
|
293
|
+
};
|
|
294
|
+
}
|
|
295
|
+
/**
|
|
296
|
+
* Creates a mock instance of a Stencil configuration entity. The mocked configuration has no guarantees around the
|
|
297
|
+
* types/validity of its data.
|
|
298
|
+
* @param overrides a partial implementation of `UnvalidatedConfig`. Any provided fields will override the defaults
|
|
299
|
+
* provided by this function.
|
|
300
|
+
* @returns the mock Stencil configuration
|
|
301
|
+
*/
|
|
302
|
+
function mockConfig(overrides = {}) {
|
|
303
|
+
const rootDir = path.resolve("/");
|
|
304
|
+
let { sys } = overrides;
|
|
305
|
+
if (!sys) sys = createTestingSystem();
|
|
306
|
+
sys.getCurrentDirectory = () => rootDir;
|
|
307
|
+
return {
|
|
308
|
+
_isTesting: true,
|
|
309
|
+
buildAppCore: false,
|
|
310
|
+
bundles: null,
|
|
311
|
+
devMode: true,
|
|
312
|
+
enableCache: false,
|
|
313
|
+
compat: {},
|
|
314
|
+
globalScript: null,
|
|
315
|
+
logger: new TestingLogger(),
|
|
316
|
+
maxConcurrentWorkers: 0,
|
|
317
|
+
minifyCss: false,
|
|
318
|
+
minifyJs: false,
|
|
319
|
+
namespace: "Testing",
|
|
320
|
+
nodeResolve: {},
|
|
321
|
+
outputTargets: null,
|
|
322
|
+
rolldownPlugins: {
|
|
323
|
+
before: [],
|
|
324
|
+
after: []
|
|
325
|
+
},
|
|
326
|
+
rootDir,
|
|
327
|
+
sourceMap: true,
|
|
328
|
+
suppressReservedPublicNameWarnings: false,
|
|
329
|
+
suppressReservedEventNameWarnings: false,
|
|
330
|
+
sys,
|
|
331
|
+
validateTypes: false,
|
|
332
|
+
...overrides
|
|
333
|
+
};
|
|
334
|
+
}
|
|
335
|
+
/**
|
|
336
|
+
* Creates a configuration object used to bootstrap a Stencil task invocation
|
|
337
|
+
*
|
|
338
|
+
* Several fields are intentionally undefined for this entity. While it would be trivial to stub them out, this mock
|
|
339
|
+
* generation function operates under the assumption that entities like loggers and compiler system abstractions will
|
|
340
|
+
* be shared by multiple entities in a test suite, who should provide those entities to this function
|
|
341
|
+
*
|
|
342
|
+
* @param overrides the properties on the default entity to manually override
|
|
343
|
+
* @returns the default configuration initialization object, with any overrides applied
|
|
344
|
+
*/
|
|
345
|
+
const mockLoadConfigInit = (overrides) => {
|
|
346
|
+
return {
|
|
347
|
+
config: {},
|
|
348
|
+
configPath: void 0,
|
|
349
|
+
logger: void 0,
|
|
350
|
+
sys: void 0,
|
|
351
|
+
...overrides
|
|
352
|
+
};
|
|
353
|
+
};
|
|
354
|
+
function mockCompilerCtx(config) {
|
|
355
|
+
const innerConfig = config || mockValidatedConfig();
|
|
356
|
+
const compilerCtx = {
|
|
357
|
+
version: 1,
|
|
358
|
+
activeBuildId: 0,
|
|
359
|
+
activeDirsAdded: [],
|
|
360
|
+
activeDirsDeleted: [],
|
|
361
|
+
activeFilesAdded: [],
|
|
362
|
+
activeFilesDeleted: [],
|
|
363
|
+
activeFilesUpdated: [],
|
|
364
|
+
addWatchDir: noop,
|
|
365
|
+
addWatchFile: noop,
|
|
366
|
+
globalStyleCache: /* @__PURE__ */ new Map(),
|
|
367
|
+
changedFiles: /* @__PURE__ */ new Set(),
|
|
368
|
+
changedModules: /* @__PURE__ */ new Set(),
|
|
369
|
+
collections: [],
|
|
370
|
+
compilerOptions: null,
|
|
371
|
+
cache: null,
|
|
372
|
+
cssModuleImports: /* @__PURE__ */ new Map(),
|
|
373
|
+
events: buildEvents(),
|
|
374
|
+
fs: null,
|
|
375
|
+
hasSuccessfulBuild: false,
|
|
376
|
+
isActivelyBuilding: false,
|
|
377
|
+
lastBuildResults: null,
|
|
378
|
+
moduleMap: /* @__PURE__ */ new Map(),
|
|
379
|
+
nodeMap: /* @__PURE__ */ new WeakMap(),
|
|
380
|
+
reset: noop,
|
|
381
|
+
resolvedCollections: /* @__PURE__ */ new Set(),
|
|
382
|
+
rolldownCache: /* @__PURE__ */ new Map(),
|
|
383
|
+
rolldownCacheSsr: null,
|
|
384
|
+
rolldownCacheLazy: null,
|
|
385
|
+
rolldownCacheNative: null,
|
|
386
|
+
transpileCache: /* @__PURE__ */ new Map(),
|
|
387
|
+
prevStylesMap: /* @__PURE__ */ new Map(),
|
|
388
|
+
styleModeNames: /* @__PURE__ */ new Set(),
|
|
389
|
+
worker: createWorkerContext(innerConfig.sys),
|
|
390
|
+
cssTransformCache: /* @__PURE__ */ new Map()
|
|
391
|
+
};
|
|
392
|
+
Object.defineProperty(compilerCtx, "fs", { get() {
|
|
393
|
+
if (this._fs == null) this._fs = createInMemoryFs(innerConfig.sys);
|
|
394
|
+
return this._fs;
|
|
395
|
+
} });
|
|
396
|
+
Object.defineProperty(compilerCtx, "cache", { get() {
|
|
397
|
+
if (this._cache == null) this._cache = mockCache(innerConfig, compilerCtx);
|
|
398
|
+
return this._cache;
|
|
399
|
+
} });
|
|
400
|
+
return compilerCtx;
|
|
401
|
+
}
|
|
402
|
+
function mockBuildCtx(config, compilerCtx) {
|
|
403
|
+
const validatedConfig = config || mockValidatedConfig();
|
|
404
|
+
return new BuildContext(validatedConfig, compilerCtx || mockCompilerCtx(validatedConfig));
|
|
405
|
+
}
|
|
406
|
+
function mockCache(config, compilerCtx) {
|
|
407
|
+
config.enableCache = true;
|
|
408
|
+
const cache = new Cache(config, compilerCtx.fs);
|
|
409
|
+
cache.initCacheDir();
|
|
410
|
+
return cache;
|
|
411
|
+
}
|
|
412
|
+
function mockLogger() {
|
|
413
|
+
return new TestingLogger();
|
|
414
|
+
}
|
|
415
|
+
/**
|
|
416
|
+
* Create a {@link d.CompilerSystem} entity for testing the compiler.
|
|
417
|
+
*
|
|
418
|
+
* This function acts as a thin wrapper around a {@link TestingSystem} entity creation. It exists to provide a logical
|
|
419
|
+
* place in the codebase where we might expect Stencil engineers to reach for when attempting to mock a
|
|
420
|
+
* {@link d.CompilerSystem} base type. Should there prove to be usage of both this function and the one it wraps,
|
|
421
|
+
* reconsider if this wrapper is necessary.
|
|
422
|
+
*
|
|
423
|
+
* @returns a System instance for testing purposes.
|
|
424
|
+
*/
|
|
425
|
+
function mockCompilerSystem() {
|
|
426
|
+
return createTestingSystem();
|
|
427
|
+
}
|
|
428
|
+
function mockDocument(html = null) {
|
|
429
|
+
return new MockWindow(html).document;
|
|
430
|
+
}
|
|
431
|
+
function mockWindow(html) {
|
|
432
|
+
return new MockWindow(html);
|
|
433
|
+
}
|
|
434
|
+
/**
|
|
435
|
+
* This gives you a mock Module, an interface which is the internal compiler
|
|
436
|
+
* representation of a module. It includes a bunch of information necessary for
|
|
437
|
+
* compilation, this mock basically sets sane defaults for all those values.
|
|
438
|
+
*
|
|
439
|
+
* @param mod is an override module that you can supply to set particular values
|
|
440
|
+
* @returns a module object ready to use in tests!
|
|
441
|
+
*/
|
|
442
|
+
const mockModule = (mod = {}) => ({
|
|
443
|
+
cmps: [],
|
|
444
|
+
isExtended: false,
|
|
445
|
+
isMixin: false,
|
|
446
|
+
hasExportableMixins: false,
|
|
447
|
+
coreRuntimeApis: [],
|
|
448
|
+
outputTargetCoreRuntimeApis: {},
|
|
449
|
+
collectionName: "",
|
|
450
|
+
dtsFilePath: "",
|
|
451
|
+
excludeFromCollection: false,
|
|
452
|
+
externalImports: [],
|
|
453
|
+
htmlAttrNames: [],
|
|
454
|
+
htmlTagNames: [],
|
|
455
|
+
htmlParts: [],
|
|
456
|
+
isCollectionDependency: false,
|
|
457
|
+
isLegacy: false,
|
|
458
|
+
jsFilePath: "",
|
|
459
|
+
localImports: [],
|
|
460
|
+
functionalComponentDeps: [],
|
|
461
|
+
originalImports: [],
|
|
462
|
+
originalCollectionComponentPath: "",
|
|
463
|
+
potentialCmpRefs: [],
|
|
464
|
+
sourceFilePath: "",
|
|
465
|
+
staticSourceFile: "",
|
|
466
|
+
staticSourceFileText: "",
|
|
467
|
+
sourceMapPath: "",
|
|
468
|
+
sourceMapFileText: "",
|
|
469
|
+
hasVdomAttribute: false,
|
|
470
|
+
hasVdomClass: false,
|
|
471
|
+
hasVdomFunctional: false,
|
|
472
|
+
hasVdomKey: false,
|
|
473
|
+
hasVdomListener: false,
|
|
474
|
+
hasVdomPropOrAttr: false,
|
|
475
|
+
hasVdomRef: false,
|
|
476
|
+
hasVdomRender: false,
|
|
477
|
+
hasVdomStyle: false,
|
|
478
|
+
hasVdomText: false,
|
|
479
|
+
hasVdomXlink: false,
|
|
480
|
+
hasSignalsImport: false,
|
|
481
|
+
...mod
|
|
482
|
+
});
|
|
483
|
+
//#endregion
|
|
484
|
+
//#region src/testing/create-test-compiler.ts
|
|
485
|
+
const __dirname = path.dirname(fileURLToPath(import.meta.url));
|
|
486
|
+
const TESTING_TSCONFIG = path.resolve(__dirname, "fixtures/tsconfig.testing.json");
|
|
487
|
+
/**
|
|
488
|
+
* Builds a patched sys that falls through to real disk for TypeScript lib files.
|
|
489
|
+
*
|
|
490
|
+
* @returns A compiler system instance with patched readFileSync, readFile, accessSync, and statSync methods
|
|
491
|
+
*/
|
|
492
|
+
const createPatchedSys = () => {
|
|
493
|
+
const sys = mockCompilerSystem();
|
|
494
|
+
const originalReadFileSync = sys.readFileSync.bind(sys);
|
|
495
|
+
sys.readFileSync = (p) => {
|
|
496
|
+
const mem = originalReadFileSync(p);
|
|
497
|
+
if (mem !== void 0) return mem;
|
|
498
|
+
try {
|
|
499
|
+
return fs.readFileSync(p, "utf-8");
|
|
500
|
+
} catch {
|
|
501
|
+
return;
|
|
502
|
+
}
|
|
503
|
+
};
|
|
504
|
+
const originalReadFile = sys.readFile.bind(sys);
|
|
505
|
+
sys.readFile = async (p) => {
|
|
506
|
+
const mem = await originalReadFile(p);
|
|
507
|
+
if (mem !== void 0) return mem;
|
|
508
|
+
try {
|
|
509
|
+
return fs.readFileSync(p, "utf-8");
|
|
510
|
+
} catch {
|
|
511
|
+
return;
|
|
512
|
+
}
|
|
513
|
+
};
|
|
514
|
+
const originalAccessSync = sys.accessSync.bind(sys);
|
|
515
|
+
sys.accessSync = (p) => {
|
|
516
|
+
if (originalAccessSync(p)) return true;
|
|
517
|
+
try {
|
|
518
|
+
fs.accessSync(p);
|
|
519
|
+
return true;
|
|
520
|
+
} catch {
|
|
521
|
+
return false;
|
|
522
|
+
}
|
|
523
|
+
};
|
|
524
|
+
const originalStatSync = sys.statSync.bind(sys);
|
|
525
|
+
sys.statSync = (p) => {
|
|
526
|
+
const mem = originalStatSync(p);
|
|
527
|
+
if (!mem.error) return mem;
|
|
528
|
+
try {
|
|
529
|
+
const s = fs.statSync(p);
|
|
530
|
+
return {
|
|
531
|
+
isDirectory: s.isDirectory(),
|
|
532
|
+
isFile: s.isFile(),
|
|
533
|
+
isSymbolicLink: s.isSymbolicLink(),
|
|
534
|
+
size: s.size,
|
|
535
|
+
error: null
|
|
536
|
+
};
|
|
537
|
+
} catch {
|
|
538
|
+
return mem;
|
|
539
|
+
}
|
|
540
|
+
};
|
|
541
|
+
sys.getCompilerExecutingPath = () => path.resolve(__dirname, "../../dist/compiler/index.mjs");
|
|
542
|
+
return sys;
|
|
543
|
+
};
|
|
544
|
+
/**
|
|
545
|
+
* Runs the expensive one-time setup for a test compiler suite: patching the
|
|
546
|
+
* sys, reading and validating the tsconfig. Use this in a `beforeAll` block
|
|
547
|
+
* when a describe block contains multiple tests that each need a fresh
|
|
548
|
+
* compiler, to avoid repeating `loadConfig` on every test.
|
|
549
|
+
*
|
|
550
|
+
* @param options - Configuration options for preparing the test compiler
|
|
551
|
+
* @returns A {@link PreparedTestCompiler} that can be passed to {@link createTestCompiler}
|
|
552
|
+
*
|
|
553
|
+
* @example
|
|
554
|
+
* ```ts
|
|
555
|
+
* let setup: PreparedTestCompiler;
|
|
556
|
+
* beforeAll(async () => { setup = await prepareTestCompiler(); });
|
|
557
|
+
* beforeEach(async () => {
|
|
558
|
+
* const { compiler } = await createTestCompiler({ setup });
|
|
559
|
+
* });
|
|
560
|
+
* ```
|
|
561
|
+
*/
|
|
562
|
+
const prepareTestCompiler = async (options = {}) => {
|
|
563
|
+
const sys = createPatchedSys();
|
|
564
|
+
const tsconfigPath = options.tsconfig ?? TESTING_TSCONFIG;
|
|
565
|
+
const { config: validatedConfig } = await loadConfig({
|
|
566
|
+
sys,
|
|
567
|
+
config: {
|
|
568
|
+
devMode: true,
|
|
569
|
+
sourceMap: false,
|
|
570
|
+
enableCache: false,
|
|
571
|
+
minifyJs: false,
|
|
572
|
+
minifyCss: false,
|
|
573
|
+
namespace: "Testing",
|
|
574
|
+
tsconfig: tsconfigPath,
|
|
575
|
+
...options.config
|
|
576
|
+
}
|
|
577
|
+
});
|
|
578
|
+
return {
|
|
579
|
+
_validatedConfig: validatedConfig,
|
|
580
|
+
_tsconfigPath: tsconfigPath
|
|
581
|
+
};
|
|
582
|
+
};
|
|
583
|
+
/**
|
|
584
|
+
* Creates a test compiler instance with a hybrid filesystem (reads from disk, writes to memory).
|
|
585
|
+
* This utility handles the common setup pattern for compiler tests.
|
|
586
|
+
*
|
|
587
|
+
* When multiple tests in the same suite need independent compiler instances,
|
|
588
|
+
* pass a {@link PreparedTestCompiler} from {@link prepareTestCompiler} as
|
|
589
|
+
* `options.setup` to skip the expensive `loadConfig` step on each test.
|
|
590
|
+
*
|
|
591
|
+
* @param options - Configuration options for the test compiler
|
|
592
|
+
* @returns An object with the compiler, validated config, and system instance
|
|
593
|
+
*
|
|
594
|
+
* @example
|
|
595
|
+
* ```ts
|
|
596
|
+
* const { compiler, config } = await createTestCompiler({
|
|
597
|
+
* config: { minifyCss: true }
|
|
598
|
+
* });
|
|
599
|
+
* await compiler.fs.writeFile('/src/index.html', '<cmp-a></cmp-a>');
|
|
600
|
+
* const result = await compiler.build();
|
|
601
|
+
* ```
|
|
602
|
+
*/
|
|
603
|
+
const createTestCompiler = async (options = {}) => {
|
|
604
|
+
let validatedConfig;
|
|
605
|
+
let tsconfigPath;
|
|
606
|
+
if (options.setup) {
|
|
607
|
+
const freshSys = createPatchedSys();
|
|
608
|
+
validatedConfig = {
|
|
609
|
+
...options.setup._validatedConfig,
|
|
610
|
+
sys: freshSys
|
|
611
|
+
};
|
|
612
|
+
tsconfigPath = options.setup._tsconfigPath;
|
|
613
|
+
} else {
|
|
614
|
+
const sys = createPatchedSys();
|
|
615
|
+
tsconfigPath = options.tsconfig ?? TESTING_TSCONFIG;
|
|
616
|
+
const { config } = await loadConfig({
|
|
617
|
+
sys,
|
|
618
|
+
config: {
|
|
619
|
+
devMode: true,
|
|
620
|
+
sourceMap: false,
|
|
621
|
+
enableCache: false,
|
|
622
|
+
minifyJs: false,
|
|
623
|
+
minifyCss: false,
|
|
624
|
+
namespace: "Testing",
|
|
625
|
+
tsconfig: tsconfigPath,
|
|
626
|
+
...options.config
|
|
627
|
+
}
|
|
628
|
+
});
|
|
629
|
+
validatedConfig = config;
|
|
630
|
+
}
|
|
631
|
+
const compiler = await createCompiler(validatedConfig);
|
|
632
|
+
const tsconfigObj = JSON.parse(fs.readFileSync(tsconfigPath, "utf-8"));
|
|
633
|
+
await compiler.fs.writeFile(tsconfigPath, JSON.stringify({
|
|
634
|
+
...tsconfigObj,
|
|
635
|
+
include: [validatedConfig.srcDir]
|
|
636
|
+
}));
|
|
637
|
+
await compiler.fs.writeFile(path.join(validatedConfig.srcDir, "components.d.ts"), "");
|
|
638
|
+
return {
|
|
639
|
+
compiler,
|
|
640
|
+
config: validatedConfig,
|
|
641
|
+
sys: validatedConfig.sys
|
|
642
|
+
};
|
|
643
|
+
};
|
|
644
|
+
//#endregion
|
|
645
|
+
//#region src/testing/platform/testing-constants.ts
|
|
646
|
+
const styles = /* @__PURE__ */ new Map();
|
|
647
|
+
const modeResolutionChain = [];
|
|
648
|
+
/**
|
|
649
|
+
* A mapping of custom element tags (e.g. `my-component`) to their constructor
|
|
650
|
+
*/
|
|
651
|
+
const cstrs = /* @__PURE__ */ new Map();
|
|
652
|
+
/**
|
|
653
|
+
* A collection of callbacks to run on a NodeJS process 'tick'
|
|
654
|
+
*/
|
|
655
|
+
const queuedTicks = [];
|
|
656
|
+
const queuedWriteTasks = [];
|
|
657
|
+
const queuedReadTasks = [];
|
|
658
|
+
const moduleLoaded = /* @__PURE__ */ new Map();
|
|
659
|
+
const queuedLoadModules = [];
|
|
660
|
+
/**
|
|
661
|
+
* A collection of errors that were detected to surface during the rendering process
|
|
662
|
+
*/
|
|
663
|
+
const caughtErrors = [];
|
|
664
|
+
//#endregion
|
|
665
|
+
//#region src/testing/platform/testing-build.ts
|
|
666
|
+
const Build = {
|
|
667
|
+
isDev: true,
|
|
668
|
+
isBrowser: false,
|
|
669
|
+
isServer: true,
|
|
670
|
+
isTesting: true
|
|
671
|
+
};
|
|
672
|
+
//#endregion
|
|
673
|
+
//#region src/testing/platform/testing-host-ref.ts
|
|
674
|
+
/**
|
|
675
|
+
* Retrieve the data structure tracking the component by its runtime reference
|
|
676
|
+
* @param elm the reference to the element
|
|
677
|
+
* @returns the corresponding Stencil reference data structure, or undefined if one cannot be found
|
|
678
|
+
*/
|
|
679
|
+
const getHostRef = (elm) => {
|
|
680
|
+
if (elm.__s_ghr) return elm.__s_ghr();
|
|
681
|
+
};
|
|
682
|
+
/**
|
|
683
|
+
* Add the provided `hostRef` instance to the global {@link hostRefs} map, using the provided `lazyInstance` as a key.
|
|
684
|
+
* @param lazyInstance a Stencil component instance
|
|
685
|
+
* @param hostRef an optional reference to Stencil's tracking data for the component. If none is provided, one will be created.
|
|
686
|
+
* @throws if the provided `lazyInstance` coerces to `null`, or if the `lazyInstance` does not have a `constructor`
|
|
687
|
+
* property
|
|
688
|
+
*/
|
|
689
|
+
const registerInstance = (lazyInstance, hostRef) => {
|
|
690
|
+
if (lazyInstance == null || lazyInstance.constructor == null) throw new Error(`Invalid component constructor`);
|
|
691
|
+
if (hostRef == null) {
|
|
692
|
+
const Cstr = lazyInstance.constructor;
|
|
693
|
+
const tagName = Cstr.COMPILER_META && Cstr.COMPILER_META.tagName ? Cstr.COMPILER_META.tagName : "div";
|
|
694
|
+
const elm = document.createElement(tagName);
|
|
695
|
+
registerHost(elm, {
|
|
696
|
+
$flags$: 0,
|
|
697
|
+
$tagName$: tagName
|
|
698
|
+
});
|
|
699
|
+
hostRef = getHostRef(elm);
|
|
700
|
+
}
|
|
701
|
+
lazyInstance.__s_ghr = () => hostRef;
|
|
702
|
+
hostRef.$lazyInstance$ = lazyInstance;
|
|
703
|
+
if (hostRef.$cmpMeta$?.$flags$ & CMP_FLAGS.hasModernPropertyDecls && (BUILD.state || BUILD.prop)) reWireGetterSetter(lazyInstance, hostRef);
|
|
704
|
+
const Cstr = lazyInstance.constructor;
|
|
705
|
+
const allEvents = [];
|
|
706
|
+
const seenEventMethods = /* @__PURE__ */ new Set();
|
|
707
|
+
if (Cstr.COMPILER_META && Cstr.COMPILER_META.events) Cstr.COMPILER_META.events.forEach((event) => {
|
|
708
|
+
if (!seenEventMethods.has(event.method)) {
|
|
709
|
+
allEvents.push(event);
|
|
710
|
+
seenEventMethods.add(event.method);
|
|
711
|
+
}
|
|
712
|
+
});
|
|
713
|
+
let currentProto = Object.getPrototypeOf(Cstr);
|
|
714
|
+
while (currentProto && currentProto !== Function.prototype && currentProto.name) {
|
|
715
|
+
if (typeof currentProto.events === "object" && Array.isArray(currentProto.events)) currentProto.events.forEach((event) => {
|
|
716
|
+
if (!seenEventMethods.has(event.method)) {
|
|
717
|
+
allEvents.push(event);
|
|
718
|
+
seenEventMethods.add(event.method);
|
|
719
|
+
}
|
|
720
|
+
});
|
|
721
|
+
currentProto = Object.getPrototypeOf(currentProto);
|
|
722
|
+
}
|
|
723
|
+
allEvents.forEach((eventMeta) => {
|
|
724
|
+
if (!lazyInstance[eventMeta.method]) {
|
|
725
|
+
let flags = 0;
|
|
726
|
+
if (eventMeta.bubbles) flags |= EVENT_FLAGS.Bubbles;
|
|
727
|
+
if (eventMeta.composed) flags |= EVENT_FLAGS.Composed;
|
|
728
|
+
if (eventMeta.cancelable) flags |= EVENT_FLAGS.Cancellable;
|
|
729
|
+
lazyInstance[eventMeta.method] = createEvent(lazyInstance, eventMeta.name, flags);
|
|
730
|
+
}
|
|
731
|
+
});
|
|
732
|
+
};
|
|
733
|
+
/**
|
|
734
|
+
* Create a new {@link d.HostRef} instance to the global {@link hostRefs} map, using the provided `elm` as a key.
|
|
735
|
+
* @param elm an HTMLElement instance associated with the Stencil component
|
|
736
|
+
* @param cmpMeta the component compiler metadata associated with the component
|
|
737
|
+
*/
|
|
738
|
+
const registerHost = (elm, cmpMeta) => {
|
|
739
|
+
const hostRef = {
|
|
740
|
+
$flags$: 0,
|
|
741
|
+
$hostElement$: elm,
|
|
742
|
+
$cmpMeta$: cmpMeta,
|
|
743
|
+
$instanceValues$: /* @__PURE__ */ new Map(),
|
|
744
|
+
$serializerValues$: /* @__PURE__ */ new Map(),
|
|
745
|
+
$renderCount$: 0
|
|
746
|
+
};
|
|
747
|
+
hostRef.$fetchedCbList$ = [];
|
|
748
|
+
hostRef.$onInstancePromise$ = new Promise((r) => hostRef.$onInstanceResolve$ = r);
|
|
749
|
+
hostRef.$onReadyPromise$ = new Promise((r) => hostRef.$onReadyResolve$ = r);
|
|
750
|
+
elm["s-p"] = [];
|
|
751
|
+
elm["s-rc"] = [];
|
|
752
|
+
elm.__s_ghr = () => hostRef;
|
|
753
|
+
};
|
|
754
|
+
const setErrorHandler = (handler) => handler;
|
|
755
|
+
//#endregion
|
|
756
|
+
//#region src/testing/platform/testing-task-queue.ts
|
|
757
|
+
/**
|
|
758
|
+
* Reset the various data structures related to the testing rendering pipeline
|
|
759
|
+
*/
|
|
760
|
+
function resetTaskQueue() {
|
|
761
|
+
queuedTicks.length = 0;
|
|
762
|
+
queuedWriteTasks.length = 0;
|
|
763
|
+
queuedReadTasks.length = 0;
|
|
764
|
+
moduleLoaded.clear();
|
|
765
|
+
queuedLoadModules.length = 0;
|
|
766
|
+
caughtErrors.length = 0;
|
|
767
|
+
}
|
|
768
|
+
/**
|
|
769
|
+
* Execute the callbacks in {@link queuedTicks} on the next NodeJS tick.
|
|
770
|
+
*
|
|
771
|
+
* Callbacks are invoked in the order that they appear in `queuedTasks` at the time this function is invoked.
|
|
772
|
+
* Async callbacks are not `await`ed.
|
|
773
|
+
*
|
|
774
|
+
* Any callbacks that are added to `queuedTasks` while this function is running are scheduled to be flushed on the
|
|
775
|
+
* next tick.
|
|
776
|
+
*/
|
|
777
|
+
function flushTicks() {
|
|
778
|
+
return new Promise((resolve, reject) => {
|
|
779
|
+
function drain() {
|
|
780
|
+
try {
|
|
781
|
+
if (queuedTicks.length > 0) {
|
|
782
|
+
const writeTasks = queuedTicks.slice();
|
|
783
|
+
queuedTicks.length = 0;
|
|
784
|
+
let cb;
|
|
785
|
+
while (cb = writeTasks.shift()) cb(Date.now());
|
|
786
|
+
}
|
|
787
|
+
if (queuedTicks.length > 0) process.nextTick(drain);
|
|
788
|
+
else resolve();
|
|
789
|
+
} catch (e) {
|
|
790
|
+
reject(`flushTicks: ${e}`);
|
|
791
|
+
}
|
|
792
|
+
}
|
|
793
|
+
process.nextTick(drain);
|
|
794
|
+
});
|
|
795
|
+
}
|
|
796
|
+
/**
|
|
797
|
+
* Push a RequestAnimationFrame callback onto the {@link queuedWriteTasks} data structure
|
|
798
|
+
* @param cb the callback to push onto `queuedWriteTasks`
|
|
799
|
+
*/
|
|
800
|
+
function writeTask(cb) {
|
|
801
|
+
queuedWriteTasks.push(cb);
|
|
802
|
+
}
|
|
803
|
+
/**
|
|
804
|
+
* Push a RequestAnimationFrame callback onto the {@link queuedReadTasks} data structure
|
|
805
|
+
* @param cb the callback to push onto `queuedReadTasks`
|
|
806
|
+
*/
|
|
807
|
+
function readTask(cb) {
|
|
808
|
+
queuedReadTasks.push(cb);
|
|
809
|
+
}
|
|
810
|
+
/**
|
|
811
|
+
* Flush the {@link queuedReadTasks} and {@link queuedWriteTasks} data structures on the next NodeJS process tick.
|
|
812
|
+
*
|
|
813
|
+
* The read task queue is drained first, followed by the write task queue.
|
|
814
|
+
* For each queue:
|
|
815
|
+
* - Each task is processed in the order it is found in its respective data structure at the time `queuedReadTasks` and
|
|
816
|
+
* `queuedWriteTasks` are read (note: these queues are not read at the same time).
|
|
817
|
+
* - When a task queue is processed, it is marked as empty before acting on the entries in the queue.
|
|
818
|
+
* - Items added to either queue after it has been read for processing will be handled on the subsequent tick.
|
|
819
|
+
* - Async items will be `await`ed
|
|
820
|
+
*/
|
|
821
|
+
function flushQueue() {
|
|
822
|
+
return new Promise((resolve, reject) => {
|
|
823
|
+
async function drain() {
|
|
824
|
+
try {
|
|
825
|
+
if (queuedReadTasks.length > 0) {
|
|
826
|
+
const readTasks = queuedReadTasks.slice();
|
|
827
|
+
queuedReadTasks.length = 0;
|
|
828
|
+
let cb;
|
|
829
|
+
while (cb = readTasks.shift()) {
|
|
830
|
+
const result = cb(Date.now());
|
|
831
|
+
if (result != null && typeof result.then === "function") await result;
|
|
832
|
+
}
|
|
833
|
+
}
|
|
834
|
+
if (queuedWriteTasks.length > 0) {
|
|
835
|
+
const writeTasks = queuedWriteTasks.slice();
|
|
836
|
+
queuedWriteTasks.length = 0;
|
|
837
|
+
let cb;
|
|
838
|
+
while (cb = writeTasks.shift()) {
|
|
839
|
+
const result = cb(Date.now());
|
|
840
|
+
if (result != null && typeof result.then === "function") await result;
|
|
841
|
+
}
|
|
842
|
+
}
|
|
843
|
+
if (queuedReadTasks.length + queuedWriteTasks.length > 0) process.nextTick(drain);
|
|
844
|
+
else resolve();
|
|
845
|
+
} catch (e) {
|
|
846
|
+
reject(`flushQueue: ${e}`);
|
|
847
|
+
}
|
|
848
|
+
}
|
|
849
|
+
process.nextTick(drain);
|
|
850
|
+
});
|
|
851
|
+
}
|
|
852
|
+
async function flushAll() {
|
|
853
|
+
while (queuedTicks.length + queuedLoadModules.length + queuedWriteTasks.length + queuedReadTasks.length > 0) {
|
|
854
|
+
await flushTicks();
|
|
855
|
+
await flushLoadModule();
|
|
856
|
+
await flushQueue();
|
|
857
|
+
}
|
|
858
|
+
if (caughtErrors.length > 0) {
|
|
859
|
+
const err = caughtErrors[0];
|
|
860
|
+
if (err == null) throw new Error("Error!");
|
|
861
|
+
if (typeof err === "string") throw new Error(err);
|
|
862
|
+
throw err;
|
|
863
|
+
}
|
|
864
|
+
return new Promise((resolve) => process.nextTick(resolve));
|
|
865
|
+
}
|
|
866
|
+
function flushLoadModule(bundleId) {
|
|
867
|
+
return new Promise((resolve, reject) => {
|
|
868
|
+
try {
|
|
869
|
+
process.nextTick(() => {
|
|
870
|
+
if (bundleId != null) {
|
|
871
|
+
for (let i = 0; i < queuedLoadModules.length; i++) if (queuedLoadModules[i].bundleId === bundleId) {
|
|
872
|
+
queuedLoadModules[i].resolve();
|
|
873
|
+
queuedLoadModules.splice(i, 1);
|
|
874
|
+
i--;
|
|
875
|
+
}
|
|
876
|
+
} else {
|
|
877
|
+
let queuedLoadModule;
|
|
878
|
+
while (queuedLoadModule = queuedLoadModules.shift()) queuedLoadModule.resolve();
|
|
879
|
+
}
|
|
880
|
+
resolve();
|
|
881
|
+
});
|
|
882
|
+
} catch (e) {
|
|
883
|
+
reject(`flushLoadModule: ${e}`);
|
|
884
|
+
}
|
|
885
|
+
});
|
|
886
|
+
}
|
|
887
|
+
//#endregion
|
|
888
|
+
//#region src/testing/platform/testing-window.ts
|
|
889
|
+
const isVitestEnvironment = typeof process !== "undefined" && process.env?.VITEST;
|
|
890
|
+
const existingWindow = typeof globalThis !== "undefined" && globalThis.window;
|
|
891
|
+
const win = isVitestEnvironment && existingWindow ? existingWindow : setupGlobal(global);
|
|
892
|
+
//#endregion
|
|
893
|
+
//#region src/testing/platform/testing-platform.ts
|
|
894
|
+
const plt = {
|
|
895
|
+
$flags$: 0,
|
|
896
|
+
$resourcesUrl$: "",
|
|
897
|
+
jmp: (h) => h(),
|
|
898
|
+
raf: (h) => requestAnimationFrame(h),
|
|
899
|
+
ael: (el, eventName, listener, opts) => el.addEventListener(eventName, listener, opts),
|
|
900
|
+
rel: (el, eventName, listener, opts) => el.removeEventListener(eventName, listener, opts),
|
|
901
|
+
ce: (eventName, opts) => new win.CustomEvent(eventName, opts)
|
|
902
|
+
};
|
|
903
|
+
/**
|
|
904
|
+
* Resets global testing variables and collections, so that a new set of tests can be started with a "clean slate".
|
|
905
|
+
*
|
|
906
|
+
* It is expected that this function be called between spec tests, and should be automatically configured by Stencil to
|
|
907
|
+
* do so.
|
|
908
|
+
*
|
|
909
|
+
* @param defaults default options for the {@link d.PlatformRuntime} used during testing. The values in this object
|
|
910
|
+
* with be assigned to the global {@link plt} object used during testing.
|
|
911
|
+
*/
|
|
912
|
+
function resetPlatform(defaults = {}) {
|
|
913
|
+
if (win && typeof win.close === "function") win.close();
|
|
914
|
+
styles.clear();
|
|
915
|
+
plt.$flags$ = 0;
|
|
916
|
+
Object.assign(plt, defaults);
|
|
917
|
+
if (plt.$orgLocNodes$ != null) {
|
|
918
|
+
plt.$orgLocNodes$.clear();
|
|
919
|
+
plt.$orgLocNodes$ = void 0;
|
|
920
|
+
}
|
|
921
|
+
resetTaskQueue();
|
|
922
|
+
stopAutoApplyChanges();
|
|
923
|
+
cstrs.clear();
|
|
924
|
+
}
|
|
925
|
+
let isAutoApplyingChanges = false;
|
|
926
|
+
let autoApplyTimer = void 0;
|
|
927
|
+
/**
|
|
928
|
+
* Cancels the JavaScript task of automatically flushing the render queue & applying DOM changes in tests
|
|
929
|
+
*/
|
|
930
|
+
function stopAutoApplyChanges() {
|
|
931
|
+
isAutoApplyingChanges = false;
|
|
932
|
+
if (autoApplyTimer) {
|
|
933
|
+
clearTimeout(autoApplyTimer);
|
|
934
|
+
autoApplyTimer = void 0;
|
|
935
|
+
}
|
|
936
|
+
}
|
|
937
|
+
/**
|
|
938
|
+
* Creates a JavaScript task to flush the render pipeline without the user having to do so manually in their tests.
|
|
939
|
+
*/
|
|
940
|
+
async function startAutoApplyChanges() {
|
|
941
|
+
isAutoApplyingChanges = true;
|
|
942
|
+
flushAll().then(() => {
|
|
943
|
+
if (isAutoApplyingChanges) autoApplyTimer = setTimeout(() => {
|
|
944
|
+
startAutoApplyChanges();
|
|
945
|
+
}, 100);
|
|
946
|
+
});
|
|
947
|
+
}
|
|
948
|
+
/**
|
|
949
|
+
* Registers a collection of component constructors with the global {@link cstrs} data structure
|
|
950
|
+
* @param Cstrs the component constructors to register
|
|
951
|
+
*/
|
|
952
|
+
const registerComponents = (Cstrs) => {
|
|
953
|
+
Cstrs.filter((Cstr) => Cstr.COMPILER_META).forEach((Cstr) => {
|
|
954
|
+
cstrs.set(Cstr.COMPILER_META.tagName, Cstr);
|
|
955
|
+
});
|
|
956
|
+
};
|
|
957
|
+
/**
|
|
958
|
+
* Add the provided component constructor, `Cstr`, to the {@link moduleLoaded} mapping, using the provided `bundleId`
|
|
959
|
+
* as the key
|
|
960
|
+
* @param bundleId the bundle identifier to use to store/retrieve the component constructor
|
|
961
|
+
* @param Cstr the component constructor to store
|
|
962
|
+
*/
|
|
963
|
+
function registerModule(bundleId, Cstr) {
|
|
964
|
+
moduleLoaded.set(bundleId, Cstr);
|
|
965
|
+
}
|
|
966
|
+
//#endregion
|
|
967
|
+
//#region src/runtime/vdom/vdom-annotations.ts
|
|
968
|
+
/**
|
|
969
|
+
* Updates the DOM generated on the server with annotations such as node attributes and
|
|
970
|
+
* comment nodes to facilitate future client-side hydration. These annotations are used for things
|
|
971
|
+
* like moving elements back to their original hosts if using Shadow DOM on the client, and for quickly
|
|
972
|
+
* reconstructing the vNode representations of the DOM.
|
|
973
|
+
*
|
|
974
|
+
* @param doc The DOM generated by the server.
|
|
975
|
+
* @param staticComponents Any components that should be considered static and do not need client-side hydration.
|
|
976
|
+
*/
|
|
977
|
+
const insertVdomAnnotations = (doc, staticComponents) => {
|
|
978
|
+
if (doc != null) {
|
|
979
|
+
/**
|
|
980
|
+
* Initiated `docData` object from the document if it exists to ensure we
|
|
981
|
+
* maintain the same `docData` object across multiple hydration hydration runs.
|
|
982
|
+
*/
|
|
983
|
+
const docData = "_stencilDocData" in doc ? doc[STENCIL_DOC_DATA] : { ...DEFAULT_DOC_DATA };
|
|
984
|
+
docData.staticComponents = new Set(staticComponents);
|
|
985
|
+
const orgLocationNodes = [];
|
|
986
|
+
parseVNodeAnnotations(doc, doc.body, docData, orgLocationNodes);
|
|
987
|
+
orgLocationNodes.forEach((orgLocationNode) => {
|
|
988
|
+
if (orgLocationNode != null && orgLocationNode["s-nr"]) {
|
|
989
|
+
const nodeRef = orgLocationNode["s-nr"];
|
|
990
|
+
let hostId = nodeRef["s-host-id"];
|
|
991
|
+
let nodeId = nodeRef["s-node-id"];
|
|
992
|
+
let childId = `${hostId}.${nodeId}`;
|
|
993
|
+
if (hostId == null) {
|
|
994
|
+
hostId = 0;
|
|
995
|
+
docData.rootLevelIds++;
|
|
996
|
+
nodeId = docData.rootLevelIds;
|
|
997
|
+
childId = `${hostId}.${nodeId}`;
|
|
998
|
+
if (nodeRef.nodeType === NODE_TYPE.ElementNode) {
|
|
999
|
+
nodeRef.setAttribute(HYDRATE_CHILD_ID, childId);
|
|
1000
|
+
if (typeof nodeRef["s-sn"] === "string" && !nodeRef.getAttribute("slot")) nodeRef.setAttribute("s-sn", nodeRef["s-sn"]);
|
|
1001
|
+
} else if (nodeRef.nodeType === NODE_TYPE.TextNode) {
|
|
1002
|
+
if (hostId === 0) {
|
|
1003
|
+
if (nodeRef.nodeValue?.trim() === "") {
|
|
1004
|
+
orgLocationNode.remove();
|
|
1005
|
+
return;
|
|
1006
|
+
}
|
|
1007
|
+
}
|
|
1008
|
+
const commentBeforeTextNode = doc.createComment(childId);
|
|
1009
|
+
commentBeforeTextNode.nodeValue = `t.${childId}`;
|
|
1010
|
+
insertBefore(nodeRef.parentNode, commentBeforeTextNode, nodeRef);
|
|
1011
|
+
} else if (nodeRef.nodeType === NODE_TYPE.CommentNode) {
|
|
1012
|
+
const commentBeforeTextNode = doc.createComment(childId);
|
|
1013
|
+
commentBeforeTextNode.nodeValue = `c.${childId}`;
|
|
1014
|
+
nodeRef.parentNode.insertBefore(commentBeforeTextNode, nodeRef);
|
|
1015
|
+
}
|
|
1016
|
+
}
|
|
1017
|
+
let orgLocationNodeId = `o.${childId}`;
|
|
1018
|
+
const orgLocationParentNode = orgLocationNode.parentElement;
|
|
1019
|
+
if (orgLocationParentNode) {
|
|
1020
|
+
if (orgLocationParentNode["s-en"] === "") orgLocationNodeId += `.`;
|
|
1021
|
+
else if (orgLocationParentNode["s-en"] === "c") orgLocationNodeId += `.c`;
|
|
1022
|
+
}
|
|
1023
|
+
orgLocationNode.nodeValue = orgLocationNodeId;
|
|
1024
|
+
}
|
|
1025
|
+
});
|
|
1026
|
+
}
|
|
1027
|
+
};
|
|
1028
|
+
/**
|
|
1029
|
+
* Recursively parses a node generated by the server and its children to set host and child id
|
|
1030
|
+
* attributes read during client-side hydration. This function also tracks whether each node is
|
|
1031
|
+
* an original location reference node meaning that a node has been moved via slot relocation.
|
|
1032
|
+
*
|
|
1033
|
+
* @param doc The DOM generated by the server.
|
|
1034
|
+
* @param node The node to parse.
|
|
1035
|
+
* @param docData An object containing metadata about the document.
|
|
1036
|
+
* @param orgLocationNodes An array of nodes that have been moved via slot relocation.
|
|
1037
|
+
*/
|
|
1038
|
+
const parseVNodeAnnotations = (doc, node, docData, orgLocationNodes) => {
|
|
1039
|
+
if (node == null) return;
|
|
1040
|
+
if (node["s-nr"] != null) orgLocationNodes.push(node);
|
|
1041
|
+
if (node.nodeType === NODE_TYPE.ElementNode) [...Array.from(node.childNodes), ...Array.from(node.shadowRoot?.childNodes || [])].forEach((childNode) => {
|
|
1042
|
+
const hostRef = getHostRef$1(childNode);
|
|
1043
|
+
if (hostRef != null && !docData.staticComponents.has(childNode.nodeName.toLowerCase())) insertVNodeAnnotations(doc, childNode, hostRef.$vnode$, docData, { nodeIds: 0 });
|
|
1044
|
+
parseVNodeAnnotations(doc, childNode, docData, orgLocationNodes);
|
|
1045
|
+
});
|
|
1046
|
+
};
|
|
1047
|
+
/**
|
|
1048
|
+
* Insert attribute annotations on an element for its host ID and, potentially, its child ID.
|
|
1049
|
+
* Also makes calls to insert annotations on the element's children, keeping track of the depth of
|
|
1050
|
+
* the component tree.
|
|
1051
|
+
*
|
|
1052
|
+
* @param doc The DOM generated by the server.
|
|
1053
|
+
* @param hostElm The element to insert annotations for.
|
|
1054
|
+
* @param vnode The vNode representation of the element.
|
|
1055
|
+
* @param docData An object containing metadata about the document.
|
|
1056
|
+
* @param cmpData An object containing metadata about the component.
|
|
1057
|
+
*/
|
|
1058
|
+
const insertVNodeAnnotations = (doc, hostElm, vnode, docData, cmpData) => {
|
|
1059
|
+
if (vnode != null) {
|
|
1060
|
+
const hostId = ++docData.hostIds;
|
|
1061
|
+
hostElm.setAttribute(HYDRATE_ID, hostId);
|
|
1062
|
+
if (hostElm["s-cr"] != null) hostElm["s-cr"].nodeValue = `r.${hostId}`;
|
|
1063
|
+
if (vnode.$children$ != null) {
|
|
1064
|
+
const depth = 0;
|
|
1065
|
+
vnode.$children$.forEach((vnodeChild, index) => {
|
|
1066
|
+
insertChildVNodeAnnotations(doc, vnodeChild, cmpData, hostId, depth, index);
|
|
1067
|
+
});
|
|
1068
|
+
}
|
|
1069
|
+
if (hostElm && vnode && vnode.$elm$ && !hostElm.hasAttribute("c-id")) {
|
|
1070
|
+
const parent = hostElm.parentElement;
|
|
1071
|
+
if (parent && parent.childNodes) {
|
|
1072
|
+
const parentChildNodes = Array.from(parent.childNodes);
|
|
1073
|
+
const comment = parentChildNodes.find((node) => node.nodeType === NODE_TYPE.CommentNode && node["s-sr"]);
|
|
1074
|
+
if (comment) {
|
|
1075
|
+
const index = parentChildNodes.indexOf(hostElm) - 1;
|
|
1076
|
+
vnode.$elm$.setAttribute(HYDRATE_CHILD_ID, `${comment["s-host-id"]}.${comment["s-node-id"]}.0.${index}`);
|
|
1077
|
+
}
|
|
1078
|
+
}
|
|
1079
|
+
}
|
|
1080
|
+
}
|
|
1081
|
+
};
|
|
1082
|
+
/**
|
|
1083
|
+
* Recursively analyzes the type of a child vNode and inserts annotations on the vNodes's element based on its type.
|
|
1084
|
+
* Element nodes receive a child ID attribute, text nodes have a comment with the child ID inserted before them,
|
|
1085
|
+
* and comment nodes representing a slot have their node value set to a slot node ID containing the child ID.
|
|
1086
|
+
*
|
|
1087
|
+
* @param doc The DOM generated by the server.
|
|
1088
|
+
* @param vnodeChild The vNode to insert annotations for.
|
|
1089
|
+
* @param cmpData An object containing metadata about the component.
|
|
1090
|
+
* @param hostId The host ID of this element's parent.
|
|
1091
|
+
* @param depth How deep this element sits in the component tree relative to its parent.
|
|
1092
|
+
* @param index The index of this element in its parent's children array.
|
|
1093
|
+
*/
|
|
1094
|
+
const insertChildVNodeAnnotations = (doc, vnodeChild, cmpData, hostId, depth, index) => {
|
|
1095
|
+
const childElm = vnodeChild.$elm$;
|
|
1096
|
+
if (childElm == null) return;
|
|
1097
|
+
const nodeId = cmpData.nodeIds++;
|
|
1098
|
+
const childId = `${hostId}.${nodeId}.${depth}.${index}`;
|
|
1099
|
+
childElm["s-host-id"] = hostId;
|
|
1100
|
+
childElm["s-node-id"] = nodeId;
|
|
1101
|
+
if (childElm.nodeType === NODE_TYPE.ElementNode) {
|
|
1102
|
+
childElm.setAttribute(HYDRATE_CHILD_ID, childId);
|
|
1103
|
+
if (typeof childElm["s-sn"] === "string" && !childElm.getAttribute("slot")) childElm.setAttribute("s-sn", childElm["s-sn"]);
|
|
1104
|
+
} else if (childElm.nodeType === NODE_TYPE.TextNode) {
|
|
1105
|
+
const parentNode = childElm.parentNode;
|
|
1106
|
+
const nodeName = parentNode?.nodeName;
|
|
1107
|
+
if (nodeName !== "STYLE" && nodeName !== "SCRIPT") {
|
|
1108
|
+
const textNodeId = `t.${childId}`;
|
|
1109
|
+
insertBefore(parentNode, doc.createComment(textNodeId), childElm);
|
|
1110
|
+
}
|
|
1111
|
+
} else if (childElm.nodeType === NODE_TYPE.CommentNode) {
|
|
1112
|
+
if (childElm["s-sr"]) childElm.nodeValue = `s.${childId}.${childElm["s-sn"] || ""}`;
|
|
1113
|
+
}
|
|
1114
|
+
if (vnodeChild.$children$ != null) {
|
|
1115
|
+
const childDepth = depth + 1;
|
|
1116
|
+
vnodeChild.$children$.forEach((vnode, childIndex) => {
|
|
1117
|
+
insertChildVNodeAnnotations(doc, vnode, cmpData, hostId, childDepth, childIndex);
|
|
1118
|
+
});
|
|
1119
|
+
}
|
|
1120
|
+
};
|
|
1121
|
+
//#endregion
|
|
1122
|
+
//#region src/testing/platform/index.ts
|
|
1123
|
+
const setMode = (handler) => {
|
|
1124
|
+
modeResolutionChain.length = 0;
|
|
1125
|
+
modeResolutionChain.push(handler);
|
|
1126
|
+
};
|
|
1127
|
+
//#endregion
|
|
1128
|
+
//#region src/testing/reset-build-conditionals.ts
|
|
1129
|
+
/**
|
|
1130
|
+
* Reset build conditionals used for testing to a known "good state".
|
|
1131
|
+
*
|
|
1132
|
+
* This function does not return a value, but rather mutates its argument in place.
|
|
1133
|
+
* Certain values are set to `true` or `false` for testing purpose (see this function's implementation for the full
|
|
1134
|
+
* list). Build conditional options _not_ in that list that are set to `true` when this function is invoked will remain
|
|
1135
|
+
* set to `true`.
|
|
1136
|
+
*
|
|
1137
|
+
* @param b the build conditionals to reset.
|
|
1138
|
+
*/
|
|
1139
|
+
function resetBuildConditionals(b) {
|
|
1140
|
+
Object.keys(b).forEach((key) => {
|
|
1141
|
+
b[key] = true;
|
|
1142
|
+
});
|
|
1143
|
+
b.isDev = true;
|
|
1144
|
+
b.isTesting = true;
|
|
1145
|
+
b.isDebug = false;
|
|
1146
|
+
b.lazyLoad = true;
|
|
1147
|
+
b.member = true;
|
|
1148
|
+
b.reflect = true;
|
|
1149
|
+
b.scoped = true;
|
|
1150
|
+
b.shadowDom = true;
|
|
1151
|
+
b.slotRelocation = true;
|
|
1152
|
+
b.asyncLoading = true;
|
|
1153
|
+
b.svg = true;
|
|
1154
|
+
b.updatable = true;
|
|
1155
|
+
b.vdomAttribute = true;
|
|
1156
|
+
b.vdomClass = true;
|
|
1157
|
+
b.vdomFunctional = true;
|
|
1158
|
+
b.vdomKey = true;
|
|
1159
|
+
b.vdomPropOrAttr = true;
|
|
1160
|
+
b.vdomRef = true;
|
|
1161
|
+
b.vdomListener = true;
|
|
1162
|
+
b.vdomStyle = true;
|
|
1163
|
+
b.vdomText = true;
|
|
1164
|
+
b.vdomXlink = true;
|
|
1165
|
+
b.allRenderFn = false;
|
|
1166
|
+
b.devTools = false;
|
|
1167
|
+
b.hydrateClientSide = false;
|
|
1168
|
+
b.hydrateServerSide = false;
|
|
1169
|
+
b.cssAnnotations = false;
|
|
1170
|
+
b.style = false;
|
|
1171
|
+
b.hydratedAttribute = false;
|
|
1172
|
+
b.hydratedClass = true;
|
|
1173
|
+
b.invisiblePrehydration = true;
|
|
1174
|
+
b.staticHydrationStyles = false;
|
|
1175
|
+
b.lightDomPatches = false;
|
|
1176
|
+
b.slotChildNodes = false;
|
|
1177
|
+
b.slotCloneNode = false;
|
|
1178
|
+
b.slotDomMutations = false;
|
|
1179
|
+
b.slotTextContent = false;
|
|
1180
|
+
b.hotModuleReplacement = false;
|
|
1181
|
+
}
|
|
1182
|
+
//#endregion
|
|
1183
|
+
//#region src/testing/spec-page.ts
|
|
1184
|
+
/**
|
|
1185
|
+
* Generates a random number for use in generating a bundle id
|
|
1186
|
+
* @returns a random number between 100000 and 999999
|
|
1187
|
+
*/
|
|
1188
|
+
const generateRandBundleId = () => Math.round(Math.random() * 899999) + 1e5;
|
|
1189
|
+
/**
|
|
1190
|
+
* Creates a new spec page for unit testing
|
|
1191
|
+
* @param opts the options to apply to the spec page that influence its configuration and operation
|
|
1192
|
+
* @returns the created spec page
|
|
1193
|
+
*/
|
|
1194
|
+
async function newSpecPage(opts) {
|
|
1195
|
+
if (opts == null) throw new Error(`NewSpecPageOptions required`);
|
|
1196
|
+
resetPlatform(opts.platform ?? {});
|
|
1197
|
+
resetBuildConditionals(BUILD);
|
|
1198
|
+
if (Array.isArray(opts.components)) registerComponents(opts.components);
|
|
1199
|
+
if (opts.hydrateClientSide) opts.includeAnnotations = true;
|
|
1200
|
+
if (opts.hydrateServerSide) opts.includeAnnotations = true;
|
|
1201
|
+
else opts.includeAnnotations = !!opts.includeAnnotations;
|
|
1202
|
+
BUILD.cssAnnotations = opts.includeAnnotations;
|
|
1203
|
+
const cmpTags = /* @__PURE__ */ new Set();
|
|
1204
|
+
win["__stencil_spec_options"] = opts;
|
|
1205
|
+
const doc = win.document;
|
|
1206
|
+
const page = {
|
|
1207
|
+
win,
|
|
1208
|
+
doc,
|
|
1209
|
+
body: doc.body,
|
|
1210
|
+
build: BUILD,
|
|
1211
|
+
styles,
|
|
1212
|
+
setContent: (html) => {
|
|
1213
|
+
doc.body.innerHTML = html;
|
|
1214
|
+
return flushAll();
|
|
1215
|
+
},
|
|
1216
|
+
waitForChanges: flushAll,
|
|
1217
|
+
flushLoadModule,
|
|
1218
|
+
flushQueue
|
|
1219
|
+
};
|
|
1220
|
+
const lazyBundles = opts.components.map((Cstr) => {
|
|
1221
|
+
/**
|
|
1222
|
+
* just pass through functional components that don't have styles nor any other metadata
|
|
1223
|
+
*/
|
|
1224
|
+
if (Cstr.COMPILER_META == null) return formatLazyBundleRuntimeMeta(`fc.${generateRandBundleId()}`, []);
|
|
1225
|
+
cmpTags.add(Cstr.COMPILER_META.tagName);
|
|
1226
|
+
Cstr.isProxied = false;
|
|
1227
|
+
proxyComponentLifeCycles(Cstr);
|
|
1228
|
+
const bundleId = `${Cstr.COMPILER_META.tagName}.${generateRandBundleId()}`;
|
|
1229
|
+
const stylesMeta = Cstr.COMPILER_META.styles;
|
|
1230
|
+
if (Array.isArray(stylesMeta)) {
|
|
1231
|
+
if (stylesMeta.length > 1) {
|
|
1232
|
+
const styleModes = {};
|
|
1233
|
+
stylesMeta.forEach((style) => {
|
|
1234
|
+
styleModes[style.modeName] = style.styleStr;
|
|
1235
|
+
});
|
|
1236
|
+
Cstr.style = styleModes;
|
|
1237
|
+
} else if (stylesMeta.length === 1) Cstr.style = stylesMeta[0].styleStr;
|
|
1238
|
+
}
|
|
1239
|
+
registerModule(bundleId, Cstr);
|
|
1240
|
+
return formatLazyBundleRuntimeMeta(bundleId, [Cstr.COMPILER_META]);
|
|
1241
|
+
});
|
|
1242
|
+
const cmpBuild = getBuildFeatures(opts.components.filter((Cstr) => Cstr.COMPILER_META != null).map((Cstr) => Cstr.COMPILER_META));
|
|
1243
|
+
if (opts.strictBuild) Object.assign(BUILD, cmpBuild);
|
|
1244
|
+
else Object.keys(cmpBuild).forEach((key) => {
|
|
1245
|
+
if (cmpBuild[key] === true) BUILD[key] = true;
|
|
1246
|
+
});
|
|
1247
|
+
BUILD.asyncLoading = true;
|
|
1248
|
+
if (opts.hydrateClientSide) {
|
|
1249
|
+
BUILD.hydrateClientSide = true;
|
|
1250
|
+
BUILD.hydrateServerSide = false;
|
|
1251
|
+
} else if (opts.hydrateServerSide) {
|
|
1252
|
+
BUILD.hydrateServerSide = true;
|
|
1253
|
+
BUILD.hydrateClientSide = false;
|
|
1254
|
+
}
|
|
1255
|
+
BUILD.slotCloneNode = false;
|
|
1256
|
+
if (opts.buildFlags) Object.assign(BUILD, opts.buildFlags);
|
|
1257
|
+
if (typeof opts.url === "string") page.win.location.href = opts.url;
|
|
1258
|
+
if (typeof opts.direction === "string") page.doc.documentElement.setAttribute("dir", opts.direction);
|
|
1259
|
+
if (typeof opts.language === "string") page.doc.documentElement.setAttribute("lang", opts.language);
|
|
1260
|
+
if (typeof opts.cookie === "string") try {
|
|
1261
|
+
page.doc.cookie = opts.cookie;
|
|
1262
|
+
} catch {}
|
|
1263
|
+
if (typeof opts.referrer === "string") try {
|
|
1264
|
+
page.doc.referrer = opts.referrer;
|
|
1265
|
+
} catch {}
|
|
1266
|
+
if (typeof opts.userAgent === "string") try {
|
|
1267
|
+
page.win.navigator.userAgent = opts.userAgent;
|
|
1268
|
+
} catch {}
|
|
1269
|
+
if (opts.hydrateServerSide && opts.serializeShadowRoot === "scoped") {
|
|
1270
|
+
for (const [, cmps] of lazyBundles) for (const cmp of cmps) if (cmp[0] & CMP_FLAGS.shadowDomEncapsulation) cmp[0] |= CMP_FLAGS.shadowNeedsScopedCss;
|
|
1271
|
+
}
|
|
1272
|
+
bootstrapLazy(lazyBundles);
|
|
1273
|
+
if (typeof opts.template === "function") renderVdom({
|
|
1274
|
+
$ancestorComponent$: void 0,
|
|
1275
|
+
$flags$: 0,
|
|
1276
|
+
$modeName$: void 0,
|
|
1277
|
+
$cmpMeta$: {
|
|
1278
|
+
$flags$: 0,
|
|
1279
|
+
$tagName$: "body"
|
|
1280
|
+
},
|
|
1281
|
+
$hostElement$: page.body
|
|
1282
|
+
}, opts.template());
|
|
1283
|
+
else if (typeof opts.html === "string") page.body.innerHTML = opts.html;
|
|
1284
|
+
if (opts.flushQueue !== false) await page.waitForChanges();
|
|
1285
|
+
let rootComponent = null;
|
|
1286
|
+
Object.defineProperty(page, "root", { get() {
|
|
1287
|
+
if (rootComponent == null) rootComponent = findRootComponent(cmpTags, page.body);
|
|
1288
|
+
if (rootComponent != null) return rootComponent;
|
|
1289
|
+
const firstElementChild = page.body.firstElementChild;
|
|
1290
|
+
if (firstElementChild != null) return firstElementChild;
|
|
1291
|
+
return null;
|
|
1292
|
+
} });
|
|
1293
|
+
Object.defineProperty(page, "rootInstance", { get() {
|
|
1294
|
+
const hostRef = getHostRef(page.root);
|
|
1295
|
+
if (hostRef != null) return hostRef.$lazyInstance$;
|
|
1296
|
+
return null;
|
|
1297
|
+
} });
|
|
1298
|
+
if (opts.hydrateServerSide) insertVdomAnnotations(doc, []);
|
|
1299
|
+
if (opts.autoApplyChanges) {
|
|
1300
|
+
startAutoApplyChanges();
|
|
1301
|
+
page.waitForChanges = () => {
|
|
1302
|
+
console.error("waitForChanges() cannot be used manually if the \"startAutoApplyChanges\" option is enabled");
|
|
1303
|
+
return Promise.resolve();
|
|
1304
|
+
};
|
|
1305
|
+
}
|
|
1306
|
+
return page;
|
|
1307
|
+
}
|
|
1308
|
+
/**
|
|
1309
|
+
* A helper method that proxies Stencil lifecycle methods by mutating the provided component class
|
|
1310
|
+
* @param Cstr the component class whose lifecycle methods will be proxied
|
|
1311
|
+
*/
|
|
1312
|
+
function proxyComponentLifeCycles(Cstr) {
|
|
1313
|
+
if (typeof Cstr.prototype?.__componentWillLoad === "function") {
|
|
1314
|
+
Cstr.prototype.componentWillLoad = Cstr.prototype.__componentWillLoad;
|
|
1315
|
+
Cstr.prototype.__componentWillLoad = null;
|
|
1316
|
+
}
|
|
1317
|
+
if (typeof Cstr.prototype?.__componentWillUpdate === "function") {
|
|
1318
|
+
Cstr.prototype.componentWillUpdate = Cstr.prototype.__componentWillUpdate;
|
|
1319
|
+
Cstr.prototype.__componentWillUpdate = null;
|
|
1320
|
+
}
|
|
1321
|
+
if (typeof Cstr.prototype?.__componentWillRender === "function") {
|
|
1322
|
+
Cstr.prototype.componentWillRender = Cstr.prototype.__componentWillRender;
|
|
1323
|
+
Cstr.prototype.__componentWillRender = null;
|
|
1324
|
+
}
|
|
1325
|
+
if (typeof Cstr.prototype?.componentWillLoad === "function") {
|
|
1326
|
+
Cstr.prototype.__componentWillLoad = Cstr.prototype.componentWillLoad;
|
|
1327
|
+
/** @returns the result from the original componentWillLoad */
|
|
1328
|
+
Cstr.prototype.componentWillLoad = function() {
|
|
1329
|
+
const result = this.__componentWillLoad();
|
|
1330
|
+
if (result != null && typeof result.then === "function") writeTask(() => result);
|
|
1331
|
+
else writeTask(() => Promise.resolve());
|
|
1332
|
+
return result;
|
|
1333
|
+
};
|
|
1334
|
+
}
|
|
1335
|
+
if (typeof Cstr.prototype?.componentWillUpdate === "function") {
|
|
1336
|
+
Cstr.prototype.__componentWillUpdate = Cstr.prototype.componentWillUpdate;
|
|
1337
|
+
/** @returns the result from the original componentWillUpdate */
|
|
1338
|
+
Cstr.prototype.componentWillUpdate = function() {
|
|
1339
|
+
const result = this.__componentWillUpdate();
|
|
1340
|
+
if (result != null && typeof result.then === "function") writeTask(() => result);
|
|
1341
|
+
else writeTask(() => Promise.resolve());
|
|
1342
|
+
return result;
|
|
1343
|
+
};
|
|
1344
|
+
}
|
|
1345
|
+
if (typeof Cstr.prototype?.componentWillRender === "function") {
|
|
1346
|
+
Cstr.prototype.__componentWillRender = Cstr.prototype.componentWillRender;
|
|
1347
|
+
/** @returns the result from the original componentWillRender */
|
|
1348
|
+
Cstr.prototype.componentWillRender = function() {
|
|
1349
|
+
const result = this.__componentWillRender();
|
|
1350
|
+
if (result != null && typeof result.then === "function") writeTask(() => result);
|
|
1351
|
+
else writeTask(() => Promise.resolve());
|
|
1352
|
+
return result;
|
|
1353
|
+
};
|
|
1354
|
+
}
|
|
1355
|
+
}
|
|
1356
|
+
/**
|
|
1357
|
+
* Return the first Element whose {@link Element#nodeName} property matches a tag found in the provided `cmpTags`
|
|
1358
|
+
* argument.
|
|
1359
|
+
*
|
|
1360
|
+
* If the `nodeName` property on the element matches any of the names found in the provided `cmpTags` argument, that
|
|
1361
|
+
* element is returned. If no match is found on the current element, the children will be inspected in a depth-first
|
|
1362
|
+
* search manner. This process continues until either:
|
|
1363
|
+
* - an element is found (and execution ends)
|
|
1364
|
+
* - no element is found after an exhaustive search
|
|
1365
|
+
*
|
|
1366
|
+
* @param cmpTags component tag names to use in the match criteria
|
|
1367
|
+
* @param node the node whose children are to be inspected
|
|
1368
|
+
* @returns An element whose name matches one of the strings in the provided `cmpTags`. If no match is found, `null` is
|
|
1369
|
+
* returned
|
|
1370
|
+
*/
|
|
1371
|
+
function findRootComponent(cmpTags, node) {
|
|
1372
|
+
if (node != null) {
|
|
1373
|
+
const children = node.children;
|
|
1374
|
+
const childrenLength = children.length;
|
|
1375
|
+
for (let i = 0; i < childrenLength; i++) {
|
|
1376
|
+
const elm = children[i];
|
|
1377
|
+
if (cmpTags.has(elm.nodeName.toLowerCase())) return elm;
|
|
1378
|
+
}
|
|
1379
|
+
for (let i = 0; i < childrenLength; i++) {
|
|
1380
|
+
const r = findRootComponent(cmpTags, children[i]);
|
|
1381
|
+
if (r != null) return r;
|
|
1382
|
+
}
|
|
1383
|
+
}
|
|
1384
|
+
return null;
|
|
1385
|
+
}
|
|
1386
|
+
//#endregion
|
|
1387
|
+
//#region src/testing/testing-utils.ts
|
|
1388
|
+
/**
|
|
1389
|
+
* Shuffle an array using Fisher-Yates algorithm
|
|
1390
|
+
* http://stackoverflow.com/questions/2450954/how-to-randomize-shuffle-a-javascript-array
|
|
1391
|
+
*
|
|
1392
|
+
* @param array - the array to shuffle
|
|
1393
|
+
* @returns the shuffled array
|
|
1394
|
+
*/
|
|
1395
|
+
function shuffleArray(array) {
|
|
1396
|
+
let currentIndex = array.length;
|
|
1397
|
+
let temporaryValue;
|
|
1398
|
+
let randomIndex;
|
|
1399
|
+
while (0 !== currentIndex) {
|
|
1400
|
+
randomIndex = Math.floor(Math.random() * currentIndex);
|
|
1401
|
+
currentIndex -= 1;
|
|
1402
|
+
temporaryValue = array[currentIndex];
|
|
1403
|
+
array[currentIndex] = array[randomIndex];
|
|
1404
|
+
array[randomIndex] = temporaryValue;
|
|
1405
|
+
}
|
|
1406
|
+
return array;
|
|
1407
|
+
}
|
|
1408
|
+
/**
|
|
1409
|
+
* Utility for silencing `console` functions in tests.
|
|
1410
|
+
*
|
|
1411
|
+
* When this function is first called it grabs a reference to the `log`,
|
|
1412
|
+
* `error`, and `warn` functions on `console` and then returns a per-test setup
|
|
1413
|
+
* function which sets up a fresh set of mocks (via `jest.fn()`) and then
|
|
1414
|
+
* assigns them to each of these functions. This setup function will return a
|
|
1415
|
+
* reference to each of the three mock functions so tests can make assertions
|
|
1416
|
+
* about their calls and so on.
|
|
1417
|
+
*
|
|
1418
|
+
* Because references to the original `.log`, `.error`, and `.warn` functions
|
|
1419
|
+
* exist in closure within the function, it can use an `afterAll` call to clean
|
|
1420
|
+
* up after itself and ensure that the original implementations are restored
|
|
1421
|
+
* after the test suite finishes.
|
|
1422
|
+
*
|
|
1423
|
+
* An example of using this to silence log statements in a single test could look
|
|
1424
|
+
* like this:
|
|
1425
|
+
*
|
|
1426
|
+
* ```ts
|
|
1427
|
+
* describe("my-test-suite", () => {
|
|
1428
|
+
* const { setupConsoleMocks, teardownConsoleMocks } = setupConsoleMocker()
|
|
1429
|
+
*
|
|
1430
|
+
* it("should log a message", () => {
|
|
1431
|
+
* const { logMock } = setupConsoleMocks();
|
|
1432
|
+
* myFunctionWhichLogs(foo, bar);
|
|
1433
|
+
* expect(logMock).toBeCalledWith('my log message');
|
|
1434
|
+
* teardownConsoleMocks();
|
|
1435
|
+
* })
|
|
1436
|
+
* })
|
|
1437
|
+
* ```
|
|
1438
|
+
*
|
|
1439
|
+
* @returns a per-test mock setup function
|
|
1440
|
+
*/
|
|
1441
|
+
function setupConsoleMocker() {
|
|
1442
|
+
const originalLog = console.log;
|
|
1443
|
+
const originalWarn = console.warn;
|
|
1444
|
+
const originalError = console.error;
|
|
1445
|
+
/**
|
|
1446
|
+
* Function to tear down console mocks where you're done with them! Ideally
|
|
1447
|
+
* this would be called right after the assertion you're looking to make in
|
|
1448
|
+
* your test.
|
|
1449
|
+
*/
|
|
1450
|
+
function teardownConsoleMocks() {
|
|
1451
|
+
console.log = originalLog;
|
|
1452
|
+
console.warn = originalWarn;
|
|
1453
|
+
console.error = originalError;
|
|
1454
|
+
}
|
|
1455
|
+
afterAll(() => {
|
|
1456
|
+
teardownConsoleMocks();
|
|
1457
|
+
});
|
|
1458
|
+
function setupConsoleMocks() {
|
|
1459
|
+
const logMock = vi.fn();
|
|
1460
|
+
const warnMock = vi.fn();
|
|
1461
|
+
const errorMock = vi.fn();
|
|
1462
|
+
console.log = logMock;
|
|
1463
|
+
console.warn = warnMock;
|
|
1464
|
+
console.error = errorMock;
|
|
1465
|
+
return {
|
|
1466
|
+
logMock,
|
|
1467
|
+
warnMock,
|
|
1468
|
+
errorMock
|
|
1469
|
+
};
|
|
1470
|
+
}
|
|
1471
|
+
return {
|
|
1472
|
+
setupConsoleMocks,
|
|
1473
|
+
teardownConsoleMocks
|
|
1474
|
+
};
|
|
1475
|
+
}
|
|
1476
|
+
//#endregion
|
|
1477
|
+
export { Build, Env, Fragment, Host, Mixin, createEvent, createTestCompiler, createTestingSystem, forceUpdate, getAssetPath, getElement, getHostRef, getMode, getRenderingRef, h, mockBuildCtx, mockCompilerCtx, mockCompilerSystem, mockComponentMeta, mockConfig, mockDocument, mockLoadConfigInit, mockLogger, mockModule, mockValidatedConfig, mockWindow, newSpecPage, prepareTestCompiler, readTask, registerHost, registerInstance, setAssetPath, setErrorHandler, setMode, setupConsoleMocker, shuffleArray, writeTask };
|