diff --git a/.changeset/breezy-pets-dream.md b/.changeset/breezy-pets-dream.md new file mode 100644 index 000000000000..45eed91cf905 --- /dev/null +++ b/.changeset/breezy-pets-dream.md @@ -0,0 +1,5 @@ +--- +"@astrojs/vercel": patch +--- + +Prevents infinite redirects when Astro `trailingSlash` configuration is set to `"always"` and "vercel.json" `trailingSlash` configuration is set to `true` diff --git a/.changeset/shaggy-spies-sit.md b/.changeset/shaggy-spies-sit.md deleted file mode 100644 index 70776cb1e4ea..000000000000 --- a/.changeset/shaggy-spies-sit.md +++ /dev/null @@ -1,41 +0,0 @@ ---- -"@astrojs/markdoc": minor ---- - -Adds support for using a custom tag (component) for optimized images - -Starting from this version, when a tag called `image` is used, its `src` attribute will automatically be resolved if it's a local image. Astro will pass the result `ImageMetadata` object to the underlying component as the `src` prop. For non-local images (i.e. images using URLs or absolute paths), Astro will continue to pass the `src` as a string. - -```ts -// markdoc.config.mjs -import { component, defineMarkdocConfig, nodes } from '@astrojs/markdoc/config'; - -export default defineMarkdocConfig({ - tags: { - image: { - attributes: nodes.image.attributes, - render: component('./src/components/MarkdocImage.astro'), - }, - }, -}); -``` -```astro ---- -// src/components/MarkdocImage.astro -import { Image } from "astro:assets"; - -interface Props { - src: ImageMetadata | string; - alt: string; - width: number; - height: number; -} - -const { src, alt, width, height } = Astro.props; ---- - - -``` -```mdoc -{% image src="./astro-logo.png" alt="Astro Logo" width="100" height="100" %} -`````` diff --git a/.changeset/sweet-chicken-sneeze.md b/.changeset/sweet-chicken-sneeze.md new file mode 100644 index 000000000000..9f145d3265db --- /dev/null +++ b/.changeset/sweet-chicken-sneeze.md @@ -0,0 +1,5 @@ +--- +"astro": patch +--- + +Clarifies error messages in endpoint routing. diff --git a/.changeset/tasty-actors-dance.md b/.changeset/tasty-actors-dance.md deleted file mode 100644 index e9ade9965192..000000000000 --- a/.changeset/tasty-actors-dance.md +++ /dev/null @@ -1,5 +0,0 @@ ---- -"astro": patch ---- - -Fixes a regression in the `astro:i18n` module, where the functions `getAbsoluteLocaleUrl` and `getAbsoluteLocaleUrlList` returned a URL with double slash with a certain combination of options. diff --git a/.changeset/thin-kangaroos-exist.md b/.changeset/thin-kangaroos-exist.md new file mode 100644 index 000000000000..5563e5638fbc --- /dev/null +++ b/.changeset/thin-kangaroos-exist.md @@ -0,0 +1,5 @@ +--- +"astro": patch +--- + +Fixes an issue where ReadableStream wasn't canceled in dev mode diff --git a/.changeset/tough-shirts-allow.md b/.changeset/tough-shirts-allow.md deleted file mode 100644 index a429d3587be7..000000000000 --- a/.changeset/tough-shirts-allow.md +++ /dev/null @@ -1,5 +0,0 @@ ---- -"astro": patch ---- - -Fixes an issue where custom client directives added by integrations broke builds with a custom root. diff --git a/.changeset/wild-singers-turn.md b/.changeset/wild-singers-turn.md deleted file mode 100644 index 0b1de3bc22f3..000000000000 --- a/.changeset/wild-singers-turn.md +++ /dev/null @@ -1,5 +0,0 @@ ---- -"astro": patch ---- - -Increases compatibility with standard browser behavior by changing where view transitions occur on browser back navigation. diff --git a/examples/basics/package.json b/examples/basics/package.json index f17344f80d4c..b4b18b6e3806 100644 --- a/examples/basics/package.json +++ b/examples/basics/package.json @@ -11,6 +11,6 @@ "astro": "astro" }, "dependencies": { - "astro": "^4.3.5" + "astro": "^4.3.6" } } diff --git a/examples/blog/package.json b/examples/blog/package.json index 1cec634a9e12..fc0f290a5eb9 100644 --- a/examples/blog/package.json +++ b/examples/blog/package.json @@ -14,6 +14,6 @@ "@astrojs/mdx": "^2.1.1", "@astrojs/rss": "^4.0.5", "@astrojs/sitemap": "^3.0.5", - "astro": "^4.3.5" + "astro": "^4.3.6" } } diff --git a/examples/component/package.json b/examples/component/package.json index 18c6a51619f1..ccfeac17d7b6 100644 --- a/examples/component/package.json +++ b/examples/component/package.json @@ -15,7 +15,7 @@ ], "scripts": {}, "devDependencies": { - "astro": "^4.3.5" + "astro": "^4.3.6" }, "peerDependencies": { "astro": "^4.0.0" diff --git a/examples/framework-alpine/package.json b/examples/framework-alpine/package.json index dbcbebff70d8..4d77e838a322 100644 --- a/examples/framework-alpine/package.json +++ b/examples/framework-alpine/package.json @@ -14,6 +14,6 @@ "@astrojs/alpinejs": "^0.4.0", "@types/alpinejs": "^3.13.5", "alpinejs": "^3.13.3", - "astro": "^4.3.5" + "astro": "^4.3.6" } } diff --git a/examples/framework-lit/package.json b/examples/framework-lit/package.json index f3d5cdb2dfcb..4edbd3a41b9e 100644 --- a/examples/framework-lit/package.json +++ b/examples/framework-lit/package.json @@ -13,7 +13,7 @@ "dependencies": { "@astrojs/lit": "^4.0.1", "@webcomponents/template-shadowroot": "^0.2.1", - "astro": "^4.3.5", + "astro": "^4.3.6", "lit": "^3.1.2" } } diff --git a/examples/framework-multiple/package.json b/examples/framework-multiple/package.json index 76a70cb8e8de..86ec4d821424 100644 --- a/examples/framework-multiple/package.json +++ b/examples/framework-multiple/package.json @@ -16,7 +16,7 @@ "@astrojs/solid-js": "^4.0.1", "@astrojs/svelte": "^5.0.3", "@astrojs/vue": "^4.0.8", - "astro": "^4.3.5", + "astro": "^4.3.6", "preact": "^10.19.2", "react": "^18.2.0", "react-dom": "^18.2.0", diff --git a/examples/framework-preact/package.json b/examples/framework-preact/package.json index 37d76e913b17..c3f4cec69c99 100644 --- a/examples/framework-preact/package.json +++ b/examples/framework-preact/package.json @@ -13,7 +13,7 @@ "dependencies": { "@astrojs/preact": "^3.1.0", "@preact/signals": "^1.2.1", - "astro": "^4.3.5", + "astro": "^4.3.6", "preact": "^10.19.2" } } diff --git a/examples/framework-react/package.json b/examples/framework-react/package.json index fbd8c5f6f237..0db74ec57c52 100644 --- a/examples/framework-react/package.json +++ b/examples/framework-react/package.json @@ -14,7 +14,7 @@ "@astrojs/react": "^3.0.10", "@types/react": "^18.2.37", "@types/react-dom": "^18.2.15", - "astro": "^4.3.5", + "astro": "^4.3.6", "react": "^18.2.0", "react-dom": "^18.2.0" } diff --git a/examples/framework-solid/package.json b/examples/framework-solid/package.json index 9482261c4ff1..30869ca0bd9f 100644 --- a/examples/framework-solid/package.json +++ b/examples/framework-solid/package.json @@ -12,7 +12,7 @@ }, "dependencies": { "@astrojs/solid-js": "^4.0.1", - "astro": "^4.3.5", + "astro": "^4.3.6", "solid-js": "^1.8.5" } } diff --git a/examples/framework-svelte/package.json b/examples/framework-svelte/package.json index 00441b6df64c..83d34fe180c3 100644 --- a/examples/framework-svelte/package.json +++ b/examples/framework-svelte/package.json @@ -12,7 +12,7 @@ }, "dependencies": { "@astrojs/svelte": "^5.0.3", - "astro": "^4.3.5", + "astro": "^4.3.6", "svelte": "^4.2.5" } } diff --git a/examples/framework-vue/package.json b/examples/framework-vue/package.json index ea36fbe8b69e..50840dc35197 100644 --- a/examples/framework-vue/package.json +++ b/examples/framework-vue/package.json @@ -12,7 +12,7 @@ }, "dependencies": { "@astrojs/vue": "^4.0.8", - "astro": "^4.3.5", + "astro": "^4.3.6", "vue": "^3.3.8" } } diff --git a/examples/hackernews/package.json b/examples/hackernews/package.json index 1f85935a4080..37c745c00ca3 100644 --- a/examples/hackernews/package.json +++ b/examples/hackernews/package.json @@ -12,6 +12,6 @@ }, "dependencies": { "@astrojs/node": "^8.2.0", - "astro": "^4.3.5" + "astro": "^4.3.6" } } diff --git a/examples/integration/package.json b/examples/integration/package.json index dc71b4923b77..4b75f184a3e5 100644 --- a/examples/integration/package.json +++ b/examples/integration/package.json @@ -15,7 +15,7 @@ ], "scripts": {}, "devDependencies": { - "astro": "^4.3.5" + "astro": "^4.3.6" }, "peerDependencies": { "astro": "^4.0.0" diff --git a/examples/middleware/package.json b/examples/middleware/package.json index 66add14a059f..57dc37085fdd 100644 --- a/examples/middleware/package.json +++ b/examples/middleware/package.json @@ -13,7 +13,7 @@ }, "dependencies": { "@astrojs/node": "^8.2.0", - "astro": "^4.3.5", + "astro": "^4.3.6", "html-minifier": "^4.0.0" }, "devDependencies": { diff --git a/examples/minimal/package.json b/examples/minimal/package.json index 4eb116742334..3db6704f8c01 100644 --- a/examples/minimal/package.json +++ b/examples/minimal/package.json @@ -11,6 +11,6 @@ "astro": "astro" }, "dependencies": { - "astro": "^4.3.5" + "astro": "^4.3.6" } } diff --git a/examples/non-html-pages/package.json b/examples/non-html-pages/package.json index 5ec95f2bc428..5ef026e2b073 100644 --- a/examples/non-html-pages/package.json +++ b/examples/non-html-pages/package.json @@ -11,6 +11,6 @@ "astro": "astro" }, "dependencies": { - "astro": "^4.3.5" + "astro": "^4.3.6" } } diff --git a/examples/portfolio/package.json b/examples/portfolio/package.json index 3087fa54520a..b4bc69830d78 100644 --- a/examples/portfolio/package.json +++ b/examples/portfolio/package.json @@ -11,6 +11,6 @@ "astro": "astro" }, "dependencies": { - "astro": "^4.3.5" + "astro": "^4.3.6" } } diff --git a/examples/ssr/package.json b/examples/ssr/package.json index ce73a19f1eb3..7f7c327095e8 100644 --- a/examples/ssr/package.json +++ b/examples/ssr/package.json @@ -14,7 +14,7 @@ "dependencies": { "@astrojs/node": "^8.2.0", "@astrojs/svelte": "^5.0.3", - "astro": "^4.3.5", + "astro": "^4.3.6", "svelte": "^4.2.5" } } diff --git a/examples/starlog/package.json b/examples/starlog/package.json index 813cb20bd880..85ed1cabddbd 100644 --- a/examples/starlog/package.json +++ b/examples/starlog/package.json @@ -10,7 +10,7 @@ "astro": "astro" }, "dependencies": { - "astro": "^4.3.5", + "astro": "^4.3.6", "sass": "^1.69.5", "sharp": "^0.32.6" } diff --git a/examples/view-transitions/package.json b/examples/view-transitions/package.json index 235cf0ef7987..2456cb16880d 100644 --- a/examples/view-transitions/package.json +++ b/examples/view-transitions/package.json @@ -12,6 +12,6 @@ "devDependencies": { "@astrojs/tailwind": "^5.1.0", "@astrojs/node": "^8.2.0", - "astro": "^4.3.5" + "astro": "^4.3.6" } } diff --git a/examples/with-markdoc/package.json b/examples/with-markdoc/package.json index 0235a61c1964..59ab5c4159a3 100644 --- a/examples/with-markdoc/package.json +++ b/examples/with-markdoc/package.json @@ -11,7 +11,7 @@ "astro": "astro" }, "dependencies": { - "@astrojs/markdoc": "^0.8.3", - "astro": "^4.3.5" + "@astrojs/markdoc": "^0.9.0", + "astro": "^4.3.6" } } diff --git a/examples/with-markdown-plugins/package.json b/examples/with-markdown-plugins/package.json index bc61cd91952a..86d96aaebcfb 100644 --- a/examples/with-markdown-plugins/package.json +++ b/examples/with-markdown-plugins/package.json @@ -12,7 +12,7 @@ }, "dependencies": { "@astrojs/markdown-remark": "^4.2.1", - "astro": "^4.3.5", + "astro": "^4.3.6", "hast-util-select": "^6.0.2", "rehype-autolink-headings": "^7.1.0", "rehype-slug": "^6.0.0", diff --git a/examples/with-markdown-shiki/package.json b/examples/with-markdown-shiki/package.json index b5f2d44ea293..a18e23f4548e 100644 --- a/examples/with-markdown-shiki/package.json +++ b/examples/with-markdown-shiki/package.json @@ -11,6 +11,6 @@ "astro": "astro" }, "dependencies": { - "astro": "^4.3.5" + "astro": "^4.3.6" } } diff --git a/examples/with-mdx/package.json b/examples/with-mdx/package.json index 07451fe975e8..fcd27a6e64d0 100644 --- a/examples/with-mdx/package.json +++ b/examples/with-mdx/package.json @@ -13,7 +13,7 @@ "dependencies": { "@astrojs/mdx": "^2.1.1", "@astrojs/preact": "^3.1.0", - "astro": "^4.3.5", + "astro": "^4.3.6", "preact": "^10.19.2" } } diff --git a/examples/with-nanostores/package.json b/examples/with-nanostores/package.json index f58b9a851dfb..636d588fefc5 100644 --- a/examples/with-nanostores/package.json +++ b/examples/with-nanostores/package.json @@ -13,7 +13,7 @@ "dependencies": { "@astrojs/preact": "^3.1.0", "@nanostores/preact": "^0.5.0", - "astro": "^4.3.5", + "astro": "^4.3.6", "nanostores": "^0.9.5", "preact": "^10.19.2" } diff --git a/examples/with-tailwindcss/package.json b/examples/with-tailwindcss/package.json index 424651f9334a..f09c25a322b8 100644 --- a/examples/with-tailwindcss/package.json +++ b/examples/with-tailwindcss/package.json @@ -14,7 +14,7 @@ "@astrojs/mdx": "^2.1.1", "@astrojs/tailwind": "^5.1.0", "@types/canvas-confetti": "^1.6.3", - "astro": "^4.3.5", + "astro": "^4.3.6", "autoprefixer": "^10.4.15", "canvas-confetti": "^1.9.1", "postcss": "^8.4.28", diff --git a/examples/with-vitest/package.json b/examples/with-vitest/package.json index 67cd49807f99..472cf45b2d82 100644 --- a/examples/with-vitest/package.json +++ b/examples/with-vitest/package.json @@ -12,7 +12,7 @@ "test": "vitest" }, "dependencies": { - "astro": "^4.3.5", + "astro": "^4.3.6", "vitest": "^1.2.1" } } diff --git a/packages/astro/CHANGELOG.md b/packages/astro/CHANGELOG.md index 26f68e4fce6b..7d47dbaf9376 100644 --- a/packages/astro/CHANGELOG.md +++ b/packages/astro/CHANGELOG.md @@ -1,5 +1,17 @@ # astro +## 4.3.6 + +### Patch Changes + +- [#10063](https://github.com/withastro/astro/pull/10063) [`dac759798c111494e76affd2c2504d63944871fe`](https://github.com/withastro/astro/commit/dac759798c111494e76affd2c2504d63944871fe) Thanks [@marwan-mohamed12](https://github.com/marwan-mohamed12)! - Moves `shikiji-core` from `devDependencies` to `dependencies` to prevent type errors + +- [#10067](https://github.com/withastro/astro/pull/10067) [`989ea63bb2a5a670021541198aa70b8dc7c4bd2f`](https://github.com/withastro/astro/commit/989ea63bb2a5a670021541198aa70b8dc7c4bd2f) Thanks [@ematipico](https://github.com/ematipico)! - Fixes a regression in the `astro:i18n` module, where the functions `getAbsoluteLocaleUrl` and `getAbsoluteLocaleUrlList` returned a URL with double slash with a certain combination of options. + +- [#10060](https://github.com/withastro/astro/pull/10060) [`1810309e65c596266355c3b7bb36cdac70f3305e`](https://github.com/withastro/astro/commit/1810309e65c596266355c3b7bb36cdac70f3305e) Thanks [@lilnasy](https://github.com/lilnasy)! - Fixes an issue where custom client directives added by integrations broke builds with a custom root. + +- [#9991](https://github.com/withastro/astro/pull/9991) [`8fb67c81bb84530b39df4a1449c0862def0854af`](https://github.com/withastro/astro/commit/8fb67c81bb84530b39df4a1449c0862def0854af) Thanks [@ktym4a](https://github.com/ktym4a)! - Increases compatibility with standard browser behavior by changing where view transitions occur on browser back navigation. + ## 4.3.5 ### Patch Changes diff --git a/packages/astro/package.json b/packages/astro/package.json index 6ae5e1aab884..62058b42f588 100644 --- a/packages/astro/package.json +++ b/packages/astro/package.json @@ -1,6 +1,6 @@ { "name": "astro", - "version": "4.3.5", + "version": "4.3.6", "description": "Astro is a modern site builder with web best practices, performance, and DX front-of-mind.", "type": "module", "author": "withastro", @@ -107,10 +107,8 @@ "build:ci": "pnpm run prebuild && astro-scripts build \"src/**/*.{ts,js}\" && pnpm run postbuild", "dev": "astro-scripts dev --copy-wasm --prebuild \"src/runtime/server/astro-island.ts\" --prebuild \"src/runtime/client/{idle,load,media,only,visible}.ts\" \"src/**/*.{ts,js}\"", "postbuild": "astro-scripts copy \"src/**/*.astro\" && astro-scripts copy \"src/**/*.wasm\"", - "test:unit": "mocha --exit --timeout 30000 ./test/units/**/*.test.js", - "test:unit:match": "mocha --exit --timeout 30000 ./test/units/**/*.test.js -g --ignore **/*.nodetest.js", - "test": "pnpm run test:node && pnpm run test:unit && mocha --exit --timeout 30000 --ignore **/*.nodetest.js --ignore **/lit-element.test.js && mocha --timeout 30000 **/lit-element.test.js --ignore **/*.nodetest.js", - "test:match": "mocha --timeout 30000 -g", + "test": "pnpm run test:node && mocha ./test/*.test.js --exit --timeout 30000 --ignore ./test/lit-element.test.js && mocha ./test/lit-element.test.js --timeout 30000", + "test:match": "mocha ./test/*.test.js --timeout 30000 -g", "test:e2e": "playwright test", "test:e2e:match": "playwright test -g", "test:node": "astro-scripts test \"test/**/*.nodetest.js\"" @@ -169,7 +167,8 @@ "resolve": "^1.22.4", "semver": "^7.5.4", "server-destroy": "^1.0.1", - "shikiji": "^0.9.18", + "shikiji": "^0.9.19", + "shikiji-core": "^0.9.19", "string-width": "^7.0.0", "strip-ansi": "^7.1.0", "tsconfck": "^3.0.0", @@ -228,7 +227,6 @@ "remark-code-titles": "^0.1.2", "rollup": "^4.5.0", "sass": "^1.69.5", - "shikiji-core": "^0.9.18", "srcset-parse": "^1.1.0", "unified": "^11.0.4" }, diff --git a/packages/astro/src/runtime/server/endpoint.ts b/packages/astro/src/runtime/server/endpoint.ts index 49f00224e61d..9b5f3e40e0da 100644 --- a/packages/astro/src/runtime/server/endpoint.ts +++ b/packages/astro/src/runtime/server/endpoint.ts @@ -23,10 +23,10 @@ export async function renderEndpoint( )} requests are not available for a static site. Update your config to \`output: 'server'\` or \`output: 'hybrid'\` to enable.` ); } - if (typeof handler !== 'function') { + if (handler === undefined) { logger.warn( 'router', - `No API Route handler exists for the method "${method}" for the route ${url.pathname}.\n` + + `No API Route handler exists for the method "${method}" for the route "${url.pathname}".\n` + `Found handlers: ${Object.keys(mod) .map((exp) => JSON.stringify(exp)) .join(', ')}\n` + @@ -38,6 +38,15 @@ export async function renderEndpoint( // 404. Should be handled by 404.astro route if possible. return new Response(null, { status: 404 }); } + if (typeof handler !== 'function') { + logger.error( + 'router', + `The route "${ + url.pathname + }" exports a value for the method "${method}", but it is of the type ${typeof handler} instead of a function.` + ); + return new Response(null, { status: 500 }); + } const response = await handler.call(mod, context); // Endpoints explicitly returning 404 or 500 response status should diff --git a/packages/astro/src/vite-plugin-astro-server/response.ts b/packages/astro/src/vite-plugin-astro-server/response.ts index 75649a714482..54cf6ef3ab90 100644 --- a/packages/astro/src/vite-plugin-astro-server/response.ts +++ b/packages/astro/src/vite-plugin-astro-server/response.ts @@ -82,6 +82,12 @@ export async function writeWebResponse(res: http.ServerResponse, webResponse: Re res.write(body); } else { const reader = body.getReader(); + res.on('close', () => { + reader.cancel().catch((error: unknown) => { + // eslint-disable-next-line no-console + console.error('An unexpected error occurred in the middle of the stream.', error); + }); + }); while (true) { const { done, value } = await reader.read(); if (done) break; diff --git a/packages/astro/test/asset-url-base.test.js b/packages/astro/test/asset-url-base.nodetest.js similarity index 85% rename from packages/astro/test/asset-url-base.test.js rename to packages/astro/test/asset-url-base.nodetest.js index de63ef4b7446..93695e2e7b1d 100644 --- a/packages/astro/test/asset-url-base.test.js +++ b/packages/astro/test/asset-url-base.nodetest.js @@ -1,4 +1,5 @@ -import { expect } from 'chai'; +import assert from 'node:assert/strict'; +import { describe, before, it } from 'node:test'; import * as cheerio from 'cheerio'; import { loadFixture } from './test-utils.js'; @@ -22,7 +23,7 @@ describe('Asset URL resolution in build', () => { const html = await fixture.readFile('/index.html'); const $ = cheerio.load(html); const href = $('link[rel=stylesheet]').attr('href'); - expect(href.startsWith('/sub/path/')).to.equal(false); + assert.equal(href.startsWith('/sub/path/'), false); }); }); @@ -42,14 +43,14 @@ describe('Asset URL resolution in build', () => { const html = await fixture.readFile('/index.html'); const $ = cheerio.load(html); const href = $('link[rel=stylesheet]').attr('href'); - expect(href.startsWith('/sub/path/')).to.equal(false); + assert.equal(href.startsWith('/sub/path/'), false); }); it('does include the base subpath', async () => { const html = await fixture.readFile('/index.html'); const $ = cheerio.load(html); const href = $('link[rel=stylesheet]').attr('href'); - expect(href.startsWith('/another/base/')).to.equal(true); + assert.equal(href.startsWith('/another/base/'), true); }); }); }); diff --git a/packages/astro/test/astro-assets-prefix.test.js b/packages/astro/test/astro-assets-prefix.nodetest.js similarity index 80% rename from packages/astro/test/astro-assets-prefix.test.js rename to packages/astro/test/astro-assets-prefix.nodetest.js index 65613f03acee..de5aa84f4f28 100644 --- a/packages/astro/test/astro-assets-prefix.test.js +++ b/packages/astro/test/astro-assets-prefix.nodetest.js @@ -1,4 +1,5 @@ -import { expect } from 'chai'; +import assert from 'node:assert/strict'; +import { describe, before, it } from 'node:test'; import * as cheerio from 'cheerio'; import testAdapter from './test-adapter.js'; import { loadFixture } from './test-utils.js'; @@ -22,7 +23,7 @@ describe('Assets Prefix - Static', () => { const $ = cheerio.load(html); const stylesheets = $('link[rel="stylesheet"]'); stylesheets.each((i, el) => { - expect(el.attribs.href).to.match(assetsPrefixRegex); + assert.match(el.attribs.href, assetsPrefixRegex); }); }); @@ -30,22 +31,22 @@ describe('Assets Prefix - Static', () => { const html = await fixture.readFile('/index.html'); const $ = cheerio.load(html); const imgAsset = $('#image-asset'); - expect(imgAsset.attr('src')).to.match(assetsPrefixRegex); + assert.match(imgAsset.attr('src'), assetsPrefixRegex); }); it('react component astro-island should import from assetsPrefix', async () => { const html = await fixture.readFile('/index.html'); const $ = cheerio.load(html); const island = $('astro-island'); - expect(island.attr('component-url')).to.match(assetsPrefixRegex); - expect(island.attr('renderer-url')).to.match(assetsPrefixRegex); + assert.match(island.attr('component-url'), assetsPrefixRegex); + assert.match(island.attr('renderer-url'), assetsPrefixRegex); }); it('import.meta.env.ASSETS_PREFIX works', async () => { const html = await fixture.readFile('/index.html'); const $ = cheerio.load(html); const env = $('#assets-prefix-env'); - expect(env.text()).to.equal(assetsPrefix); + assert.equal(env.text(), assetsPrefix); }); it('markdown image src start with assetsPrefix', async () => { @@ -53,7 +54,7 @@ describe('Assets Prefix - Static', () => { const $ = cheerio.load(html); const imgAssets = $('img'); imgAssets.each((i, el) => { - expect(el.attribs.src).to.match(assetsPrefixRegex); + assert.match(el.attribs.src, assetsPrefixRegex); }); }); @@ -61,7 +62,7 @@ describe('Assets Prefix - Static', () => { const html = await fixture.readFile('/blog/index.html'); const $ = cheerio.load(html); const imgAsset = $('img'); - expect(imgAsset.attr('src')).to.match(assetsPrefixRegex); + assert.match(imgAsset.attr('src'), assetsPrefixRegex); }); }); @@ -83,7 +84,7 @@ describe('Assets Prefix - with path prefix', () => { const $ = cheerio.load(html); const stylesheets = $('link[rel="stylesheet"]'); stylesheets.each((i, el) => { - expect(el.attribs.href).to.match(/^\/starting-slash\/.*/); + assert.match(el.attribs.href, /^\/starting-slash\/.*/); }); }); }); @@ -104,44 +105,44 @@ describe('Assets Prefix, server', () => { it('all stylesheets should start with assetPrefix', async () => { const request = new Request('http://example.com/custom-base/'); const response = await app.render(request); - expect(response.status).to.equal(200); + assert.equal(response.status, 200); const html = await response.text(); const $ = cheerio.load(html); const stylesheets = $('link[rel="stylesheet"]'); stylesheets.each((i, el) => { - expect(el.attribs.href).to.match(assetsPrefixRegex); + assert.match(el.attribs.href, assetsPrefixRegex); }); }); it('image src start with assetsPrefix', async () => { const request = new Request('http://example.com/custom-base/'); const response = await app.render(request); - expect(response.status).to.equal(200); + assert.equal(response.status, 200); const html = await response.text(); const $ = cheerio.load(html); const imgAsset = $('#image-asset'); - expect(imgAsset.attr('src')).to.match(assetsPrefixRegex); + assert.match(imgAsset.attr('src'), assetsPrefixRegex); }); it('react component astro-island should import from assetsPrefix', async () => { const request = new Request('http://example.com/custom-base/'); const response = await app.render(request); - expect(response.status).to.equal(200); + assert.equal(response.status, 200); const html = await response.text(); const $ = cheerio.load(html); const island = $('astro-island'); - expect(island.attr('component-url')).to.match(assetsPrefixRegex); - expect(island.attr('renderer-url')).to.match(assetsPrefixRegex); + assert.match(island.attr('component-url'), assetsPrefixRegex); + assert.match(island.attr('renderer-url'), assetsPrefixRegex); }); it('markdown optimized image src does not start with assetsPrefix in SSR', async () => { const request = new Request('http://example.com/custom-base/markdown/'); const response = await app.render(request); - expect(response.status).to.equal(200); + assert.equal(response.status, 200); const html = await response.text(); const $ = cheerio.load(html); const imgAsset = $('img'); - expect(imgAsset.attr('src')).to.not.match(assetsPrefixRegex); + assert.doesNotMatch(imgAsset.attr('src'), assetsPrefixRegex); }); }); @@ -164,12 +165,12 @@ describe('Assets Prefix, with path prefix', () => { it('all stylesheets should start with assetPrefix', async () => { const request = new Request('http://example.com/custom-base/'); const response = await app.render(request); - expect(response.status).to.equal(200); + assert.equal(response.status, 200); const html = await response.text(); const $ = cheerio.load(html); const stylesheets = $('link[rel="stylesheet"]'); stylesheets.each((i, el) => { - expect(el.attribs.href).to.match(/^\/starting-slash\/.*/); + assert.match(el.attribs.href, /^\/starting-slash\/.*/); }); }); }); diff --git a/packages/astro/test/astro-assets.test.js b/packages/astro/test/astro-assets.nodetest.js similarity index 88% rename from packages/astro/test/astro-assets.test.js rename to packages/astro/test/astro-assets.nodetest.js index 7daa4aaa3daa..266159b707b8 100644 --- a/packages/astro/test/astro-assets.test.js +++ b/packages/astro/test/astro-assets.nodetest.js @@ -1,4 +1,5 @@ -import { expect } from 'chai'; +import assert from 'node:assert/strict'; +import { describe, before, it } from 'node:test'; import * as cheerio from 'cheerio'; import { loadFixture } from './test-utils.js'; import srcsetParse from 'srcset-parse'; @@ -22,7 +23,7 @@ describe('Assets', () => { const $ = cheerio.load(html); const imgPath = $('img').attr('src'); const data = await fixture.readFile(imgPath); - expect(!!data).to.equal(true); + assert.equal(!!data, true); }); it('built the 2x image', async () => { @@ -32,7 +33,7 @@ describe('Assets', () => { const candidates = matchSrcset(srcset); const match = candidates.find((a) => a.density === 2); const data = await fixture.readFile(match.url); - expect(!!data).to.equal(true); + assert.equal(!!data, true); }); it('built the 3x image', async () => { @@ -42,7 +43,7 @@ describe('Assets', () => { const candidates = matchSrcset(srcset); const match = candidates.find((a) => a.density === 3); const data = await fixture.readFile(match.url); - expect(!!data).to.equal(true); + assert.equal(!!data, true); }); it('built image from an import specifier', async () => { @@ -50,7 +51,7 @@ describe('Assets', () => { const $ = cheerio.load(html); const src = $('#import-no-url').attr('src'); const data = await fixture.readFile(src); - expect(!!data).to.equal(true); + assert.equal(!!data, true); }); it('built image from an import specifier using ?url', async () => { @@ -58,6 +59,6 @@ describe('Assets', () => { const $ = cheerio.load(html); const src = $('#import-url').attr('src'); const data = await fixture.readFile(src); - expect(!!data).to.equal(true); + assert.equal(!!data, true); }); }); diff --git a/packages/astro/test/astro-attrs.test.js b/packages/astro/test/astro-attrs.nodetest.js similarity index 76% rename from packages/astro/test/astro-attrs.test.js rename to packages/astro/test/astro-attrs.nodetest.js index d2d5859506ca..a3a8b7e81737 100644 --- a/packages/astro/test/astro-attrs.test.js +++ b/packages/astro/test/astro-attrs.nodetest.js @@ -1,4 +1,5 @@ -import { expect } from 'chai'; +import assert from 'node:assert/strict'; +import { describe, before, it } from 'node:test'; import * as cheerio from 'cheerio'; import { loadFixture } from './test-utils.js'; @@ -33,7 +34,7 @@ describe('Attributes', async () => { for (const id of Object.keys(attrs)) { const { attribute, value } = attrs[id]; const attr = $(`#${id}`).attr(attribute); - expect(attr).to.equal(value); + assert.equal(attr, value); } }); @@ -41,24 +42,24 @@ describe('Attributes', async () => { const html = await fixture.readFile('/component/index.html'); const $ = cheerio.load(html); - expect($('#true').attr('attr')).to.equal('attr-true'); - expect($('#true').attr('type')).to.equal('boolean'); - expect($('#false').attr('attr')).to.equal('attr-false'); - expect($('#false').attr('type')).to.equal('boolean'); + assert.equal($('#true').attr('attr'), 'attr-true'); + assert.equal($('#true').attr('type'), 'boolean'); + assert.equal($('#false').attr('attr'), 'attr-false'); + assert.equal($('#false').attr('type'), 'boolean'); }); it('Passes namespaced attributes as expected', async () => { const html = await fixture.readFile('/namespaced/index.html'); const $ = cheerio.load(html); - expect($('div').attr('xmlns:happy')).to.equal('https://example.com/schemas/happy'); - expect($('img').attr('happy:smile')).to.equal('sweet'); + assert.equal($('div').attr('xmlns:happy'), 'https://example.com/schemas/happy'); + assert.equal($('img').attr('happy:smile'), 'sweet'); }); it('Passes namespaced attributes to components as expected', async () => { const html = await fixture.readFile('/namespaced-component/index.html'); const $ = cheerio.load(html); - expect($('span').attr('on:click')).to.deep.equal('(event) => console.log(event)'); + assert.deepEqual($('span').attr('on:click'), '(event) => console.log(event)'); }); }); diff --git a/packages/astro/test/astro-basic.test.js b/packages/astro/test/astro-basic.nodetest.js similarity index 63% rename from packages/astro/test/astro-basic.test.js rename to packages/astro/test/astro-basic.nodetest.js index 6bd78c2d3360..f363d7287549 100644 --- a/packages/astro/test/astro-basic.test.js +++ b/packages/astro/test/astro-basic.nodetest.js @@ -1,4 +1,5 @@ -import { expect } from 'chai'; +import assert from 'node:assert/strict'; +import { after, describe, before, it } from 'node:test'; import * as cheerio from 'cheerio'; import { loadFixture } from './test-utils.js'; @@ -25,70 +26,70 @@ describe('Astro basic build', () => { const html = await fixture.readFile(`/index.html`); const $ = cheerio.load(html); - expect($('h1').text()).to.equal('Hello world!'); + assert.equal($('h1').text(), 'Hello world!'); }); it('Correctly serializes boolean attributes', async () => { const html = await fixture.readFile('/index.html'); const $ = cheerio.load(html); - expect($('h1').attr('data-something')).to.equal(''); - expect($('h2').attr('not-data-ok')).to.equal(''); + assert.equal($('h1').attr('data-something'), ''); + assert.equal($('h2').attr('not-data-ok'), ''); }); it('Selector with an empty body', async () => { const html = await fixture.readFile('/empty-class/index.html'); const $ = cheerio.load(html); - expect($('.author')).to.have.lengthOf(1); + assert.equal($('.author').length, 1); }); it('Allows forward-slashes in mustache tags (#407)', async () => { const html = await fixture.readFile('/forward-slash/index.html'); const $ = cheerio.load(html); - expect($('a[href="/post/one"]')).to.have.lengthOf(1); - expect($('a[href="/post/two"]')).to.have.lengthOf(1); - expect($('a[href="/post/three"]')).to.have.lengthOf(1); + assert.equal($('a[href="/post/one"]').length, 1); + assert.equal($('a[href="/post/two"]').length, 1); + assert.equal($('a[href="/post/three"]').length, 1); }); it('Allows spread attributes (#521)', async () => { const html = await fixture.readFile('/spread/index.html'); const $ = cheerio.load(html); - expect($('#spread-leading')).to.have.lengthOf(1); - expect($('#spread-leading').attr('a')).to.equal('0'); - expect($('#spread-leading').attr('b')).to.equal('1'); - expect($('#spread-leading').attr('c')).to.equal('2'); + assert.equal($('#spread-leading').length, 1); + assert.equal($('#spread-leading').attr('a'), '0'); + assert.equal($('#spread-leading').attr('b'), '1'); + assert.equal($('#spread-leading').attr('c'), '2'); - expect($('#spread-trailing')).to.have.lengthOf(1); - expect($('#spread-trailing').attr('a')).to.equal('0'); - expect($('#spread-trailing').attr('b')).to.equal('1'); - expect($('#spread-trailing').attr('c')).to.equal('2'); + assert.equal($('#spread-trailing').length, 1); + assert.equal($('#spread-trailing').attr('a'), '0'); + assert.equal($('#spread-trailing').attr('b'), '1'); + assert.equal($('#spread-trailing').attr('c'), '2'); }); it('Allows spread attributes with TypeScript (#521)', async () => { const html = await fixture.readFile('/spread/index.html'); const $ = cheerio.load(html); - expect($('#spread-ts')).to.have.lengthOf(1); - expect($('#spread-ts').attr('a')).to.equal('0'); - expect($('#spread-ts').attr('b')).to.equal('1'); - expect($('#spread-ts').attr('c')).to.equal('2'); + assert.equal($('#spread-ts').length, 1); + assert.equal($('#spread-ts').attr('a'), '0'); + assert.equal($('#spread-ts').attr('b'), '1'); + assert.equal($('#spread-ts').attr('c'), '2'); }); it('Allows scoped classes with spread', async () => { const html = await fixture.readFile('/spread-scope/index.html'); const $ = cheerio.load(html); - expect($('#spread-plain')).to.have.lengthOf(1); - expect($('#spread-plain').attr('class')).to.match(/astro-.*/); + assert.equal($('#spread-plain').length, 1); + assert.match($('#spread-plain').attr('class'), /astro-.*/); - expect($('#spread-class')).to.have.lengthOf(1); - expect($('#spread-class').attr('class')).to.match(/astro-.*/); + assert.equal($('#spread-class').length, 1); + assert.match($('#spread-class').attr('class'), /astro-.*/); - expect($('#spread-class-list')).to.have.lengthOf(1); - expect($('#spread-class-list').attr('class')).to.match(/astro-.*/); + assert.equal($('#spread-class-list').length, 1); + assert.match($('#spread-class-list').attr('class'), /astro-.*/); }); it('Allows using the Fragment element to be used', async () => { @@ -96,30 +97,30 @@ describe('Astro basic build', () => { const $ = cheerio.load(html); // will be 1 if element rendered correctly - expect($('#one')).to.have.lengthOf(1); + assert.strictEqual($('#one').length, 1); }); it('supports special chars in filename', async () => { // will have already erred by now, but add test anyway - expect(await fixture.readFile('/special-“characters” -in-file/index.html')).to.be.ok; + assert.ok(await fixture.readFile('/special-“characters” -in-file/index.html')); }); it('renders the components top-down', async () => { const html = await fixture.readFile('/order/index.html'); const $ = cheerio.load(html); - expect($('#rendered-order').text()).to.eq('Rendered order: A, B'); + assert.strictEqual($('#rendered-order').text(), 'Rendered order: A, B'); }); it('renders markdown in utf-8 by default', async () => { const html = await fixture.readFile('/chinese-encoding-md/index.html'); const $ = cheerio.load(html); - expect($('h1').text()).to.equal('我的第一篇博客文章'); + assert.strictEqual($('h1').text(), '我的第一篇博客文章'); }); it('renders MDX in utf-8 by default', async () => { const html = await fixture.readFile('/chinese-encoding-mdx/index.html'); const $ = cheerio.load(html); - expect($('h1').text()).to.equal('我的第一篇博客文章'); + assert.strictEqual($('h1').text(), '我的第一篇博客文章'); }); it('Supports void elements whose name is a string (#2062)', async () => { @@ -127,45 +128,49 @@ describe('Astro basic build', () => { const $ = cheerio.load(html); // - expect($('body > :nth-child(1)').prop('outerHTML')).to.equal(''); + assert.strictEqual($('body > :nth-child(1)').prop('outerHTML'), ''); // - expect($('body > :nth-child(2)').prop('outerHTML')).to.equal(''); + assert.strictEqual($('body > :nth-child(2)').prop('outerHTML'), ''); // - expect($('body > :nth-child(3)').prop('outerHTML')).to.equal(''); + assert.strictEqual($('body > :nth-child(3)').prop('outerHTML'), ''); // - expect($('body > :nth-child(4)').prop('outerHTML')).to.equal( + assert.strictEqual( + $('body > :nth-child(4)').prop('outerHTML'), '' ); // textarea - expect($('body > :nth-child(5)').prop('outerHTML')).to.equal(''); + assert.strictEqual( + $('body > :nth-child(5)').prop('outerHTML'), + '' + ); }); it('Generates pages that end with .mjs', async () => { const content1 = await fixture.readFile('/get-static-paths-with-mjs/example.mjs'); - expect(content1).to.be.ok; + assert.ok(content1); const content2 = await fixture.readFile('/get-static-paths-with-mjs/example.js'); - expect(content2).to.be.ok; + assert.ok(content2); }); it('allows file:// urls as module specifiers', async () => { const html = await fixture.readFile('/fileurl/index.html'); const $ = cheerio.load(html); - expect($('h1').text()).to.equal('WORKS'); + assert.strictEqual($('h1').text(), 'WORKS'); }); describe('preview', () => { it('returns 200 for valid URLs', async () => { const result = await fixture.fetch('/'); - expect(result.status).to.equal(200); + assert.strictEqual(result.status, 200); }); it('returns 404 for invalid URLs', async () => { const result = await fixture.fetch('/bad-url'); - expect(result.status).to.equal(404); + assert.strictEqual(result.status, 404); }); }); }); @@ -188,25 +193,25 @@ describe('Astro basic development', () => { it('Renders markdown in utf-8 by default', async () => { const res = await fixture.fetch('/chinese-encoding-md'); - expect(res.status).to.equal(200); + assert.strictEqual(res.status, 200); const html = await res.text(); const $ = cheerio.load(html); - expect($('h1').text()).to.equal('我的第一篇博客文章'); + assert.equal($('h1').text(), '我的第一篇博客文章'); const isUtf8 = res.headers.get('content-type').includes('charset=utf-8') || html.includes(''); - expect(isUtf8).to.be.true; + assert.ok(isUtf8); }); it('Renders MDX in utf-8 by default', async () => { const res = await fixture.fetch('/chinese-encoding-mdx'); - expect(res.status).to.equal(200); + assert.strictEqual(res.status, 200); const html = await res.text(); const $ = cheerio.load(html); - expect($('h1').text()).to.equal('我的第一篇博客文章'); + assert.equal($('h1').text(), '我的第一篇博客文章'); const isUtf8 = res.headers.get('content-type').includes('charset=utf-8') || html.includes(''); - expect(isUtf8).to.be.true; + assert.ok(isUtf8); }); }); diff --git a/packages/astro/test/astro-children.test.js b/packages/astro/test/astro-children.nodetest.js similarity index 55% rename from packages/astro/test/astro-children.test.js rename to packages/astro/test/astro-children.nodetest.js index 8a396cce4901..884442804eea 100644 --- a/packages/astro/test/astro-children.test.js +++ b/packages/astro/test/astro-children.nodetest.js @@ -1,4 +1,5 @@ -import { expect } from 'chai'; +import assert from 'node:assert/strict'; +import { describe, before, it } from 'node:test'; import * as cheerio from 'cheerio'; import { loadFixture } from './test-utils.js'; @@ -16,15 +17,15 @@ describe('Component children', () => { // test 1: Can pass text to Preact components const $preact = $('#preact'); - expect($preact.text().trim()).to.equal('Hello world'); + assert.strictEqual($preact.text().trim(), 'Hello world'); // test 2: Can pass text to Vue components const $vue = $('#vue'); - expect($vue.text().trim()).to.equal('Hello world'); + assert.strictEqual($vue.text().trim(), 'Hello world'); // test 3: Can pass text to Svelte components const $svelte = $('#svelte'); - expect($svelte.text().trim()).to.equal('Hello world'); + assert.strictEqual($svelte.text().trim(), 'Hello world'); }); it('Passes markup children to framework components', async () => { @@ -33,15 +34,15 @@ describe('Component children', () => { // test 1: Can pass markup to Preact components const $preact = $('#preact h1'); - expect($preact.text().trim()).to.equal('Hello world'); + assert.strictEqual($preact.text().trim(), 'Hello world'); // test 2: Can pass markup to Vue components const $vue = $('#vue h1'); - expect($vue.text().trim()).to.equal('Hello world'); + assert.strictEqual($vue.text().trim(), 'Hello world'); // test 3: Can pass markup to Svelte components const $svelte = $('#svelte h1'); - expect($svelte.text().trim()).to.equal('Hello world'); + assert.strictEqual($svelte.text().trim(), 'Hello world'); }); it('Passes multiple children to framework components', async () => { @@ -50,21 +51,21 @@ describe('Component children', () => { // test 1: Can pass multiple children to Preact components const $preact = $('#preact'); - expect($preact.children()).to.have.lengthOf(2); - expect($preact.children(':first-child').text().trim()).to.equal('Hello world'); - expect($preact.children(':last-child').text().trim()).to.equal('Goodbye world'); + assert.strictEqual($preact.children().length, 2); + assert.strictEqual($preact.children(':first-child').text().trim(), 'Hello world'); + assert.strictEqual($preact.children(':last-child').text().trim(), 'Goodbye world'); // test 2: Can pass multiple children to Vue components const $vue = $('#vue'); - expect($vue.children()).to.have.lengthOf(2); - expect($vue.children(':first-child').text().trim()).to.equal('Hello world'); - expect($vue.children(':last-child').text().trim()).to.equal('Goodbye world'); + assert.strictEqual($vue.children().length, 2); + assert.strictEqual($vue.children(':first-child').text().trim(), 'Hello world'); + assert.strictEqual($vue.children(':last-child').text().trim(), 'Goodbye world'); // test 3: Can pass multiple children to Svelte components const $svelte = $('#svelte'); - expect($svelte.children()).to.have.lengthOf(2); - expect($svelte.children(':first-child').text().trim()).to.equal('Hello world'); - expect($svelte.children(':last-child').text().trim()).to.equal('Goodbye world'); + assert.strictEqual($svelte.children().length, 2); + assert.strictEqual($svelte.children(':first-child').text().trim(), 'Hello world'); + assert.strictEqual($svelte.children(':last-child').text().trim(), 'Goodbye world'); }); it('Renders a template when children are not rendered for client components', async () => { @@ -72,24 +73,26 @@ describe('Component children', () => { const $ = cheerio.load(html); // test 1: If SSR only, no children are rendered. - expect($('#ssr-only').children()).to.have.lengthOf(0); + assert.strictEqual($('#ssr-only').children().length, 0); // test 2: If client, and no children are rendered, a template is. - expect($('#client').parent().children()).to.have.lengthOf( + assert.strictEqual( + $('#client').parent().children().length, 2, 'rendered the client component and a template' ); - expect($('#client').parent().find('template[data-astro-template]')).to.have.lengthOf( + assert.strictEqual( + $('#client').parent().find('template[data-astro-template]').length, 1, 'Found 1 template' ); // test 3: If client, and children are rendered, no template is. - expect($('#client-render').parent().children()).to.have.lengthOf(1); - expect($('#client-render').parent().find('template')).to.have.lengthOf(0); + assert.strictEqual($('#client-render').parent().children().length, 1); + assert.strictEqual($('#client-render').parent().find('template').length, 0); // test 4: If client and no children are provided, no template is. - expect($('#client-no-children').parent().children()).to.have.lengthOf(1); - expect($('#client-no-children').parent().find('template')).to.have.lengthOf(0); + assert.strictEqual($('#client-no-children').parent().children().length, 1); + assert.strictEqual($('#client-no-children').parent().find('template').length, 0); }); }); diff --git a/packages/astro/test/astro-class-list.nodetest.js b/packages/astro/test/astro-class-list.nodetest.js new file mode 100644 index 000000000000..7d300e997fe9 --- /dev/null +++ b/packages/astro/test/astro-class-list.nodetest.js @@ -0,0 +1,63 @@ +import assert from 'node:assert/strict'; +import { describe, before, it } from 'node:test'; +import * as cheerio from 'cheerio'; +import { loadFixture } from './test-utils.js'; + +describe('Class List', async () => { + let fixture; + + before(async () => { + fixture = await loadFixture({ root: './fixtures/astro-class-list/' }); + await fixture.build(); + }); + + it('Passes class:list attributes as expected to elements', async () => { + const html = await fixture.readFile('/index.html'); + const $ = cheerio.load(html); + + assert.equal($('[class="test control"]').length, 1, '[class="test control"]'); + assert.equal($('[class="test expression"]').length, 1, '[class="test expression"]'); + assert.equal($('[class="test true"]').length, 1, '[class="test true"]'); + assert.equal($('[class="test truthy"]').length, 1, '[class="test truthy"]'); + assert.equal($('[class="test set"]').length, 1, '[class="test set"]'); + assert.equal( + $('[class="hello goodbye hello world hello friend"]').length, + 1, + '[class="hello goodbye hello world hello friend"]' + ); + assert.equal($('[class="foo baz"]').length, 1, '[class="foo baz"]'); + assert.equal($('span:not([class])').length, 1, 'span:not([class])'); + + assert.equal($('.false, .noshow1, .noshow2, .noshow3, .noshow4').length, 0); + }); + + it('Passes class:list attributes as expected to components', async () => { + const html = await fixture.readFile('/component/index.html'); + const $ = cheerio.load(html); + + assert.equal($('[class="test control"]').length, 1, '[class="test control"]'); + assert.equal($('[class="test expression"]').length, 1, '[class="test expression"]'); + assert.equal($('[class="test true"]').length, 1, '[class="test true"]'); + assert.equal($('[class="test truthy"]').length, 1, '[class="test truthy"]'); + assert.equal($('[class="test set"]').length, 1, '[class="test set"]'); + assert.equal( + $('[class="hello goodbye hello world hello friend"]').length, + 1, + '[class="hello goodbye hello world hello friend"]' + ); + assert.equal($('[class="foo baz"]').length, 1, '[class="foo baz"]'); + assert.equal($('span:not([class])').length, 1, 'span:not([class])'); + + assert.equal($('[class="test control"]').text(), 'test control'); + assert.equal($('[class="test expression"]').text(), 'test expression'); + assert.equal($('[class="test true"]').text(), 'test true'); + assert.equal($('[class="test truthy"]').text(), 'test truthy'); + assert.equal($('[class="test set"]').text(), 'test set'); + assert.equal( + $('[class="hello goodbye hello world hello friend"]').text(), + 'hello goodbye hello world hello friend' + ); + assert.equal($('[class="foo baz"]').text(), 'foo baz'); + assert.equal($('span:not([class])').text(), ''); + }); +}); diff --git a/packages/astro/test/astro-class-list.test.js b/packages/astro/test/astro-class-list.test.js deleted file mode 100644 index 4fd7cd13f718..000000000000 --- a/packages/astro/test/astro-class-list.test.js +++ /dev/null @@ -1,59 +0,0 @@ -import { expect } from 'chai'; -import * as cheerio from 'cheerio'; -import { loadFixture } from './test-utils.js'; - -describe('Class List', async () => { - let fixture; - - before(async () => { - fixture = await loadFixture({ root: './fixtures/astro-class-list/' }); - await fixture.build(); - }); - - it('Passes class:list attributes as expected to elements', async () => { - const html = await fixture.readFile('/index.html'); - const $ = cheerio.load(html); - - expect($('[class="test control"]')).to.have.lengthOf(1, '[class="test control"]'); - expect($('[class="test expression"]')).to.have.lengthOf(1, '[class="test expression"]'); - expect($('[class="test true"]')).to.have.lengthOf(1, '[class="test true"]'); - expect($('[class="test truthy"]')).to.have.lengthOf(1, '[class="test truthy"]'); - expect($('[class="test set"]')).to.have.lengthOf(1, '[class="test set"]'); - expect($('[class="hello goodbye hello world hello friend"]')).to.have.lengthOf( - 1, - '[class="hello goodbye hello world hello friend"]' - ); - expect($('[class="foo baz"]')).to.have.lengthOf(1, '[class="foo baz"]'); - expect($('span:not([class])')).to.have.lengthOf(1, 'span:not([class])'); - - expect($('.false, .noshow1, .noshow2, .noshow3, .noshow4')).to.have.lengthOf(0); - }); - - it('Passes class:list attributes as expected to components', async () => { - const html = await fixture.readFile('/component/index.html'); - const $ = cheerio.load(html); - - expect($('[class="test control"]')).to.have.lengthOf(1, '[class="test control"]'); - expect($('[class="test expression"]')).to.have.lengthOf(1, '[class="test expression"]'); - expect($('[class="test true"]')).to.have.lengthOf(1, '[class="test true"]'); - expect($('[class="test truthy"]')).to.have.lengthOf(1, '[class="test truthy"]'); - expect($('[class="test set"]')).to.have.lengthOf(1, '[class="test set"]'); - expect($('[class="hello goodbye hello world hello friend"]')).to.have.lengthOf( - 1, - '[class="hello goodbye hello world hello friend"]' - ); - expect($('[class="foo baz"]')).to.have.lengthOf(1, '[class="foo baz"]'); - expect($('span:not([class])')).to.have.lengthOf(1, 'span:not([class])'); - - expect($('[class="test control"]').text()).to.equal('test control'); - expect($('[class="test expression"]').text()).to.equal('test expression'); - expect($('[class="test true"]').text()).to.equal('test true'); - expect($('[class="test truthy"]').text()).to.equal('test truthy'); - expect($('[class="test set"]').text()).to.equal('test set'); - expect($('[class="hello goodbye hello world hello friend"]').text()).to.equal( - 'hello goodbye hello world hello friend' - ); - expect($('[class="foo baz"]').text()).to.equal('foo baz'); - expect($('span:not([class])').text()).to.equal(''); - }); -}); diff --git a/packages/astro/test/astro-component-bundling.test.js b/packages/astro/test/astro-component-bundling.nodetest.js similarity index 77% rename from packages/astro/test/astro-component-bundling.test.js rename to packages/astro/test/astro-component-bundling.nodetest.js index 9a12919429a9..2d8b75aa55a6 100644 --- a/packages/astro/test/astro-component-bundling.test.js +++ b/packages/astro/test/astro-component-bundling.nodetest.js @@ -1,4 +1,5 @@ -import { expect } from 'chai'; +import assert from 'node:assert/strict'; +import { describe, before, it } from 'node:test'; import { loadFixture } from './test-utils.js'; describe('Component bundling', () => { @@ -15,6 +16,6 @@ describe('Component bundling', () => { chunk.startsWith('ManyComponents') ); const manyComponentsChunkContent = await fixture.readFile(`/_astro/${manyComponentsChunkName}`); - expect(manyComponentsChunkContent).to.not.include('FooComponent'); + assert.equal(manyComponentsChunkContent.includes('FooComponent'), false); }); }); diff --git a/packages/astro/test/astro-external-files.test.js b/packages/astro/test/astro-external-files.nodetest.js similarity index 70% rename from packages/astro/test/astro-external-files.test.js rename to packages/astro/test/astro-external-files.nodetest.js index 7aaf04c80339..5db44bc21a55 100644 --- a/packages/astro/test/astro-external-files.test.js +++ b/packages/astro/test/astro-external-files.nodetest.js @@ -1,4 +1,5 @@ -import { expect } from 'chai'; +import assert from 'node:assert/strict'; +import { describe, before, it } from 'node:test'; import { loadFixture } from './test-utils.js'; describe('External file references', () => { @@ -11,7 +12,7 @@ describe('External file references', () => { it('Build with externeal reference', async () => { const html = await fixture.readFile('/index.html'); - expect(html).to.include(''), true); + assert.equal(indexHtml.includes(''), true); + assert.equal(indexHtml.includes(''), true); + }); +}); diff --git a/packages/astro/test/astro-public.test.js b/packages/astro/test/astro-public.test.js deleted file mode 100644 index 9f4094e1c8d7..000000000000 --- a/packages/astro/test/astro-public.test.js +++ /dev/null @@ -1,18 +0,0 @@ -import { expect } from 'chai'; -import { loadFixture } from './test-utils.js'; - -describe('Public', () => { - let fixture; - - before(async () => { - fixture = await loadFixture({ root: './fixtures/astro-public/' }); - await fixture.build(); - }); - - it('css and js files do not get bundled', async () => { - let indexHtml = await fixture.readFile('/index.html'); - expect(indexHtml).to.include(''); - expect(indexHtml).to.include(''); - expect(indexHtml).to.include(''); - }); -}); diff --git a/packages/astro/test/astro-response.test.js b/packages/astro/test/astro-response.nodetest.js similarity index 78% rename from packages/astro/test/astro-response.test.js rename to packages/astro/test/astro-response.nodetest.js index c77e7bad34ef..3a1bc306f252 100644 --- a/packages/astro/test/astro-response.test.js +++ b/packages/astro/test/astro-response.nodetest.js @@ -1,4 +1,5 @@ -import { expect } from 'chai'; +import assert from 'node:assert/strict'; +import { after, describe, before, it } from 'node:test'; import { loadFixture } from './test-utils.js'; // Asset bundling @@ -21,6 +22,6 @@ describe('Returning responses', () => { it('Works from a page', async () => { let response = await fixture.fetch('/not-found'); - expect(response.status).to.equal(404); + assert.equal(response.status, 404); }); }); diff --git a/packages/astro/test/astro-slot-with-client.test.js b/packages/astro/test/astro-slot-with-client.nodetest.js similarity index 77% rename from packages/astro/test/astro-slot-with-client.test.js rename to packages/astro/test/astro-slot-with-client.nodetest.js index 4ad26dee41ab..d0789689d56e 100644 --- a/packages/astro/test/astro-slot-with-client.test.js +++ b/packages/astro/test/astro-slot-with-client.nodetest.js @@ -1,4 +1,5 @@ -import { expect } from 'chai'; +import assert from 'node:assert/strict'; +import { describe, before, it } from 'node:test'; import * as cheerio from 'cheerio'; import { loadFixture } from './test-utils.js'; @@ -14,12 +15,12 @@ describe('Slots with client: directives', () => { it('Tags of dynamic tags works', async () => { const html = await fixture.readFile('/index.html'); const $ = cheerio.load(html); - expect($('script')).to.have.a.lengthOf(1); + assert.equal($('script').length, 1); }); it('Astro slot tags are cleaned', async () => { const html = await fixture.readFile('/index.html'); const $ = cheerio.load(html); - expect($('astro-slot')).to.have.a.lengthOf(0); + assert.equal($('astro-slot').length, 0); }); }); diff --git a/packages/astro/test/astro-slots.test.js b/packages/astro/test/astro-slots.nodetest.js similarity index 56% rename from packages/astro/test/astro-slots.test.js rename to packages/astro/test/astro-slots.nodetest.js index 69a0025e1f27..5e916685f54e 100644 --- a/packages/astro/test/astro-slots.test.js +++ b/packages/astro/test/astro-slots.nodetest.js @@ -1,4 +1,5 @@ -import { expect } from 'chai'; +import assert from 'node:assert/strict'; +import { describe, before, it } from 'node:test'; import * as cheerio from 'cheerio'; import { loadFixture } from './test-utils.js'; @@ -14,59 +15,59 @@ describe('Slots', () => { const html = await fixture.readFile('/index.html'); const $ = cheerio.load(html); - expect($('#a').text().trim()).to.equal('A'); - expect($('#b').text().trim()).to.equal('B'); - expect($('#c').text().trim()).to.equal('C'); - expect($('#default').text().trim()).to.equal('Default'); + assert.equal($('#a').text().trim(), 'A'); + assert.equal($('#b').text().trim(), 'B'); + assert.equal($('#c').text().trim(), 'C'); + assert.equal($('#default').text().trim(), 'Default'); }); it('Dynamic named slots work', async () => { const html = await fixture.readFile('/dynamic/index.html'); const $ = cheerio.load(html); - expect($('#a').text().trim()).to.equal('A'); - expect($('#b').text().trim()).to.equal('B'); - expect($('#c').text().trim()).to.equal('C'); - expect($('#default').text().trim()).to.equal('Default'); + assert.equal($('#a').text().trim(), 'A'); + assert.equal($('#b').text().trim(), 'B'); + assert.equal($('#c').text().trim(), 'C'); + assert.equal($('#default').text().trim(), 'Default'); }); it('Conditional named slots work', async () => { const html = await fixture.readFile('/conditional/index.html'); const $ = cheerio.load(html); - expect($('#a').text().trim()).to.equal('A'); - expect($('#b').text().trim()).to.equal('B'); - expect($('#c').text().trim()).to.equal('C'); - expect($('#default').text().trim()).to.equal('Default'); + assert.equal($('#a').text().trim(), 'A'); + assert.equal($('#b').text().trim(), 'B'); + assert.equal($('#c').text().trim(), 'C'); + assert.equal($('#default').text().trim(), 'Default'); }); it('Slots of a component render fallback content by default', async () => { const html = await fixture.readFile('/fallback/index.html'); const $ = cheerio.load(html); - expect($('#default')).to.have.lengthOf(1); + assert.equal($('#default').length, 1); }); it('Slots of a page render fallback content', async () => { const html = await fixture.readFile('/fallback-own/index.html'); const $ = cheerio.load(html); - expect($('#default')).to.have.lengthOf(1); + assert.equal($('#default').length, 1); }); it('Slots override fallback content', async () => { const html = await fixture.readFile('/fallback-override/index.html'); const $ = cheerio.load(html); - expect($('#override')).to.have.lengthOf(1); - expect($('#fallback-2').text()).to.equal('Slotty slot.'); + assert.equal($('#override').length, 1); + assert.equal($('#fallback-2').text(), 'Slotty slot.'); }); it('Slots work with multiple elements', async () => { const html = await fixture.readFile('/multiple/index.html'); const $ = cheerio.load(html); - expect($('#a').text().trim()).to.equal('ABC'); + assert.equal($('#a').text().trim(), 'ABC'); }); it('Slots work on Components', async () => { @@ -74,13 +75,12 @@ describe('Slots', () => { const $ = cheerio.load(html); // test 1: #a renders - expect($('#a')).to.have.lengthOf(1); + assert.equal($('#a').length, 1); // test 2: Slotted component into #a - expect($('#a').children('astro-component')).to.have.lengthOf(1); - + assert.equal($('#a').children('astro-component').length, 1); // test 3: Slotted component into default slot - expect($('#default').children('astro-component')).to.have.lengthOf(1); + assert.equal($('#default').children('astro-component').length, 1); }); describe('Slots API work on Components', () => { @@ -88,42 +88,42 @@ describe('Slots', () => { const html = await fixture.readFile('/slottedapi-default/index.html'); const $ = cheerio.load(html); - expect($('#a')).to.have.lengthOf(1); - expect($('#b')).to.have.lengthOf(1); - expect($('#c')).to.have.lengthOf(1); - expect($('#default')).to.have.lengthOf(1); + assert.equal($('#a').length, 1); + assert.equal($('#b').length, 1); + assert.equal($('#c').length, 1); + assert.equal($('#default').length, 1); }); it('IDs will not exist because the slots are not filled', async () => { const html = await fixture.readFile('/slottedapi-empty/index.html'); const $ = cheerio.load(html); - expect($('#a')).to.have.lengthOf(0); - expect($('#b')).to.have.lengthOf(0); - expect($('#c')).to.have.lengthOf(0); - expect($('#default')).to.have.lengthOf(0); + assert.equal($('#a').length, 0); + assert.equal($('#b').length, 0); + assert.equal($('#c').length, 0); + assert.equal($('#default').length, 0); }); it('IDs will exist because the slots are filled', async () => { const html = await fixture.readFile('/slottedapi-filled/index.html'); const $ = cheerio.load(html); - expect($('#a')).to.have.lengthOf(1); - expect($('#b')).to.have.lengthOf(1); - expect($('#c')).to.have.lengthOf(1); + assert.equal($('#a').length, 1); + assert.equal($('#b').length, 1); + assert.equal($('#c').length, 1); - expect($('#default')).to.have.lengthOf(0); // the default slot is not filled + assert.equal($('#default').length, 0); // the default slot is not filled }); it('Default ID will exist because the default slot is filled', async () => { const html = await fixture.readFile('/slottedapi-default-filled/index.html'); const $ = cheerio.load(html); - expect($('#a')).to.have.lengthOf(0); - expect($('#b')).to.have.lengthOf(0); - expect($('#c')).to.have.lengthOf(0); + assert.equal($('#a').length, 0); + assert.equal($('#b').length, 0); + assert.equal($('#c').length, 0); - expect($('#default')).to.have.lengthOf(1); // the default slot is filled + assert.equal($('#default').length, 1); // the default slot is not filled }); }); @@ -133,8 +133,8 @@ describe('Slots', () => { const html = await fixture.readFile('/slottedapi-render/index.html'); const $ = cheerio.load(html); - expect($('#render')).to.have.lengthOf(1); - expect($('#render').text()).to.equal('render'); + assert.equal($('#render').length, 1); + assert.equal($('#render').text(), 'render'); } // Child function render without args @@ -142,8 +142,8 @@ describe('Slots', () => { const html = await fixture.readFile('/slottedapi-render/index.html'); const $ = cheerio.load(html); - expect($('#render-fn')).to.have.lengthOf(1); - expect($('#render-fn').text()).to.equal('render-fn'); + assert.equal($('#render-fn').length, 1); + assert.equal($('#render-fn').text(), 'render-fn'); } // Child function render with args @@ -151,9 +151,9 @@ describe('Slots', () => { const html = await fixture.readFile('/slottedapi-render/index.html'); const $ = cheerio.load(html); - expect($('#render-args')).to.have.lengthOf(1); - expect($('#render-args span')).to.have.lengthOf(1); - expect($('#render-args').text()).to.equal('render-args'); + assert.equal($('#render-args').length, 1); + assert.equal($('#render-args span').length, 1); + assert.equal($('#render-args').text(), 'render-args'); } { @@ -161,13 +161,13 @@ describe('Slots', () => { const $ = cheerio.load(html); const elements = $('div'); - expect(elements).to.have.lengthOf(10); + assert.equal(elements.length, 10); const [first, second, third] = elements; - expect(first.children[0].data).to.not.equal(second.children[0].data); - expect(second.children[0].data).to.not.equal(third.children[0].data); - expect(third.children[0].data).to.not.equal(first.children[0].data); + assert.notEqual(first.children[0].data, second.children[0].data); + assert.notEqual(second.children[0].data, third.children[0].data); + assert.notEqual(third.children[0].data, first.children[0].data); } }); }); diff --git a/packages/astro/test/before-hydration.test.js b/packages/astro/test/before-hydration.nodetest.js similarity index 88% rename from packages/astro/test/before-hydration.test.js rename to packages/astro/test/before-hydration.nodetest.js index f429c31b35a0..76d824a75098 100644 --- a/packages/astro/test/before-hydration.test.js +++ b/packages/astro/test/before-hydration.nodetest.js @@ -1,4 +1,5 @@ -import { expect } from 'chai'; +import assert from 'node:assert/strict'; +import { after, describe, before, it } from 'node:test'; import * as cheerio from 'cheerio'; import { loadFixture } from './test-utils.js'; import { preact } from './fixtures/before-hydration/deps.mjs'; @@ -43,7 +44,7 @@ describe('Astro Scripts before-hydration', () => { let res = await fixture.fetch('/'); let html = await res.text(); let $ = cheerio.load(html); - expect($('astro-island[before-hydration-url]')).has.a.lengthOf(1); + assert.equal($('astro-island[before-hydration-url]').length, 1); }); }); @@ -55,7 +56,7 @@ describe('Astro Scripts before-hydration', () => { it('Is included in the astro-island', async () => { let html = await fixture.readFile('/index.html'); let $ = cheerio.load(html); - expect($('astro-island[before-hydration-url]')).has.a.lengthOf(1); + assert.equal($('astro-island[before-hydration-url]').length, 1); }); }); }); @@ -86,7 +87,7 @@ describe('Astro Scripts before-hydration', () => { let res = await fixture.fetch('/'); let html = await res.text(); let $ = cheerio.load(html); - expect($('astro-island[before-hydration-url]')).has.a.lengthOf(1); + assert.equal($('astro-island[before-hydration-url]').length, 1); }); }); @@ -98,7 +99,7 @@ describe('Astro Scripts before-hydration', () => { it('Does not include before-hydration-url on the astro-island', async () => { let html = await fixture.readFile('/index.html'); let $ = cheerio.load(html); - expect($('astro-island[before-hydration-url]')).has.a.lengthOf(0); + assert.equal($('astro-island[before-hydration-url]').length, 0); }); }); }); @@ -139,7 +140,7 @@ describe('Astro Scripts before-hydration', () => { let response = await app.render(request); let html = await response.text(); let $ = cheerio.load(html); - expect($('astro-island[before-hydration-url]')).has.a.lengthOf(1); + assert.equal($('astro-island[before-hydration-url]').length, 1); }); }); }); @@ -167,7 +168,7 @@ describe('Astro Scripts before-hydration', () => { let response = await app.render(request); let html = await response.text(); let $ = cheerio.load(html); - expect($('astro-island[before-hydration-url]')).has.a.lengthOf(0); + assert.equal($('astro-island[before-hydration-url]').length, 0); }); }); }); diff --git a/packages/astro/test/build-assets.test.js b/packages/astro/test/build-assets.nodetest.js similarity index 74% rename from packages/astro/test/build-assets.test.js rename to packages/astro/test/build-assets.nodetest.js index 3d4dacd7b5b0..cba3e5b46a37 100644 --- a/packages/astro/test/build-assets.test.js +++ b/packages/astro/test/build-assets.nodetest.js @@ -1,4 +1,5 @@ -import { expect } from 'chai'; +import assert from 'node:assert/strict'; +import { describe, before, it } from 'node:test'; import * as cheerio from 'cheerio'; import { loadFixture } from './test-utils.js'; import { preact } from './fixtures/before-hydration/deps.mjs'; @@ -21,13 +22,13 @@ describe('build assets (static)', () => { it('Populates /_astro directory', async () => { let files = await fixture.readdir('/_astro'); - expect(files.length).to.be.greaterThan(0); + assert.equal(files.length > 0, true); }); it('Defaults to flat /_astro output', async () => { let files = await fixture.readdir('/_astro'); for (const file of files) { - expect(file.slice(1)).to.not.contain('/'); + assert.equal(file.slice(1).includes('/'), false); } }); @@ -35,7 +36,7 @@ describe('build assets (static)', () => { let html = await fixture.readFile('/index.html'); let $ = cheerio.load(html); - expect($('link[href$=".css"]').attr('href')).to.match(/^\/_astro\//); + assert.match($('link[href$=".css"]').attr('href'), /^\/_astro\//); }); it('emits JS assets to /_astro', async () => { @@ -43,9 +44,9 @@ describe('build assets (static)', () => { let $ = cheerio.load(html); const island = $('astro-island'); - expect(island.length).to.eq(1); - expect(island.attr('component-url')).to.match(/^\/_astro\//); - expect(island.attr('renderer-url')).to.match(/^\/_astro\//); + assert.equal(island.length, 1); + assert.match(island.attr('component-url'), /^\/_astro\//); + assert.match(island.attr('renderer-url'), /^\/_astro\//); }); }); @@ -67,14 +68,14 @@ describe('build assets (static)', () => { it('Populates /custom-assets directory', async () => { let files = await fixture.readdir('/custom-assets'); - expect(files.length).to.be.greaterThan(0); + assert.equal(files.length > 0, true); }); it('emits CSS assets to /custom-assets', async () => { let html = await fixture.readFile('/index.html'); let $ = cheerio.load(html); - expect($('link[href$=".css"]').attr('href')).to.match(/^\/custom-assets\//); + assert.match($('link[href$=".css"]').attr('href'), /^\/custom-assets\//); }); it('emits JS assets to /custom-assets', async () => { @@ -82,9 +83,9 @@ describe('build assets (static)', () => { let $ = cheerio.load(html); const island = $('astro-island'); - expect(island.length).to.eq(1); - expect(island.attr('component-url')).to.match(/^\/custom-assets\//); - expect(island.attr('renderer-url')).to.match(/^\/custom-assets\//); + assert.equal(island.length, 1); + assert.match(island.attr('component-url'), /^\/custom-assets\//); + assert.match(island.attr('renderer-url'), /^\/custom-assets\//); }); }); }); @@ -107,13 +108,13 @@ describe('build assets (server)', () => { it('Populates /_astro directory', async () => { let files = await fixture.readdir('/_astro'); - expect(files.length).to.be.greaterThan(0); + assert.equal(files.length > 0, true); }); it('Defaults to flat /_astro output', async () => { let files = await fixture.readdir('/_astro'); for (const file of files) { - expect(file.slice(1)).to.not.contain('/'); + assert.equal(file.slice(1).includes('/'), false); } }); @@ -121,7 +122,7 @@ describe('build assets (server)', () => { let html = await fixture.readFile('/index.html'); let $ = cheerio.load(html); - expect($('link[href$=".css"]').attr('href')).to.match(/^\/_astro\//); + assert.match($('link[href$=".css"]').attr('href'), /^\/_astro\//); }); it('emits JS assets to /_astro', async () => { @@ -129,9 +130,9 @@ describe('build assets (server)', () => { let $ = cheerio.load(html); const island = $('astro-island'); - expect(island.length).to.eq(1); - expect(island.attr('component-url')).to.match(/^\/_astro\//); - expect(island.attr('renderer-url')).to.match(/^\/_astro\//); + assert.equal(island.length, 1); + assert.match(island.attr('component-url'), /^\/_astro\//); + assert.match(island.attr('renderer-url'), /^\/_astro\//); }); }); @@ -154,14 +155,14 @@ describe('build assets (server)', () => { it('Populates /custom-assets directory', async () => { let files = await fixture.readdir('/custom-assets'); - expect(files.length).to.be.greaterThan(0); + assert.equal(files.length > 0, true); }); it('emits CSS assets to /custom-assets', async () => { let html = await fixture.readFile('/index.html'); let $ = cheerio.load(html); - expect($('link[href$=".css"]').attr('href')).to.match(/^\/custom-assets\//); + assert.match($('link[href$=".css"]').attr('href'), /^\/custom-assets\//); }); it('emits JS assets to /custom-assets', async () => { @@ -169,9 +170,9 @@ describe('build assets (server)', () => { let $ = cheerio.load(html); const island = $('astro-island'); - expect(island.length).to.eq(1); - expect(island.attr('component-url')).to.match(/^\/custom-assets\//); - expect(island.attr('renderer-url')).to.match(/^\/custom-assets\//); + assert.equal(island.length, 1); + assert.match(island.attr('component-url'), /^\/custom-assets\//); + assert.match(island.attr('renderer-url'), /^\/custom-assets\//); }); }); }); diff --git a/packages/astro/test/content-collection-references.test.js b/packages/astro/test/content-collection-references.nodetest.js similarity index 66% rename from packages/astro/test/content-collection-references.test.js rename to packages/astro/test/content-collection-references.nodetest.js index da15486211f0..bf31f5dc46ae 100644 --- a/packages/astro/test/content-collection-references.test.js +++ b/packages/astro/test/content-collection-references.nodetest.js @@ -1,4 +1,5 @@ -import { expect } from 'chai'; +import * as assert from 'node:assert/strict'; +import { after, describe, before, it } from 'node:test'; import * as cheerio from 'cheerio'; import { fixLineEndings, loadFixture } from './test-utils.js'; @@ -39,31 +40,32 @@ describe('Content Collections - references', () => { }); it('Returns expected keys', () => { - expect(json).to.haveOwnProperty('welcomePost'); - expect(json).to.haveOwnProperty('banner'); - expect(json).to.haveOwnProperty('author'); - expect(json).to.haveOwnProperty('relatedPosts'); + assert.ok(json.hasOwnProperty('welcomePost')); + assert.ok(json.hasOwnProperty('banner')); + assert.ok(json.hasOwnProperty('author')); + assert.ok(json.hasOwnProperty('relatedPosts')); }); it('Returns `banner` data', () => { const { banner } = json; - expect(banner).to.haveOwnProperty('data'); - expect(banner.id).to.equal('welcome'); - expect(banner.collection).to.equal('banners'); - expect(banner.data.alt).to.equal( + assert.ok(banner.hasOwnProperty('data')); + assert.equal(banner.id, 'welcome'); + assert.equal(banner.collection, 'banners'); + assert.equal( + banner.data.alt, 'Futuristic landscape with chrome buildings and blue skies' ); - expect(banner.data.src.width).to.equal(400); - expect(banner.data.src.height).to.equal(225); - expect(banner.data.src.format).to.equal('jpg'); - expect(banner.data.src.src.includes('the-future')).to.be.true; + assert.equal(banner.data.src.width, 400); + assert.equal(banner.data.src.height, 225); + assert.equal(banner.data.src.format, 'jpg'); + assert.equal(banner.data.src.src.includes('the-future'), true); }); it('Returns `author` data', () => { const { author } = json; - expect(author).to.haveOwnProperty('data'); - expect(author).to.deep.equal({ + assert.ok(author.hasOwnProperty('data')); + assert.deepEqual(author, { id: 'nate-moore', collection: 'authors', data: { @@ -75,12 +77,12 @@ describe('Content Collections - references', () => { it('Returns `relatedPosts` data', () => { const { relatedPosts } = json; - expect(Array.isArray(relatedPosts)).to.be.true; + assert.equal(Array.isArray(relatedPosts), true, 'Expected relatedPosts to be an array'); const topLevelInfo = relatedPosts.map(({ data, body, ...meta }) => ({ ...meta, body: fixLineEndings(body).trim(), })); - expect(topLevelInfo).to.deep.equal([ + assert.deepEqual(topLevelInfo, [ { id: 'related-1.md', slug: 'related-1', @@ -95,7 +97,7 @@ describe('Content Collections - references', () => { }, ]); const postData = relatedPosts.map(({ data }) => data); - expect(postData).to.deep.equal([ + assert.deepEqual(postData, [ { title: 'Related post 1', banner: { id: 'welcome', collection: 'banners' }, @@ -125,32 +127,33 @@ describe('Content Collections - references', () => { it('Renders `banner` data', () => { const banner = $('img[data-banner]'); - expect(banner.length).to.equal(1); - expect(banner.attr('src')).to.include('the-future'); - expect(banner.attr('alt')).to.equal( + assert.equal(banner.length, 1); + assert.ok(banner.attr('src').includes('the-future')); + assert.equal( + banner.attr('alt'), 'Futuristic landscape with chrome buildings and blue skies' ); - expect(banner.attr('width')).to.equal('400'); - expect(banner.attr('height')).to.equal('225'); + assert.equal(banner.attr('width'), '400'); + assert.equal(banner.attr('height'), '225'); }); it('Renders `author` data', () => { const author = $('a[data-author-name]'); - expect(author.length).to.equal(1); - expect(author.attr('href')).to.equal('https://twitter.com/n_moore'); - expect(author.text()).to.equal('Nate Something Moore'); + assert.equal(author.length, 1); + assert.equal(author.attr('href'), 'https://twitter.com/n_moore'); + assert.equal(author.text(), 'Nate Something Moore'); }); it('Renders `relatedPosts` data', () => { const relatedPosts = $('ul[data-related-posts]'); - expect(relatedPosts.length).to.equal(1); + assert.equal(relatedPosts.length, 1); const relatedPost1 = relatedPosts.find('li').eq(0); - expect(relatedPost1.find('a').attr('href')).to.equal('/blog/related-1'); - expect(relatedPost1.find('a').text()).to.equal('Related post 1'); + assert.equal(relatedPost1.find('a').attr('href'), '/blog/related-1'); + assert.equal(relatedPost1.find('a').text(), 'Related post 1'); const relatedPost2 = relatedPosts.find('li').eq(1); - expect(relatedPost2.find('a').attr('href')).to.equal('/blog/related-2'); - expect(relatedPost2.find('a').text()).to.equal('Related post 2'); + assert.equal(relatedPost2.find('a').attr('href'), '/blog/related-2'); + assert.equal(relatedPost2.find('a').text(), 'Related post 2'); }); }); }); diff --git a/packages/astro/test/content-collections-render.test.js b/packages/astro/test/content-collections-render.nodetest.js similarity index 73% rename from packages/astro/test/content-collections-render.test.js rename to packages/astro/test/content-collections-render.nodetest.js index 27eb33b5a6b5..b177fa54263f 100644 --- a/packages/astro/test/content-collections-render.test.js +++ b/packages/astro/test/content-collections-render.nodetest.js @@ -1,9 +1,12 @@ -import { expect } from 'chai'; +import * as assert from 'node:assert/strict'; +import { after, describe, before, it } from 'node:test'; import * as cheerio from 'cheerio'; import { loadFixture, isWindows } from './test-utils.js'; import testAdapter from './test-adapter.js'; -const describe = isWindows ? global.describe.skip : global.describe; +if (!isWindows) { + describe(); +} describe('Content Collections - render()', () => { describe('Build - SSG', () => { @@ -24,10 +27,10 @@ describe('Content Collections - render()', () => { const $ = cheerio.load(html); // Renders content - expect($('ul li')).to.have.a.lengthOf(3); + assert.equal($('ul li').length, 3); // Includes styles - expect($('link[rel=stylesheet]')).to.have.a.lengthOf(1); + assert.equal($('link[rel=stylesheet]').length, 1); }); it('Excludes CSS for non-rendered entries', async () => { @@ -35,7 +38,7 @@ describe('Content Collections - render()', () => { const $ = cheerio.load(html); // Excludes styles - expect($('link[rel=stylesheet]')).to.have.a.lengthOf(0); + assert.equal($('link[rel=stylesheet]').length, 0); }); it('De-duplicates CSS used both in layout and directly in target page', async () => { @@ -46,13 +49,13 @@ describe('Content Collections - render()', () => { $('link[rel=stylesheet]').each((_, linkEl) => { const href = linkEl.attribs.href; - expect(set).to.not.contain(href); + assert.equal(set.has(href), false); set.add(href); }); $('style').each((_, styleEl) => { const textContent = styleEl.children[0].data; - expect(set).to.not.contain(textContent); + assert.equal(set.has(textContent), false); set.add(textContent); }); }); @@ -62,16 +65,20 @@ describe('Content Collections - render()', () => { const $ = cheerio.load(html); const allScripts = $('head > script[type="module"]'); - expect(allScripts).to.have.length; + assert.ok(allScripts.length); // Includes hoisted script - expect( - [...allScripts].find((script) => $(script).attr('src')?.includes('WithScripts')), + const scriptWithSrc = [...allScripts].find((script) => + $(script).attr('src')?.includes('WithScripts') + ); + assert.notEqual( + scriptWithSrc, + undefined, '`WithScripts.astro` hoisted script missing from head.' - ).to.not.be.undefined; + ); // Includes inline script - expect($('script[data-is-inline]')).to.have.a.lengthOf(1); + assert.equal($('script[data-is-inline]').length, 1); }); it('Excludes component scripts for non-rendered entries', async () => { @@ -81,12 +88,14 @@ describe('Content Collections - render()', () => { const allScripts = $('head > script[type="module"]'); // Excludes hoisted script - expect( - [...allScripts].find((script) => - $(script).text().includes('document.querySelector("#update-me")') - ), + const scriptWithText = [...allScripts].find((script) => + $(script).text().includes('document.querySelector("#update-me")') + ); + assert.equal( + scriptWithText, + undefined, '`WithScripts.astro` hoisted script included unexpectedly.' - ).to.be.undefined; + ); }); it('Applies MDX components export', async () => { @@ -94,8 +103,8 @@ describe('Content Collections - render()', () => { const $ = cheerio.load(html); const h2 = $('h2'); - expect(h2).to.have.a.lengthOf(1); - expect(h2.attr('data-components-export-applied')).to.equal('true'); + assert.equal(h2.length, 1); + assert.equal(h2.attr('data-components-export-applied'), 'true'); }); }); @@ -122,10 +131,10 @@ describe('Content Collections - render()', () => { const $ = cheerio.load(html); // Renders content - expect($('ul li')).to.have.a.lengthOf(3); + assert.equal($('ul li').length, 3); // Includes styles - expect($('link[rel=stylesheet]')).to.have.a.lengthOf(1); + assert.equal($('link[rel=stylesheet]').length, 1); }); it('Exclude CSS for non-rendered entries', async () => { @@ -136,7 +145,7 @@ describe('Content Collections - render()', () => { const $ = cheerio.load(html); // Includes styles - expect($('link[rel=stylesheet]')).to.have.a.lengthOf(0); + assert.equal($('link[rel=stylesheet]').length, 0); }); it('De-duplicates CSS used both in layout and directly in target page', async () => { @@ -150,13 +159,13 @@ describe('Content Collections - render()', () => { $('link[rel=stylesheet]').each((_, linkEl) => { const href = linkEl.attribs.href; - expect(set).to.not.contain(href); + assert.equal(set.has(href), false); set.add(href); }); $('style').each((_, styleEl) => { const textContent = styleEl.children[0].data; - expect(set).to.not.contain(textContent); + assert.equal(set.has(textContent), false); set.add(textContent); }); }); @@ -169,8 +178,8 @@ describe('Content Collections - render()', () => { const $ = cheerio.load(html); const h2 = $('h2'); - expect(h2).to.have.a.lengthOf(1); - expect(h2.attr('data-components-export-applied')).to.equal('true'); + assert.equal(h2.length, 1); + assert.equal(h2.attr('data-components-export-applied'), 'true'); }); it('getCollection should return new instances of the array to be mutated safely', async () => { @@ -180,13 +189,13 @@ describe('Content Collections - render()', () => { let response = await app.render(request); let html = await response.text(); let $ = cheerio.load(html); - expect($('li').first().text()).to.equal('With Layout Prop'); + assert.equal($('li').first().text(), 'With Layout Prop'); request = new Request('http://example.com/'); response = await app.render(request); html = await response.text(); $ = cheerio.load(html); - expect($('li').first().text()).to.equal('Hello world'); + assert.equal($('li').first().text(), 'Hello world'); }); }); @@ -208,68 +217,71 @@ describe('Content Collections - render()', () => { it('Includes CSS for rendered entry', async () => { const response = await fixture.fetch('/launch-week', { method: 'GET' }); - expect(response.status).to.equal(200); + assert.equal(response.status, 200); const html = await response.text(); const $ = cheerio.load(html); // Renders content - expect($('ul li')).to.have.a.lengthOf(3); + assert.equal($('ul li').length, 3); // Includes styles - expect($('head > style')).to.have.a.lengthOf(1); - expect($('head > style').text()).to.include("font-family: 'Comic Sans MS'"); + assert.equal($('head > style').length, 1); + assert.ok($('head > style').text().includes("font-family: 'Comic Sans MS'")); }); it('Includes component scripts for rendered entry', async () => { const response = await fixture.fetch('/launch-week-component-scripts', { method: 'GET' }); - expect(response.status).to.equal(200); + assert.equal(response.status, 200); const html = await response.text(); const $ = cheerio.load(html); const allScripts = $('head > script[src]'); - expect(allScripts).to.have.length; - + assert.ok(allScripts.length); // Includes hoisted script - expect( - [...allScripts].find((script) => script.attribs.src.includes('WithScripts.astro')), + const scriptWithSrc = [...allScripts].find((script) => + script.attribs.src.includes('WithScripts.astro') + ); + assert.notEqual( + scriptWithSrc, + undefined, '`WithScripts.astro` hoisted script missing from head.' - ).to.not.be.undefined; + ); // Includes inline script - expect($('script[data-is-inline]')).to.have.a.lengthOf(1); + assert.equal($('script[data-is-inline]').length, 1); }); it('Applies MDX components export', async () => { const response = await fixture.fetch('/launch-week-components-export', { method: 'GET' }); - expect(response.status).to.equal(200); + assert.equal(response.status, 200); const html = await response.text(); const $ = cheerio.load(html); const h2 = $('h2'); - expect(h2).to.have.a.lengthOf(1); - expect(h2.attr('data-components-export-applied')).to.equal('true'); + assert.equal(h2.length, 1); + assert.equal(h2.attr('data-components-export-applied'), 'true'); }); it('Supports layout prop with recursive getCollection() call', async () => { const response = await fixture.fetch('/with-layout-prop', { method: 'GET' }); - expect(response.status).to.equal(200); + assert.equal(response.status, 200); const html = await response.text(); const $ = cheerio.load(html); const body = $('body'); - expect(body.attr('data-layout-prop')).to.equal('true'); + assert.equal(body.attr('data-layout-prop'), 'true'); const h1 = $('h1'); - expect(h1).to.have.a.lengthOf(1); - expect(h1.text()).to.equal('With Layout Prop'); + assert.equal(h1.length, 1); + assert.equal(h1.text(), 'With Layout Prop'); const h2 = $('h2'); - expect(h2).to.have.a.lengthOf(1); - expect(h2.text()).to.equal('Content with a layout prop'); + assert.equal(h2.length, 1); + assert.equal(h2.text(), 'Content with a layout prop'); }); }); }); diff --git a/packages/astro/test/custom-404-implicit-rerouting.nodetest.js b/packages/astro/test/custom-404-implicit-rerouting.nodetest.js index af52f7296c9b..2c369d4f698a 100644 --- a/packages/astro/test/custom-404-implicit-rerouting.nodetest.js +++ b/packages/astro/test/custom-404-implicit-rerouting.nodetest.js @@ -19,19 +19,31 @@ for (const caseNumber of [1, 2, 3, 4]) { }); // sanity check - it('dev server handles normal requests', async () => { - const resPromise = fixture.fetch('/'); - const result = await withTimeout(resPromise, 1000); - assert.notStrictEqual(result, timeout); - assert.strictEqual(result.status, 200); - }); + it.skip( + 'dev server handles normal requests', + { + todo: 'To re-enabled after we understand why this fails when the test suite is run in parallel', + }, + async () => { + const resPromise = fixture.fetch('/'); + const result = await withTimeout(resPromise, 1000); + assert.notStrictEqual(result, timeout); + assert.strictEqual(result.status, 200); + } + ); - it('dev server stays responsive', async () => { - const resPromise = fixture.fetch('/alvsibdlvjks'); - const result = await withTimeout(resPromise, 1000); - assert.notStrictEqual(result, timeout); - assert.strictEqual(result.status, 404); - }); + it.skip( + 'dev server stays responsive', + { + todo: 'To re-enabled after we understand why this fails when the test suite is run in parallel', + }, + async () => { + const resPromise = fixture.fetch('/alvsibdlvjks'); + const result = await withTimeout(resPromise, 1000); + assert.notStrictEqual(result, timeout); + assert.strictEqual(result.status, 404); + } + ); after(async () => { await devServer.stop(); diff --git a/packages/astro/test/slots-vue.test.js b/packages/astro/test/slots-vue.nodetest.js similarity index 59% rename from packages/astro/test/slots-vue.test.js rename to packages/astro/test/slots-vue.nodetest.js index 2193c7772674..8edee824118c 100644 --- a/packages/astro/test/slots-vue.test.js +++ b/packages/astro/test/slots-vue.nodetest.js @@ -1,4 +1,5 @@ -import { expect } from 'chai'; +import assert from 'node:assert/strict'; +import { before, describe, it } from 'node:test'; import * as cheerio from 'cheerio'; import { loadFixture } from './test-utils.js'; @@ -14,43 +15,43 @@ describe('Slots: Vue', () => { const html = await fixture.readFile('/index.html'); const $ = cheerio.load(html); - expect($('#default-self-closing').text().trim()).to.equal('Fallback'); - expect($('#default-empty').text().trim()).to.equal('Fallback'); - expect($('#zero').text().trim()).to.equal('0'); - expect($('#false').text().trim()).to.equal(''); - expect($('#string').text().trim()).to.equal(''); - expect($('#content').text().trim()).to.equal('Hello world!'); + assert.equal($('#default-self-closing').text().trim(), 'Fallback'); + assert.equal($('#default-empty').text().trim(), 'Fallback'); + assert.equal($('#zero').text().trim(), '0'); + assert.equal($('#false').text().trim(), ''); + assert.equal($('#string').text().trim(), ''); + assert.equal($('#content').text().trim(), 'Hello world!'); }); it('Renders named slot', async () => { const html = await fixture.readFile('/index.html'); const $ = cheerio.load(html); - expect($('#named').text().trim()).to.equal('Fallback / Named'); + assert.equal($('#named').text().trim(), 'Fallback / Named'); }); it('Preserves dash-case slot', async () => { const html = await fixture.readFile('/index.html'); const $ = cheerio.load(html); - expect($('#dash-case').text().trim()).to.equal('Fallback / Dash Case'); + assert.equal($('#dash-case').text().trim(), 'Fallback / Dash Case'); }); describe('For MDX Pages', () => { it('Renders default slot', async () => { const html = await fixture.readFile('/mdx/index.html'); const $ = cheerio.load(html); - expect($('#content').text().trim()).to.equal('Hello world!'); + assert.equal($('#content').text().trim(), 'Hello world!'); }); it('Renders named slot', async () => { const html = await fixture.readFile('/mdx/index.html'); const $ = cheerio.load(html); - expect($('#named').text().trim()).to.equal('Fallback / Named'); + assert.equal($('#named').text().trim(), 'Fallback / Named'); }); it('Converts dash-case slot to camelCase', async () => { const html = await fixture.readFile('/mdx/index.html'); const $ = cheerio.load(html); - expect($('#dash-case').text().trim()).to.equal('Fallback / Dash Case'); + assert.equal($('#dash-case').text().trim(), 'Fallback / Dash Case'); }); }); }); diff --git a/packages/astro/test/ssr-adapter-build-config.test.js b/packages/astro/test/ssr-adapter-build-config.nodetest.js similarity index 91% rename from packages/astro/test/ssr-adapter-build-config.test.js rename to packages/astro/test/ssr-adapter-build-config.nodetest.js index 5d2221c31298..d1566f097d61 100644 --- a/packages/astro/test/ssr-adapter-build-config.test.js +++ b/packages/astro/test/ssr-adapter-build-config.nodetest.js @@ -1,4 +1,5 @@ -import { expect } from 'chai'; +import assert from 'node:assert/strict'; +import { describe, before, it } from 'node:test'; import { loadFixture } from './test-utils.js'; import { viteID } from '../dist/core/util.js'; @@ -58,11 +59,11 @@ describe('Integration buildConfig hook', () => { it('Puts client files in the client folder', async () => { let data = await fixture.readFile('/.root/client/cars.json'); - expect(data).to.not.be.undefined; + assert.notEqual(data, undefined); }); it('Puts the server entry into the server folder', async () => { let data = await fixture.readFile('/.root/server/entry.mjs'); - expect(data).to.not.be.undefined; + assert.notEqual(data, undefined); }); }); diff --git a/packages/astro/test/ssr-api-route.test.js b/packages/astro/test/ssr-api-route.nodetest.js similarity index 77% rename from packages/astro/test/ssr-api-route.test.js rename to packages/astro/test/ssr-api-route.nodetest.js index d6ea4ac842c0..d5fefb17a0e5 100644 --- a/packages/astro/test/ssr-api-route.test.js +++ b/packages/astro/test/ssr-api-route.nodetest.js @@ -1,4 +1,5 @@ -import { expect } from 'chai'; +import assert from 'node:assert/strict'; +import { after, describe, before, it } from 'node:test'; import net from 'node:net'; import testAdapter from './test-adapter.js'; import { loadFixture } from './test-utils.js'; @@ -21,32 +22,32 @@ describe('API routes in SSR', () => { const request = new Request('http://example.com/'); const response = await app.render(request); const html = await response.text(); - expect(html).to.not.be.empty; + assert.notEqual(html, ''); }); it('Can load the API route too', async () => { const app = await fixture.loadTestAdapterApp(); const request = new Request('http://example.com/food.json'); const response = await app.render(request); - expect(response.status).to.equal(200); + assert.equal(response.status, 200); const body = await response.json(); - expect(body.length).to.equal(3); + assert.equal(body.length, 3); }); it('Has valid api context', async () => { const app = await fixture.loadTestAdapterApp(); const request = new Request('http://example.com/context/any'); const response = await app.render(request); - expect(response.status).to.equal(200); + assert.equal(response.status, 200); const data = await response.json(); - expect(data.cookiesExist).to.equal(true); - expect(data.requestExist).to.equal(true); - expect(data.redirectExist).to.equal(true); - expect(data.propsExist).to.equal(true); - expect(data.params).to.deep.equal({ param: 'any' }); - expect(data.generator).to.match(/^Astro v/); - expect(data.url).to.equal('http://example.com/context/any'); - expect(data.clientAddress).to.equal('0.0.0.0'); + assert.equal(data.cookiesExist, true); + assert.equal(data.requestExist, true); + assert.equal(data.redirectExist, true); + assert.equal(data.propsExist, true); + assert.deepEqual(data.params, { param: 'any' }); + assert.match(data.generator, /^Astro v/); + assert.equal(data.url, 'http://example.com/context/any'); + assert.equal(data.clientAddress, '0.0.0.0'); }); describe('API Routes - Dev', () => { @@ -64,9 +65,9 @@ describe('API routes in SSR', () => { method: 'POST', body: `some data`, }); - expect(response.status).to.equal(200); + assert.equal(response.status, 200); const text = await response.text(); - expect(text).to.equal(`ok`); + assert.equal(text, 'ok'); }); it('Can be passed binary data from multipart formdata', async () => { @@ -82,7 +83,7 @@ describe('API routes in SSR', () => { body: formData, }); - expect(res.status).to.equal(200); + assert.equal(res.status, 200); }); it('Can set multiple headers of the same type', async () => { @@ -113,7 +114,7 @@ describe('API routes in SSR', () => { count++; } - expect(count).to.equal(2, 'Found two seperate set-cookie response headers'); + assert.equal(count, 2, 'Found two seperate set-cookie response headers'); }); }); }); diff --git a/packages/astro/test/ssr-assets.test.js b/packages/astro/test/ssr-assets.nodetest.js similarity index 78% rename from packages/astro/test/ssr-assets.test.js rename to packages/astro/test/ssr-assets.nodetest.js index 01015f087753..9d900babe4a8 100644 --- a/packages/astro/test/ssr-assets.test.js +++ b/packages/astro/test/ssr-assets.nodetest.js @@ -1,4 +1,5 @@ -import { expect } from 'chai'; +import assert from 'node:assert/strict'; +import { describe, before, it } from 'node:test'; import { loadFixture } from './test-utils.js'; import testAdapter from './test-adapter.js'; @@ -21,7 +22,7 @@ describe('SSR Assets', () => { const app = await fixture.loadTestAdapterApp(); /** @type {Set} */ const assets = app.manifest.assets; - expect(assets.size).to.equal(1); - expect(Array.from(assets)[0].endsWith('.css')).to.be.true; + assert.equal(assets.size, 1); + assert.equal(Array.from(assets)[0].endsWith('.css'), true); }); }); diff --git a/packages/astro/test/ssr-dynamic.test.js b/packages/astro/test/ssr-dynamic.nodetest.js similarity index 88% rename from packages/astro/test/ssr-dynamic.test.js rename to packages/astro/test/ssr-dynamic.nodetest.js index f867ff999d71..36cf0aceddff 100644 --- a/packages/astro/test/ssr-dynamic.test.js +++ b/packages/astro/test/ssr-dynamic.nodetest.js @@ -1,4 +1,5 @@ -import { expect } from 'chai'; +import assert from 'node:assert/strict'; +import { describe, before, it } from 'node:test'; import { load as cheerioLoad } from 'cheerio'; import { loadFixture } from './test-utils.js'; import testAdapter from './test-adapter.js'; @@ -56,27 +57,27 @@ describe('Dynamic pages in SSR', () => { it('Do not have to implement getStaticPaths', async () => { const html = await fetchHTML('/123'); const $ = cheerioLoad(html); - expect($('h1').text()).to.equal('Item 123'); + assert.equal($('h1').text(), 'Item 123'); }); it('Includes page styles', async () => { const html = await fetchHTML('/123'); const $ = cheerioLoad(html); - expect($('link').length).to.equal(1); + assert.equal($('link').length, 1); }); it('Dynamic API routes work', async () => { const json = await fetchJSON('/api/products/33'); - expect(json.id).to.equal('33'); + assert.equal(json.id, '33'); }); it('Injected route work', async () => { const json = await fetchJSON('/path-alias/33'); - expect(json.id).to.equal('33'); + assert.equal(json.id, '33'); }); it('Public assets take priority', async () => { const favicon = await matchRoute('/favicon.ico'); - expect(favicon).to.equal(undefined); + assert.equal(favicon, undefined); }); }); diff --git a/packages/astro/test/ssr-env.test.js b/packages/astro/test/ssr-env.nodetest.js similarity index 83% rename from packages/astro/test/ssr-env.test.js rename to packages/astro/test/ssr-env.nodetest.js index fb369482dff1..619495f3f017 100644 --- a/packages/astro/test/ssr-env.test.js +++ b/packages/astro/test/ssr-env.nodetest.js @@ -1,4 +1,5 @@ -import { expect } from 'chai'; +import assert from 'node:assert/strict'; +import { describe, before, it } from 'node:test'; import * as cheerio from 'cheerio'; import { loadFixture } from './test-utils.js'; import testAdapter from './test-adapter.js'; @@ -22,6 +23,6 @@ describe('SSR Environment Variables', () => { const response = await app.render(request); const html = await response.text(); const $ = cheerio.load(html); - expect($('#ssr').text()).to.equal('true'); + assert.equal($('#ssr').text(), 'true'); }); }); diff --git a/packages/astro/test/ssr-hoisted-script.test.js b/packages/astro/test/ssr-hoisted-script.nodetest.js similarity index 88% rename from packages/astro/test/ssr-hoisted-script.test.js rename to packages/astro/test/ssr-hoisted-script.nodetest.js index bebb766fbd69..271b19b940b8 100644 --- a/packages/astro/test/ssr-hoisted-script.test.js +++ b/packages/astro/test/ssr-hoisted-script.nodetest.js @@ -1,4 +1,5 @@ -import { expect } from 'chai'; +import assert from 'node:assert/strict'; +import { after, describe, before, it } from 'node:test'; import { load as cheerioLoad } from 'cheerio'; import { loadFixture } from './test-utils.js'; import testAdapter from './test-adapter.js'; @@ -31,7 +32,7 @@ describe('Hoisted inline scripts in SSR', () => { it('scripts get included', async () => { const html = await fetchHTML(fixture, '/'); const $ = cheerioLoad(html); - expect($('script').length).to.equal(1); + assert.equal($('script').length, 1); }); }); @@ -49,7 +50,7 @@ describe('Hoisted inline scripts in SSR', () => { it('Inlined scripts get included without base path in the script', async () => { const html = await fetchHTML(fixture, '/hello/'); const $ = cheerioLoad(html); - expect($('script').html()).to.equal('console.log("hello world");\n'); + assert.equal($('script').html(), 'console.log("hello world");\n'); }); }); }); @@ -74,7 +75,7 @@ describe('Hoisted external scripts in SSR', () => { it('script has correct path', async () => { const html = await fetchHTML(fixture, '/'); const $ = cheerioLoad(html); - expect($('script').attr('src')).to.match(/^\/_astro\/hoisted\..{8}\.js$/); + assert.match($('script').attr('src'), /^\/_astro\/hoisted\..{8}\.js$/); }); }); @@ -95,7 +96,7 @@ describe('Hoisted external scripts in SSR', () => { it('script has correct path', async () => { const html = await fetchHTML(fixture, '/hello/'); const $ = cheerioLoad(html); - expect($('script').attr('src')).to.match(/^\/hello\/_astro\/hoisted\..{8}\.js$/); + assert.match($('script').attr('src'), /^\/hello\/_astro\/hoisted\..{8}\.js$/); }); }); @@ -118,7 +119,8 @@ describe('Hoisted external scripts in SSR', () => { it('script has correct path', async () => { const html = await fetchHTML(fixture, '/'); const $ = cheerioLoad(html); - expect($('script').attr('src')).to.match( + assert.match( + $('script').attr('src'), /^https:\/\/cdn\.example\.com\/_astro\/hoisted\..{8}\.js$/ ); }); @@ -147,7 +149,7 @@ describe('Hoisted external scripts in SSR', () => { it('script has correct path', async () => { const html = await fetchHTML(fixture, '/'); const $ = cheerioLoad(html); - expect($('script').attr('src')).to.match(/^\/assets\/entry\..{8}\.mjs$/); + assert.match($('script').attr('src'), /^\/assets\/entry\..{8}\.mjs$/); }); }); @@ -175,7 +177,7 @@ describe('Hoisted external scripts in SSR', () => { it('script has correct path', async () => { const html = await fetchHTML(fixture, '/hello/'); const $ = cheerioLoad(html); - expect($('script').attr('src')).to.match(/^\/hello\/assets\/entry\..{8}\.mjs$/); + assert.match($('script').attr('src'), /^\/hello\/assets\/entry\..{8}\.mjs$/); }); }); @@ -205,7 +207,8 @@ describe('Hoisted external scripts in SSR', () => { it('script has correct path', async () => { const html = await fetchHTML(fixture, '/'); const $ = cheerioLoad(html); - expect($('script').attr('src')).to.match( + assert.match( + $('script').attr('src'), /^https:\/\/cdn\.example\.com\/assets\/entry\..{8}\.mjs$/ ); }); diff --git a/packages/astro/test/ssr-large-array.test.js b/packages/astro/test/ssr-large-array.nodetest.js similarity index 70% rename from packages/astro/test/ssr-large-array.test.js rename to packages/astro/test/ssr-large-array.nodetest.js index 0145a2fe4591..c004660e9c4b 100644 --- a/packages/astro/test/ssr-large-array.test.js +++ b/packages/astro/test/ssr-large-array.nodetest.js @@ -1,4 +1,5 @@ -import { expect } from 'chai'; +import assert from 'node:assert/strict'; +import { describe, before, it } from 'node:test'; import * as cheerio from 'cheerio'; import { loadFixture } from './test-utils.js'; import testAdapter from './test-adapter.js'; @@ -24,10 +25,10 @@ describe('SSR with Large Array and client rendering', () => { const html = new TextDecoder().decode(data); const $ = cheerio.load(html); - expect($('head meta[name="viewport"]')).to.have.a.lengthOf(1); - expect($('head link[rel="icon"]')).to.have.a.lengthOf(1); - expect($('main')).to.have.a.lengthOf(1); - expect($('astro-island')).to.have.a.lengthOf(1); - expect($('h1').text()).to.equal('Hello, Solid!'); + assert.equal($('head meta[name="viewport"]').length, 1); + assert.equal($('head link[rel="icon"]').length, 1); + assert.equal($('main').length, 1); + assert.equal($('astro-island').length, 1); + assert.equal($('h1').text(), 'Hello, Solid!'); }); }); diff --git a/packages/astro/test/ssr-lit.test.js b/packages/astro/test/ssr-lit.nodetest.js similarity index 84% rename from packages/astro/test/ssr-lit.test.js rename to packages/astro/test/ssr-lit.nodetest.js index 6615e644402c..edcc0b9b070c 100644 --- a/packages/astro/test/ssr-lit.test.js +++ b/packages/astro/test/ssr-lit.nodetest.js @@ -1,4 +1,5 @@ -import { expect } from 'chai'; +import assert from 'node:assert/strict'; +import { describe, before, it } from 'node:test'; import { load as cheerioLoad } from 'cheerio'; import { loadFixture } from './test-utils.js'; import testAdapter from './test-adapter.js'; @@ -27,6 +28,6 @@ describe('Lit integration in SSR', () => { it('Is able to load', async () => { const html = await fetchHTML('/'); const $ = cheerioLoad(html); - expect($('#str').text()).to.equal('initialized'); + assert.equal($('#str').text(), 'initialized'); }); }); diff --git a/packages/astro/test/ssr-locals.test.js b/packages/astro/test/ssr-locals.nodetest.js similarity index 83% rename from packages/astro/test/ssr-locals.test.js rename to packages/astro/test/ssr-locals.nodetest.js index 68e628990859..2f0fa8d3564b 100644 --- a/packages/astro/test/ssr-locals.test.js +++ b/packages/astro/test/ssr-locals.nodetest.js @@ -1,4 +1,5 @@ -import { expect } from 'chai'; +import assert from 'node:assert/strict'; +import { describe, before, it } from 'node:test'; import * as cheerio from 'cheerio'; import { loadFixture } from './test-utils.js'; import testAdapter from './test-adapter.js'; @@ -24,7 +25,7 @@ describe('SSR Astro.locals from server', () => { const html = await response.text(); const $ = cheerio.load(html); - expect($('#foo').text()).to.equal('bar'); + assert.equal($('#foo').text(), 'bar'); }); it('Can access Astro.locals in api context', async () => { @@ -32,9 +33,9 @@ describe('SSR Astro.locals from server', () => { const request = new Request('http://example.com/api'); const locals = { foo: 'bar' }; const response = await app.render(request, undefined, locals); - expect(response.status).to.equal(200); + assert.equal(response.status, 200); const body = await response.json(); - expect(body.foo).to.equal('bar'); + assert.equal(body.foo, 'bar'); }); }); diff --git a/packages/astro/test/ssr-manifest.test.js b/packages/astro/test/ssr-manifest.nodetest.js similarity index 76% rename from packages/astro/test/ssr-manifest.test.js rename to packages/astro/test/ssr-manifest.nodetest.js index 02feed6b3993..0a499b6b585f 100644 --- a/packages/astro/test/ssr-manifest.test.js +++ b/packages/astro/test/ssr-manifest.nodetest.js @@ -1,4 +1,5 @@ -import { expect } from 'chai'; +import assert from 'node:assert/strict'; +import { describe, before, it } from 'node:test'; import { loadFixture } from './test-utils.js'; import testAdapter from './test-adapter.js'; import * as cheerio from 'cheerio'; @@ -25,12 +26,12 @@ describe('astro:ssr-manifest', () => { const html = await response.text(); const $ = cheerio.load(html); - expect($('#assets').text()).to.match(/\["\/_astro\/index.([\w-]{8})\.css"\]/); + assert.match($('#assets').text(), /\["\/_astro\/index.([\w-]{8})\.css"\]/); }); it('includes compressHTML', async () => { const app = await fixture.loadTestAdapterApp(); - expect(app.manifest).to.haveOwnProperty('compressHTML'); - expect(app.manifest.compressHTML).to.be.true; + assert.equal(app.manifest.compressHTML, true); + assert.equal(app.manifest.compressHTML, true); }); }); diff --git a/packages/astro/test/ssr-params.test.js b/packages/astro/test/ssr-params.nodetest.js similarity index 77% rename from packages/astro/test/ssr-params.test.js rename to packages/astro/test/ssr-params.nodetest.js index b15955a9faf4..df050f9e7616 100644 --- a/packages/astro/test/ssr-params.test.js +++ b/packages/astro/test/ssr-params.nodetest.js @@ -1,10 +1,11 @@ -import { expect } from 'chai'; +import assert from 'node:assert/strict'; +import { describe, before, it } from 'node:test'; import * as cheerio from 'cheerio'; import { loadFixture } from './test-utils.js'; import testAdapter from './test-adapter.js'; describe('Astro.params in SSR', () => { - /** @type {import('./test-utils').Fixture} */ + /** @type {import('./test-utils.js').Fixture} */ let fixture; before(async () => { @@ -21,10 +22,10 @@ describe('Astro.params in SSR', () => { const app = await fixture.loadTestAdapterApp(); const request = new Request('http://example.com/users/houston/food'); const response = await app.render(request); - expect(response.status).to.equal(200); + assert.equal(response.status, 200); const html = await response.text(); const $ = cheerio.load(html); - expect($('.category').text()).to.equal('food'); + assert.equal($('.category').text(), 'food'); }); describe('Non-english characters in the URL', () => { @@ -32,10 +33,10 @@ describe('Astro.params in SSR', () => { const app = await fixture.loadTestAdapterApp(); const request = new Request('http://example.com/users/houston/東西/food'); const response = await app.render(request); - expect(response.status).to.equal(200); + assert.equal(response.status, 200); const html = await response.text(); const $ = cheerio.load(html); - expect($('.category').text()).to.equal('food'); + assert.equal($('.category').text(), 'food'); }); }); @@ -43,9 +44,9 @@ describe('Astro.params in SSR', () => { const app = await fixture.loadTestAdapterApp(); const request = new Request('http://example.com/users/houston/%25'); const response = await app.render(request); - expect(response.status).to.equal(200); + assert.equal(response.status, 200); const html = await response.text(); const $ = cheerio.load(html); - expect($('.category').text()).to.equal('%'); + assert.equal($('.category').text(), '%'); }); }); diff --git a/packages/astro/test/ssr-partytown.test.js b/packages/astro/test/ssr-partytown.nodetest.js similarity index 68% rename from packages/astro/test/ssr-partytown.test.js rename to packages/astro/test/ssr-partytown.nodetest.js index 4be8456aa3b5..04e7abc23799 100644 --- a/packages/astro/test/ssr-partytown.test.js +++ b/packages/astro/test/ssr-partytown.nodetest.js @@ -1,4 +1,5 @@ -import { expect } from 'chai'; +import assert from 'node:assert/strict'; +import { describe, before, it } from 'node:test'; import { load as cheerioLoad } from 'cheerio'; import { loadFixture } from './test-utils.js'; import testAdapter from './test-adapter.js'; @@ -22,11 +23,20 @@ describe('Using the Partytown integration in SSR', () => { const response = await app.render(request); const html = await response.text(); const $ = cheerioLoad(html); - expect($('script')).to.have.a.lengthOf(1); + assert.equal($('script').length, 1); }); it('The partytown scripts are in the manifest', async () => { const app = await fixture.loadTestAdapterApp(); - expect(app.manifest.assets).to.contain('/~partytown/partytown-sw.js'); + const partytownScript = '/~partytown/partytown-sw.js'; + const assets = app.manifest.assets; + let found = false; + for (const asset of assets) { + if (asset === partytownScript) { + found = true; + break; + } + } + assert.equal(found, true); }); }); diff --git a/packages/astro/test/ssr-prerender-get-static-paths.test.js b/packages/astro/test/ssr-prerender-get-static-paths.nodetest.js similarity index 83% rename from packages/astro/test/ssr-prerender-get-static-paths.test.js rename to packages/astro/test/ssr-prerender-get-static-paths.nodetest.js index 3fe2950cb83d..9a76c62a5350 100644 --- a/packages/astro/test/ssr-prerender-get-static-paths.test.js +++ b/packages/astro/test/ssr-prerender-get-static-paths.nodetest.js @@ -1,4 +1,5 @@ -import { expect } from 'chai'; +import assert from 'node:assert/strict'; +import { after, afterEach, describe, before, it } from 'node:test'; import * as cheerio from 'cheerio'; import testAdapter from './test-adapter.js'; import { loadFixture } from './test-utils.js'; @@ -30,15 +31,15 @@ describe('Prerender', () => { it('is only called once during build', () => { // useless expect; if build() throws in setup then this test fails - expect(true).to.equal(true); + assert.equal(true, true); }); it('Astro.url sets the current pathname', async () => { const html = await fixture.readFile('/client/food/tacos/index.html'); const $ = cheerio.load(html); - expect($('#props').text()).to.equal('10'); - expect($('#url').text()).to.equal('/blog/food/tacos/'); + assert.equal($('#props').text(), '10'); + assert.equal($('#url').text(), '/blog/food/tacos/'); }); }); @@ -62,42 +63,43 @@ describe('Prerender', () => { it('only calls prerender getStaticPaths once', async function () { // Sometimes this fail in CI as the chokidar watcher triggers an update and invalidates the route cache, // causing getStaticPaths to be called twice. Workaround this with 2 retries for now. - this.retries(2); + // it was used in the original test using chai, but it's not available in the current version of node:test + // this.retries(2); let res = await fixture.fetch('/blog/a'); - expect(res.status).to.equal(200); + assert.equal(res.status, 200); res = await fixture.fetch('/blog/b'); - expect(res.status).to.equal(200); + assert.equal(res.status, 200); res = await fixture.fetch('/blog/c'); - expect(res.status).to.equal(200); + assert.equal(res.status, 200); }); describe('404 behavior', () => { it('resolves 200 on matching static path - named params', async () => { const res = await fixture.fetch('/blog/pizza/provolone-sausage'); - expect(res.status).to.equal(200); + assert.equal(res.status, 200); }); it('resolves 404 on pattern match without static path - named params', async () => { const res = await fixture.fetch('/blog/pizza/provolone-pineapple'); const html = await res.text(); - expect(res.status).to.equal(404); - expect(html).to.match(/404/); + assert.equal(res.status, 404); + assert.match(html, /404/); }); it('resolves 200 on matching static path - rest params', async () => { const res = await fixture.fetch('/blog/pizza/grimaldis/new-york'); - expect(res.status).to.equal(200); + assert.equal(res.status, 200); }); it('resolves 404 on pattern match without static path - rest params', async () => { const res = await fixture.fetch('/blog/pizza/pizza-hut'); const html = await res.text(); - expect(res.status).to.equal(404); - expect(html).to.match(/404/); + assert.equal(res.status, 404); + assert.match(html, /404/); }); }); @@ -105,13 +107,13 @@ describe('Prerender', () => { it('resolves 200 on matching static path - string params', async () => { // route provided with { params: { year: "2022", slug: "post-2" }} const res = await fixture.fetch('/blog/blog/2022/post-1'); - expect(res.status).to.equal(200); + assert.equal(res.status, 200); }); it('resolves 200 on matching static path - numeric params', async () => { // route provided with { params: { year: 2022, slug: "post-2" }} const res = await fixture.fetch('/blog/blog/2022/post-2'); - expect(res.status).to.equal(200); + assert.equal(res.status, 200); }); }); @@ -119,13 +121,14 @@ describe('Prerender', () => { // routes params provided for pages /posts/1, /posts/2, and /posts/3 for (const page of [1, 2, 3]) { let res = await fixture.fetch(`/blog/posts/${page}`); - expect(res.status).to.equal(200); + assert.equal(res.status, 200); const html = await res.text(); const $ = cheerio.load(html); const canonical = $('link[rel=canonical]'); - expect(canonical.attr('href')).to.equal( + assert.equal( + canonical.attr('href'), `https://mysite.dev/blog/posts/${page}`, `doesn't trim the /${page} route param` ); @@ -161,15 +164,15 @@ describe('Prerender', () => { it('is only called once during build', () => { // useless expect; if build() throws in setup then this test fails - expect(true).to.equal(true); + assert.equal(true, true); }); it('Astro.url sets the current pathname', async () => { const html = await fixture.readFile('/client/food/tacos/index.html'); const $ = cheerio.load(html); - expect($('#props').text()).to.equal('10'); - expect($('#url').text()).to.equal('/blog/food/tacos/'); + assert.equal($('#props').text(), '10'); + assert.equal($('#url').text(), '/blog/food/tacos/'); }); }); @@ -192,39 +195,39 @@ describe('Prerender', () => { it('only calls hybrid getStaticPaths once', async () => { let res = await fixture.fetch('/blog/a'); - expect(res.status).to.equal(200); + assert.equal(res.status, 200); res = await fixture.fetch('/blog/b'); - expect(res.status).to.equal(200); + assert.equal(res.status, 200); res = await fixture.fetch('/blog/c'); - expect(res.status).to.equal(200); + assert.equal(res.status, 200); }); describe('404 behavior', () => { it('resolves 200 on matching static path - named params', async () => { const res = await fixture.fetch('/blog/pizza/provolone-sausage'); - expect(res.status).to.equal(200); + assert.equal(res.status, 200); }); it('resolves 404 on pattern match without static path - named params', async () => { const res = await fixture.fetch('/blog/pizza/provolone-pineapple'); const html = await res.text(); - expect(res.status).to.equal(404); - expect(html).to.match(/404/); + assert.equal(res.status, 404); + assert.match(html, /404/); }); it('resolves 200 on matching static path - rest params', async () => { const res = await fixture.fetch('/blog/pizza/grimaldis/new-york'); - expect(res.status).to.equal(200); + assert.equal(res.status, 200); }); it('resolves 404 on pattern match without static path - rest params', async () => { const res = await fixture.fetch('/blog/pizza/pizza-hut'); const html = await res.text(); - expect(res.status).to.equal(404); - expect(html).to.match(/404/); + assert.equal(res.status, 404); + assert.match(html, /404/); }); }); @@ -232,13 +235,13 @@ describe('Prerender', () => { it('resolves 200 on matching static path - string params', async () => { // route provided with { params: { year: "2022", slug: "post-2" }} const res = await fixture.fetch('/blog/blog/2022/post-1'); - expect(res.status).to.equal(200); + assert.equal(res.status, 200); }); it('resolves 200 on matching static path - numeric params', async () => { // route provided with { params: { year: 2022, slug: "post-2" }} const res = await fixture.fetch('/blog/blog/2022/post-2'); - expect(res.status).to.equal(200); + assert.equal(res.status, 200); }); }); @@ -246,13 +249,14 @@ describe('Prerender', () => { // routes params provided for pages /posts/1, /posts/2, and /posts/3 for (const page of [1, 2, 3]) { let res = await fixture.fetch(`/blog/posts/${page}`); - expect(res.status).to.equal(200); + assert.equal(res.status, 200); const html = await res.text(); const $ = cheerio.load(html); const canonical = $('link[rel=canonical]'); - expect(canonical.attr('href')).to.equal( + assert.equal( + canonical.attr('href'), `https://mysite.dev/blog/posts/${page}`, `doesn't trim the /${page} route param` ); diff --git a/packages/astro/test/ssr-prerender.test.js b/packages/astro/test/ssr-prerender.nodetest.js similarity index 87% rename from packages/astro/test/ssr-prerender.test.js rename to packages/astro/test/ssr-prerender.nodetest.js index 567371f0bbaa..98678d681df7 100644 --- a/packages/astro/test/ssr-prerender.test.js +++ b/packages/astro/test/ssr-prerender.nodetest.js @@ -1,4 +1,5 @@ -import { expect } from 'chai'; +import assert from 'node:assert/strict'; +import { describe, before, it } from 'node:test'; import * as cheerio from 'cheerio'; import { loadFixture } from './test-utils.js'; import testAdapter from './test-adapter.js'; @@ -23,14 +24,14 @@ describe('SSR: prerender', () => { const app = await fixture.loadTestAdapterApp(); const request = new Request('http://example.com/static'); const response = await app.render(request); - expect(response.status).to.equal(404); + assert.equal(response.status, 404); }); it('includes prerendered pages in the asset manifest', async () => { const app = await fixture.loadTestAdapterApp(); /** @type {Set} */ const assets = app.manifest.assets; - expect(assets).to.contain('/static/index.html'); + assert.equal(assets.has('/static/index.html'), true); }); }); @@ -39,10 +40,10 @@ describe('SSR: prerender', () => { const app = await fixture.loadTestAdapterApp(); const request = new Request('http://example.com/users/houston'); const response = await app.render(request); - expect(response.status).to.equal(200); + assert.equal(response.status, 200); const html = await response.text(); const $ = cheerio.load(html); - expect($('.user').text()).to.equal('houston'); + assert.equal($('.user').text(), 'houston'); }); }); @@ -52,10 +53,10 @@ describe('SSR: prerender', () => { const app = await fixture.loadTestAdapterApp(); const request = new Request('http://example.com/some'); const response = await app.render(request); - expect(response.status).to.equal(200); + assert.equal(response.status, 200); const html = await response.text(); const $ = cheerio.load(html); - expect($('p').text()).to.include('not give 404'); + assert.equal($('p').text().includes('not give 404'), true); }); }); }); @@ -94,13 +95,13 @@ describe('Integrations can hook into the prerendering decision', () => { const app = await fixture.loadTestAdapterApp(); const request = new Request('http://example.com/static'); const response = await app.render(request); - expect(response.status).to.equal(200); + assert.equal(response.status, 200); }); it('An integration can turn a normal page to a prerendered one', async () => { const app = await fixture.loadTestAdapterApp(); const request = new Request('http://example.com/not-prerendered'); const response = await app.render(request); - expect(response.status).to.equal(404); + assert.equal(response.status, 404); }); }); diff --git a/packages/astro/test/ssr-request.test.js b/packages/astro/test/ssr-request.nodetest.js similarity index 75% rename from packages/astro/test/ssr-request.test.js rename to packages/astro/test/ssr-request.nodetest.js index 7bdce20b557c..4569fe291f53 100644 --- a/packages/astro/test/ssr-request.test.js +++ b/packages/astro/test/ssr-request.nodetest.js @@ -1,4 +1,5 @@ -import { expect } from 'chai'; +import assert from 'node:assert/strict'; +import { describe, before, it } from 'node:test'; import { load as cheerioLoad } from 'cheerio'; import { loadFixture } from './test-utils.js'; import testAdapter from './test-adapter.js'; @@ -36,66 +37,65 @@ describe('Using Astro.request in SSR', () => { const app = await fixture.loadTestAdapterApp(); const request = new Request('http://example.com/subpath/request'); const response = await app.render(request); - expect(response.status).to.equal(200); + assert.equal(response.status, 200); const html = await response.text(); const $ = cheerioLoad(html); - expect($('#origin').text()).to.equal('http://example.com'); + assert.equal($('#origin').text(), 'http://example.com'); }); it('Duplicate slashes are collapsed', async () => { const app = await fixture.loadTestAdapterApp(); const request = new Request('http://example.com/subpath////request/////'); const response = await app.render(request); - expect(response.status).to.equal(200); + assert.equal(response.status, 200); const html = await response.text(); const $ = cheerioLoad(html); - expect($('#origin').text()).to.equal('http://example.com'); - expect($('#pathname').text()).to.equal('/subpath/request/'); - expect($('#request-pathname').text()).to.equal('/subpath/request/'); + assert.equal($('#origin').text(), 'http://example.com'); + assert.equal($('#pathname').text(), '/subpath/request/'); + assert.equal($('#request-pathname').text(), '/subpath/request/'); }); it('public file is copied over', async () => { const json = await fixture.readFile('/client/cars.json'); - expect(json).to.not.be.undefined; + assert.notEqual(json, undefined); }); it('CSS assets have their base prefix', async () => { const app = await fixture.loadTestAdapterApp(); let request = new Request('http://example.com/subpath/request'); let response = await app.render(request); - expect(response.status).to.equal(200); + assert.equal(response.status, 200); const html = await response.text(); const $ = cheerioLoad(html); const linkHref = $('link').attr('href'); - expect(linkHref.startsWith('/subpath/')).to.equal(true); + assert.equal(linkHref.startsWith('/subpath/'), true); request = new Request('http://example.com' + linkHref); response = await app.render(request); - expect(response.status).to.equal(200); + assert.equal(response.status, 200); const css = await response.text(); - expect(css).to.not.be.an('undefined'); + assert.notEqual(css, undefined); }); it('script assets have their base prefix', async () => { const app = await fixture.loadTestAdapterApp(); let request = new Request('http://example.com/subpath/request'); let response = await app.render(request); - expect(response.status).to.equal(200); + assert.equal(response.status, 200); const html = await response.text(); const $ = cheerioLoad(html); for (const el of $('script')) { const scriptSrc = $(el).attr('src'); - expect(scriptSrc.startsWith('/subpath/')).to.equal(true); - + assert.equal(scriptSrc.startsWith('/subpath/'), true); request = new Request('http://example.com' + scriptSrc); response = await app.render(request); - expect(response.status).to.equal(200); + assert.equal(response.status, 200); const js = await response.text(); - expect(js).to.not.be.an('undefined'); + assert.notEqual(js, undefined); } }); @@ -103,8 +103,8 @@ describe('Using Astro.request in SSR', () => { const app = await fixture.loadTestAdapterApp(); const request = new Request('http://example.com/subpath/cars.json'); const response = await app.render(request); - expect(response.status).to.equal(200); + assert.equal(response.status, 200); const data = await response.json(); - expect(data).to.be.an('array'); + assert.equal(data instanceof Array, true); }); }); diff --git a/packages/astro/test/ssr-response.test.js b/packages/astro/test/ssr-response.nodetest.js similarity index 76% rename from packages/astro/test/ssr-response.test.js rename to packages/astro/test/ssr-response.nodetest.js index 0be4b86ef86a..703ee76967fa 100644 --- a/packages/astro/test/ssr-response.test.js +++ b/packages/astro/test/ssr-response.nodetest.js @@ -1,4 +1,5 @@ -import { expect } from 'chai'; +import assert from 'node:assert/strict'; +import { describe, before, it } from 'node:test'; import { loadFixture } from './test-utils.js'; import testAdapter from './test-adapter.js'; @@ -19,14 +20,14 @@ describe('Using Astro.response in SSR', () => { const app = await fixture.loadTestAdapterApp(); const request = new Request('http://example.com/status-code'); const response = await app.render(request); - expect(response.status).to.equal(404); + assert.equal(response.status, 404); }); it('Can set the statusText', async () => { const app = await fixture.loadTestAdapterApp(); const request = new Request('http://example.com/status-code'); const response = await app.render(request); - expect(response.statusText).to.equal('Oops'); + assert.equal(response.statusText, 'Oops'); }); it('Can set headers for 404 page', async () => { @@ -34,7 +35,7 @@ describe('Using Astro.response in SSR', () => { const request = new Request('http://example.com/status-code'); const response = await app.render(request); const headers = response.headers; - expect(headers.get('one-two')).to.equal('three'); + assert.equal(headers.get('one-two'), 'three'); }); it('Can add headers', async () => { @@ -42,8 +43,8 @@ describe('Using Astro.response in SSR', () => { const request = new Request('http://example.com/some-header'); const response = await app.render(request); const headers = response.headers; - expect(headers.get('one-two')).to.equal('three'); - expect(headers.get('four-five')).to.equal('six'); - expect(headers.get('Cache-Control')).to.equal(`max-age=0, s-maxage=86400`); + assert.equal(headers.get('one-two'), 'three'); + assert.equal(headers.get('four-five'), 'six'); + assert.equal(headers.get('Cache-Control'), `max-age=0, s-maxage=86400`); }); }); diff --git a/packages/astro/test/ssr-scripts.test.js b/packages/astro/test/ssr-scripts.nodetest.js similarity index 83% rename from packages/astro/test/ssr-scripts.test.js rename to packages/astro/test/ssr-scripts.nodetest.js index 241ec894bce5..f1a213ea6f76 100644 --- a/packages/astro/test/ssr-scripts.test.js +++ b/packages/astro/test/ssr-scripts.nodetest.js @@ -1,4 +1,5 @@ -import { expect } from 'chai'; +import assert from 'node:assert/strict'; +import { describe, before, it } from 'node:test'; import { loadFixture } from './test-utils.js'; import testAdapter from './test-adapter.js'; @@ -20,6 +21,6 @@ describe('SSR Hydrated component scripts', () => { /** @type {Set} */ const assets = app.manifest.assets; - expect(assets.size).to.be.greaterThan(0); + assert.ok(assets.size > 0); }); }); diff --git a/packages/astro/test/ssr-split-manifest.test.js b/packages/astro/test/ssr-split-manifest.nodetest.js similarity index 88% rename from packages/astro/test/ssr-split-manifest.test.js rename to packages/astro/test/ssr-split-manifest.nodetest.js index 74d2fe74e574..04cb1219ac68 100644 --- a/packages/astro/test/ssr-split-manifest.test.js +++ b/packages/astro/test/ssr-split-manifest.nodetest.js @@ -1,4 +1,5 @@ -import { expect } from 'chai'; +import assert from 'node:assert/strict'; +import { describe, before, it } from 'node:test'; import { loadFixture } from './test-utils.js'; import testAdapter from './test-adapter.js'; import * as cheerio from 'cheerio'; @@ -45,17 +46,18 @@ describe('astro:ssr-manifest, split', () => { const html = await response.text(); const $ = cheerio.load(html); - expect($('#assets').text()).to.match( + assert.match( + $('#assets').text(), /\["\/_astro\/index\.([\w-]{8})\.css","\/prerender\/index\.html"\]/ ); }); it('should give access to entry points that exists on file system', async () => { // number of the pages inside src/ - expect(entryPoints.size).to.equal(6); + assert.equal(entryPoints.size, 6); for (const fileUrl of entryPoints.values()) { let filePath = fileURLToPath(fileUrl); - expect(existsSync(filePath)).to.be.true; + assert.equal(existsSync(filePath), true); } }); @@ -66,7 +68,7 @@ describe('astro:ssr-manifest, split', () => { encoding: 'utf8', } ); - expect(text.includes('Pre render me')).to.be.true; + assert.equal(text.includes('Pre render me'), true); }); it('should emit an entry point to request the pre-rendered page', async () => { @@ -75,7 +77,7 @@ describe('astro:ssr-manifest, split', () => { const request = new Request('http://example.com/'); const response = await app.render(request); const html = await response.text(); - expect(html.includes('Pre render me')).to.be.true; + assert.equal(html.includes('Pre render me'), true); }); describe('when function per route is enabled', async () => { @@ -109,7 +111,7 @@ describe('astro:ssr-manifest, split', () => { const request = new Request('http://example.com/'); const response = await app.render(request); const html = await response.text(); - expect(html.includes('Testing')).to.be.true; + assert.equal(html.includes('Testing'), true); }); }); }); diff --git a/packages/astro/test/units/app/headers.test.js b/packages/astro/test/units/app/headers.nodetest.js similarity index 79% rename from packages/astro/test/units/app/headers.test.js rename to packages/astro/test/units/app/headers.nodetest.js index d9e5d6f8e455..e8ae33f53a1b 100644 --- a/packages/astro/test/units/app/headers.test.js +++ b/packages/astro/test/units/app/headers.nodetest.js @@ -1,29 +1,29 @@ -import { expect } from 'chai'; - +import { describe, it } from 'node:test'; +import * as assert from 'node:assert/strict'; import { createOutgoingHttpHeaders } from '../../../dist/core/app/createOutgoingHttpHeaders.js'; describe('createOutgoingHttpHeaders', () => { it('undefined input headers', async () => { const result = createOutgoingHttpHeaders(undefined); - expect(result).to.equal(undefined); + assert.equal(result, undefined); }); it('null input headers', async () => { const result = createOutgoingHttpHeaders(undefined); - expect(result).to.equal(undefined); + assert.equal(result, undefined); }); it('Empty Headers', async () => { const headers = new Headers(); const result = createOutgoingHttpHeaders(headers); - expect(result).to.equal(undefined); + assert.equal(result, undefined); }); it('Headers with single key', async () => { const headers = new Headers(); headers.append('x-test', 'hello world'); const result = createOutgoingHttpHeaders(headers); - expect(result).to.deep.equal({ 'x-test': 'hello world' }); + assert.deepEqual(result, { 'x-test': 'hello world' }); }); it('Headers with multiple keys', async () => { @@ -31,7 +31,7 @@ describe('createOutgoingHttpHeaders', () => { headers.append('x-test1', 'hello'); headers.append('x-test2', 'world'); const result = createOutgoingHttpHeaders(headers); - expect(result).to.deep.equal({ 'x-test1': 'hello', 'x-test2': 'world' }); + assert.deepEqual(result, { 'x-test1': 'hello', 'x-test2': 'world' }); }); it('Headers with multiple values (not set-cookie)', async () => { @@ -39,7 +39,7 @@ describe('createOutgoingHttpHeaders', () => { headers.append('x-test', 'hello'); headers.append('x-test', 'world'); const result = createOutgoingHttpHeaders(headers); - expect(result).to.deep.equal({ 'x-test': 'hello, world' }); + assert.deepEqual(result, { 'x-test': 'hello, world' }); }); it('Headers with multiple values (set-cookie special case)', async () => { @@ -47,7 +47,7 @@ describe('createOutgoingHttpHeaders', () => { headers.append('set-cookie', 'hello'); headers.append('set-cookie', 'world'); const result = createOutgoingHttpHeaders(headers); - expect(result).to.deep.equal({ 'set-cookie': ['hello', 'world'] }); + assert.deepEqual(result, { 'set-cookie': ['hello', 'world'] }); }); it('Headers with multiple values (set-cookie case handling)', async () => { @@ -55,7 +55,7 @@ describe('createOutgoingHttpHeaders', () => { headers.append('Set-cookie', 'hello'); headers.append('Set-Cookie', 'world'); const result = createOutgoingHttpHeaders(headers); - expect(result).to.deep.equal({ 'set-cookie': ['hello', 'world'] }); + assert.deepEqual(result, { 'set-cookie': ['hello', 'world'] }); }); it('Headers with all use cases', async () => { @@ -67,7 +67,7 @@ describe('createOutgoingHttpHeaders', () => { headers.append('Set-cookie', 'hello'); headers.append('Set-Cookie', 'world'); const result = createOutgoingHttpHeaders(headers); - expect(result).to.deep.equal({ + assert.deepEqual(result, { 'x-single': 'single', 'x-triple': 'one, two, three', 'set-cookie': ['hello', 'world'], diff --git a/packages/astro/test/units/assets/remote-pattern.nodetest.js b/packages/astro/test/units/assets/remote-pattern.nodetest.js new file mode 100644 index 000000000000..316b81860098 --- /dev/null +++ b/packages/astro/test/units/assets/remote-pattern.nodetest.js @@ -0,0 +1,116 @@ +import { describe, it } from 'node:test'; +import * as assert from 'node:assert/strict'; +import { + matchProtocol, + matchPort, + matchHostname, + matchPathname, + matchPattern, +} from '../../../dist/assets/utils/remotePattern.js'; + +describe('astro/src/assets/utils/remotePattern', () => { + const url1 = new URL('https://docs.astro.build/en/getting-started'); + const url2 = new URL('http://preview.docs.astro.build:8080/'); + const url3 = new URL('https://astro.build/'); + const url4 = new URL('https://example.co/'); + + describe('remote pattern matchers', () => { + it('matches protocol', async () => { + // undefined + assert.equal(matchProtocol(url1), true); + + // defined, true/false + assert.equal(matchProtocol(url1, 'http'), false); + assert.equal(matchProtocol(url1, 'https'), true); + }); + + it('matches port', async () => { + // undefined + assert.equal(matchPort(url1), true); + + // defined, but port is empty (default port used in URL) + assert.equal(matchPort(url1, ''), true); + + // defined and port is custom + assert.equal(matchPort(url2, '8080'), true); + }); + + it('matches hostname (no wildcards)', async () => { + // undefined + assert.equal(matchHostname(url1), true); + + // defined, true/false + assert.equal(matchHostname(url1, 'astro.build'), false); + assert.equal(matchHostname(url1, 'docs.astro.build'), true); + }); + + it('matches hostname (with wildcards)', async () => { + // defined, true/false + assert.equal(matchHostname(url1, 'docs.astro.build', true), true); + assert.equal(matchHostname(url1, '**.astro.build', true), true); + assert.equal(matchHostname(url1, '*.astro.build', true), true); + + assert.equal(matchHostname(url2, '*.astro.build', true), false); + assert.equal(matchHostname(url2, '**.astro.build', true), true); + + assert.equal(matchHostname(url3, 'astro.build', true), true); + assert.equal(matchHostname(url3, '*.astro.build', true), false); + assert.equal(matchHostname(url3, '**.astro.build', true), false); + }); + + it('matches pathname (no wildcards)', async () => { + // undefined + assert.equal(matchPathname(url1), true); + + // defined, true/false + assert.equal(matchPathname(url1, '/'), false); + assert.equal(matchPathname(url1, '/en/getting-started'), true); + }); + + it('matches pathname (with wildcards)', async () => { + // defined, true/false + assert.equal(matchPathname(url1, '/en/**', true), true); + assert.equal(matchPathname(url1, '/en/*', true), true); + assert.equal(matchPathname(url1, '/**', true), true); + + assert.equal(matchPathname(url2, '/**', true), false); + assert.equal(matchPathname(url2, '/*', true), false); + }); + + it('matches patterns', async () => { + assert.equal(matchPattern(url1, {}), true); + + assert.equal( + matchPattern(url1, { + protocol: 'https', + }), + true + ); + + assert.equal( + matchPattern(url1, { + protocol: 'https', + hostname: '**.astro.build', + }), + true + ); + + assert.equal( + matchPattern(url1, { + protocol: 'https', + hostname: '**.astro.build', + pathname: '/en/**', + }), + true + ); + + assert.equal( + matchPattern(url4, { + protocol: 'https', + hostname: 'example.com', + }), + false + ); + }); + }); +}); diff --git a/packages/astro/test/units/assets/remote-pattern.test.js b/packages/astro/test/units/assets/remote-pattern.test.js deleted file mode 100644 index 62a411e3a659..000000000000 --- a/packages/astro/test/units/assets/remote-pattern.test.js +++ /dev/null @@ -1,111 +0,0 @@ -import { expect } from 'chai'; -import { - matchProtocol, - matchPort, - matchHostname, - matchPathname, - matchPattern, -} from '../../../dist/assets/utils/remotePattern.js'; - -describe('astro/src/assets/utils/remotePattern', () => { - const url1 = new URL('https://docs.astro.build/en/getting-started'); - const url2 = new URL('http://preview.docs.astro.build:8080/'); - const url3 = new URL('https://astro.build/'); - const url4 = new URL('https://example.co/'); - - describe('remote pattern matchers', () => { - it('matches protocol', async () => { - // undefined - expect(matchProtocol(url1)).to.be.true; - - // defined, true/false - expect(matchProtocol(url1, 'http')).to.be.false; - expect(matchProtocol(url1, 'https')).to.be.true; - }); - - it('matches port', async () => { - // undefined - expect(matchPort(url1)).to.be.true; - - // defined, but port is empty (default port used in URL) - expect(matchPort(url1, '')).to.be.true; - - // defined and port is custom - expect(matchPort(url2, '8080')).to.be.true; - }); - - it('matches hostname (no wildcards)', async () => { - // undefined - expect(matchHostname(url1)).to.be.true; - - // defined, true/false - expect(matchHostname(url1, 'astro.build')).to.be.false; - expect(matchHostname(url1, 'docs.astro.build')).to.be.true; - }); - - it('matches hostname (with wildcards)', async () => { - // defined, true/false - expect(matchHostname(url1, 'docs.astro.build', true)).to.be.true; - expect(matchHostname(url1, '**.astro.build', true)).to.be.true; - expect(matchHostname(url1, '*.astro.build', true)).to.be.true; - - expect(matchHostname(url2, '*.astro.build', true)).to.be.false; - expect(matchHostname(url2, '**.astro.build', true)).to.be.true; - - expect(matchHostname(url3, 'astro.build', true)).to.be.true; - expect(matchHostname(url3, '*.astro.build', true)).to.be.false; - expect(matchHostname(url3, '**.astro.build', true)).to.be.false; - }); - - it('matches pathname (no wildcards)', async () => { - // undefined - expect(matchPathname(url1)).to.be.true; - - // defined, true/false - expect(matchPathname(url1, '/')).to.be.false; - expect(matchPathname(url1, '/en/getting-started')).to.be.true; - }); - - it('matches pathname (with wildcards)', async () => { - // defined, true/false - expect(matchPathname(url1, '/en/**', true)).to.be.true; - expect(matchPathname(url1, '/en/*', true)).to.be.true; - expect(matchPathname(url1, '/**', true)).to.be.true; - - expect(matchPathname(url2, '/**', true)).to.be.false; - expect(matchPathname(url2, '/*', true)).to.be.false; - }); - - it('matches patterns', async () => { - expect(matchPattern(url1, {})).to.be.true; - - expect( - matchPattern(url1, { - protocol: 'https', - }) - ).to.be.true; - - expect( - matchPattern(url1, { - protocol: 'https', - hostname: '**.astro.build', - }) - ).to.be.true; - - expect( - matchPattern(url1, { - protocol: 'https', - hostname: '**.astro.build', - pathname: '/en/**', - }) - ).to.be.true; - - expect( - matchPattern(url4, { - protocol: 'https', - hostname: 'example.com', - }) - ).to.be.false; - }); - }); -}); diff --git a/packages/astro/test/units/build/static-build.test.js b/packages/astro/test/units/build/static-build.nodetest.js similarity index 88% rename from packages/astro/test/units/build/static-build.test.js rename to packages/astro/test/units/build/static-build.nodetest.js index 38896c5aaaf9..acc3395df3f2 100644 --- a/packages/astro/test/units/build/static-build.test.js +++ b/packages/astro/test/units/build/static-build.nodetest.js @@ -1,4 +1,5 @@ -import { expect } from 'chai'; +import { describe, it } from 'node:test'; +import * as assert from 'node:assert/strict'; import { makeAstroPageEntryPointFileName } from '../../../dist/core/build/static-build.js'; describe('astro/src/core/build', () => { @@ -30,21 +31,21 @@ describe('astro/src/core/build', () => { const input = '@astro-page:src/pages/index@_@astro'; const output = 'pages/index.astro.mjs'; const result = makeAstroPageEntryPointFileName('@astro-page:', input, routes); - expect(result).to.equal(output); + assert.equal(result, output); }); it('handles dynamic pages', async () => { const input = '@astro-page:src/pages/blog/[year]/[...slug]@_@astro'; const output = 'pages/blog/_year_/_---slug_.astro.mjs'; const result = makeAstroPageEntryPointFileName('@astro-page:', input, routes); - expect(result).to.equal(output); + assert.equal(result, output); }); it('handles node_modules pages', async () => { const input = '@astro-page:../node_modules/my-dep/injected@_@astro'; const output = 'pages/injected.astro.mjs'; const result = makeAstroPageEntryPointFileName('@astro-page:', input, routes); - expect(result).to.equal(output); + assert.equal(result, output); }); // Fix #7561 @@ -52,7 +53,7 @@ describe('astro/src/core/build', () => { const input = '@astro-page:../../packages/demo/[...all]@_@astro'; const output = 'pages/injected-workspace.astro.mjs'; const result = makeAstroPageEntryPointFileName('@astro-page:', input, routes); - expect(result).to.equal(output); + assert.equal(result, output); }); }); }); diff --git a/packages/astro/test/units/compile/invalid-css.test.js b/packages/astro/test/units/compile/invalid-css.nodetest.js similarity index 80% rename from packages/astro/test/units/compile/invalid-css.test.js rename to packages/astro/test/units/compile/invalid-css.nodetest.js index 794e335b42c4..b43fb8ff657e 100644 --- a/packages/astro/test/units/compile/invalid-css.test.js +++ b/packages/astro/test/units/compile/invalid-css.nodetest.js @@ -1,5 +1,6 @@ import { resolveConfig } from 'vite'; -import { expect } from 'chai'; +import { describe, it } from 'node:test'; +import * as assert from 'node:assert/strict'; import { compile } from '../../../dist/core/compile/index.js'; import { AggregateError } from '../../../dist/core/errors/index.js'; import { pathToFileURL } from 'node:url'; @@ -35,8 +36,8 @@ describe('astro/src/core/compile', () => { error = err; } - expect(error).to.be.an.instanceOf(AggregateError); - expect(error.errors[0].message).to.contain('expected ")"'); + assert.equal(error instanceof AggregateError, true); + assert.equal(error.errors[0].message.includes('expected ")"'), true); }); }); }); diff --git a/packages/astro/test/units/dev/base.test.js b/packages/astro/test/units/dev/base.nodetest.js similarity index 91% rename from packages/astro/test/units/dev/base.test.js rename to packages/astro/test/units/dev/base.nodetest.js index 041d6bcb52be..a3006163b230 100644 --- a/packages/astro/test/units/dev/base.test.js +++ b/packages/astro/test/units/dev/base.nodetest.js @@ -1,4 +1,5 @@ -import { expect } from 'chai'; +import { describe, it } from 'node:test'; +import * as assert from 'node:assert/strict'; import { fileURLToPath } from 'node:url'; import { createFs, createRequestAndResponse, runInContainer } from '../test-utils.js'; @@ -31,7 +32,7 @@ describe('base configuration', () => { }); container.handle(req, res); await done; - expect(res.statusCode).to.equal(404); + assert.equal(res.statusCode, 404); } ); }); @@ -60,7 +61,7 @@ describe('base configuration', () => { }); container.handle(req, res); await done; - expect(res.statusCode).to.equal(200); + assert.equal(res.statusCode, 200); } ); }); @@ -91,7 +92,7 @@ describe('base configuration', () => { }); container.handle(req, res); await done; - expect(res.statusCode).to.equal(404); + assert.equal(res.statusCode, 404); } ); }); @@ -120,7 +121,7 @@ describe('base configuration', () => { }); container.handle(req, res); await done; - expect(res.statusCode).to.equal(200); + assert.equal(res.statusCode, 200); } ); }); diff --git a/packages/astro/test/units/dev/collections-mixed-content-errors.test.js b/packages/astro/test/units/dev/collections-mixed-content-errors.nodetest.js similarity index 92% rename from packages/astro/test/units/dev/collections-mixed-content-errors.test.js rename to packages/astro/test/units/dev/collections-mixed-content-errors.nodetest.js index 9cad4f5e8a31..26ea1334d01e 100644 --- a/packages/astro/test/units/dev/collections-mixed-content-errors.test.js +++ b/packages/astro/test/units/dev/collections-mixed-content-errors.nodetest.js @@ -1,4 +1,5 @@ -import { expect } from 'chai'; +import { describe, it } from 'node:test'; +import * as assert from 'node:assert/strict'; import { fileURLToPath } from 'node:url'; import _sync from '../../../dist/core/sync/index.js'; import { createFsWithFallback } from '../test-utils.js'; @@ -35,7 +36,7 @@ name: Ben root ); - expect(await sync({ fs })).to.equal(1); + assert.equal(await sync({ fs }), 1); }); it('raises "mixed content" error when data in content collection', async () => { @@ -63,7 +64,7 @@ title: Post root ); - expect(await sync({ fs })).to.equal(1); + assert.equal(await sync({ fs }), 1); }); it('raises error when data collection configured as content collection', async () => { @@ -86,7 +87,7 @@ title: Post root ); - expect(await sync({ fs })).to.equal(1); + assert.equal(await sync({ fs }), 1); }); it('does not raise error for empty collection with config', async () => { @@ -111,7 +112,7 @@ title: Post try { const res = await sync({ fs }); - expect(res).to.equal(0); + assert.equal(res, 0); } catch (e) { expect.fail(0, 1, `Did not expect sync to throw: ${e.message}`); } diff --git a/packages/astro/test/units/dev/collections-renderentry.test.js b/packages/astro/test/units/dev/collections-renderentry.nodetest.js similarity index 92% rename from packages/astro/test/units/dev/collections-renderentry.test.js rename to packages/astro/test/units/dev/collections-renderentry.nodetest.js index 873bb91646c7..cf36740270b4 100644 --- a/packages/astro/test/units/dev/collections-renderentry.test.js +++ b/packages/astro/test/units/dev/collections-renderentry.nodetest.js @@ -1,4 +1,5 @@ -import { expect } from 'chai'; +import { describe, it } from 'node:test'; +import * as assert from 'node:assert/strict'; import * as cheerio from 'cheerio'; import os from 'node:os'; import { fileURLToPath } from 'node:url'; @@ -8,7 +9,7 @@ import { createFsWithFallback, createRequestAndResponse, runInContainer } from ' const root = new URL('../../fixtures/content/', import.meta.url); -const describe = os.platform() === 'win32' ? global.describe.skip : global.describe; +const _describe = os.platform() === 'win32' ? describe.skip : describe; /** @type {typeof runInContainer} */ async function runInContainerWithContentListeners(params, callback) { @@ -18,7 +19,7 @@ async function runInContainerWithContentListeners(params, callback) { }); } -describe('Content Collections - render()', () => { +_describe('Content Collections - render()', () => { it('can be called in a page component', async () => { const fs = createFsWithFallback( { @@ -72,10 +73,10 @@ describe('Content Collections - render()', () => { const $ = cheerio.load(html); // Rendered the content - expect($('ul li')).to.have.a.lengthOf(3); + assert.equal($('ul li').length, 3); // Rendered the styles - expect($('style')).to.have.a.lengthOf(1); + assert.equal($('style').length, 1); } ); }); @@ -144,10 +145,10 @@ description: Astro is launching this week! const $ = cheerio.load(html); // Rendered the content - expect($('ul li')).to.have.a.lengthOf(3); + assert.equal($('ul li').length, 3); // Rendered the styles - expect($('style')).to.have.a.lengthOf(1); + assert.equal($('style').length, 1); } ); }); @@ -214,10 +215,10 @@ description: Astro is launching this week! const $ = cheerio.load(html); // Rendered the content - expect($('ul li')).to.have.a.lengthOf(3); + assert.equal($('ul li').length, 3); // Rendered the styles - expect($('style')).to.have.a.lengthOf(1); + assert.equal($('style').length, 1); } ); }); @@ -283,10 +284,10 @@ description: Astro is launching this week! const $ = cheerio.load(html); // Rendered the content - expect($('ul li')).to.have.a.lengthOf(3); + assert.equal($('ul li').length, 3); // Rendered the styles - expect($('style')).to.have.a.lengthOf(1); + assert.equal($('style').length, 1); } ); }); diff --git a/packages/astro/test/units/dev/dev.test.js b/packages/astro/test/units/dev/dev.nodetest.js similarity index 88% rename from packages/astro/test/units/dev/dev.test.js rename to packages/astro/test/units/dev/dev.nodetest.js index 9b713d62a77d..b89e18feb312 100644 --- a/packages/astro/test/units/dev/dev.test.js +++ b/packages/astro/test/units/dev/dev.nodetest.js @@ -1,4 +1,5 @@ -import { expect } from 'chai'; +import { describe, it } from 'node:test'; +import * as assert from 'node:assert/strict'; import * as cheerio from 'cheerio'; import { fileURLToPath } from 'node:url'; import { @@ -37,8 +38,8 @@ describe('dev container', () => { container.handle(req, res); const html = await text(); const $ = cheerio.load(html); - expect(res.statusCode).to.equal(200); - expect($('h1')).to.have.a.lengthOf(1); + assert.equal(res.statusCode, 200); + assert.equal($('h1').length, 1); }); }); @@ -72,7 +73,7 @@ describe('dev container', () => { container.handle(r.req, r.res); let html = await r.text(); let $ = cheerio.load(html); - expect($('body.one')).to.have.a.lengthOf(1); + assert.equal($('body.one').length, 1); fs.writeFileFromRootSync( '/src/components/Header.astro', @@ -106,8 +107,8 @@ describe('dev container', () => { container.handle(r.req, r.res); html = await r.text(); $ = cheerio.load(html); - expect($('body.one')).to.have.a.lengthOf(0); - expect($('body.two')).to.have.a.lengthOf(1); + assert.equal($('body.one').length, 0); + assert.equal($('body.two').length, 1); }); }); @@ -148,7 +149,7 @@ describe('dev container', () => { }); container.handle(r.req, r.res); await r.done; - expect(r.res.statusCode).to.equal(200); + assert.equal(r.res.statusCode, 200); // Try with the injected route r = createRequestAndResponse({ @@ -157,7 +158,7 @@ describe('dev container', () => { }); container.handle(r.req, r.res); await r.done; - expect(r.res.statusCode).to.equal(200); + assert.equal(r.res.statusCode, 200); } ); }); @@ -199,8 +200,8 @@ describe('dev container', () => { container.handle(r.req, r.res); await r.done; const doc = await r.text(); - expect(doc).to.match(/Regular page/); - expect(r.res.statusCode).to.equal(200); + assert.equal(/Regular page/.test(doc), true); + assert.equal(r.res.statusCode, 200); } { // `/404` serves the custom 404 page as expected. @@ -208,8 +209,8 @@ describe('dev container', () => { container.handle(r.req, r.res); await r.done; const doc = await r.text(); - expect(doc).to.match(/Custom 404/); - expect(r.res.statusCode).to.equal(404); + assert.equal(/Custom 404/.test(doc), true); + assert.equal(r.res.statusCode, 404); } { // A non-existent page also serves the custom 404 page. @@ -217,8 +218,8 @@ describe('dev container', () => { container.handle(r.req, r.res); await r.done; const doc = await r.text(); - expect(doc).to.match(/Custom 404/); - expect(r.res.statusCode).to.equal(404); + assert.equal(/Custom 404/.test(doc), true); + assert.equal(r.res.statusCode, 404); } } ); @@ -242,7 +243,7 @@ describe('dev container', () => { container.handle(r.req, r.res); await r.done; - expect(r.res.statusCode).to.equal(200); + assert.equal(r.res.statusCode, 200); // Next try the root path r = createRequestAndResponse({ @@ -253,7 +254,7 @@ describe('dev container', () => { container.handle(r.req, r.res); await r.done; - expect(r.res.statusCode).to.equal(404); + assert.equal(r.res.statusCode, 404); } ); }); @@ -269,7 +270,7 @@ describe('dev container', () => { container.handle(r.req, r.res); await r.done; - expect(r.res.statusCode).to.equal(200); + assert.equal(r.res.statusCode, 200); }); }); }); diff --git a/packages/astro/test/units/dev/head-injection.test.js b/packages/astro/test/units/dev/head-injection.nodetest.js similarity index 92% rename from packages/astro/test/units/dev/head-injection.test.js rename to packages/astro/test/units/dev/head-injection.nodetest.js index 9b38feae6267..837fc45b9644 100644 --- a/packages/astro/test/units/dev/head-injection.test.js +++ b/packages/astro/test/units/dev/head-injection.nodetest.js @@ -1,4 +1,5 @@ -import { expect } from 'chai'; +import { describe, it } from 'node:test'; +import * as assert from 'node:assert/strict'; import * as cheerio from 'cheerio'; import { fileURLToPath } from 'node:url'; import { createFs, createRequestAndResponse, runInContainer } from '../test-utils.js'; @@ -79,8 +80,8 @@ describe('head injection', () => { const html = await text(); const $ = cheerio.load(html); - expect($('link[rel=stylesheet][href="/some/fake/styles.css"]')).to.have.a.lengthOf(1); - expect($('#other')).to.have.a.lengthOf(1); + assert.equal($('link[rel=stylesheet][href="/some/fake/styles.css"]').length, 1); + assert.equal($('#other').length, 1); } ); }); @@ -179,11 +180,12 @@ describe('head injection', () => { const html = await text(); const $ = cheerio.load(html); - expect($('link[rel=stylesheet][href="/some/fake/styles.css"]')).to.have.a.lengthOf( + assert.equal( + $('link[rel=stylesheet][href="/some/fake/styles.css"]').length, 1, 'found inner link' ); - expect($('#other')).to.have.a.lengthOf(1, 'Found the #other div'); + assert.equal($('#other').length, 1, 'Found the #other div'); } ); }); diff --git a/packages/astro/test/units/dev/hydration.test.js b/packages/astro/test/units/dev/hydration.nodetest.js similarity index 89% rename from packages/astro/test/units/dev/hydration.test.js rename to packages/astro/test/units/dev/hydration.nodetest.js index ae4cb2d994f1..4507f0c84bbb 100644 --- a/packages/astro/test/units/dev/hydration.test.js +++ b/packages/astro/test/units/dev/hydration.nodetest.js @@ -1,4 +1,5 @@ -import { expect } from 'chai'; +import { describe, it } from 'node:test'; +import * as assert from 'node:assert/strict'; import { fileURLToPath } from 'node:url'; import { createFs, createRequestAndResponse, runInContainer } from '../test-utils.js'; @@ -41,7 +42,8 @@ describe('hydration', () => { }); container.handle(req, res); await done; - expect(res.statusCode).to.equal( + assert.equal( + res.statusCode, 200, "We get a 200 because the error occurs in the template, but we didn't crash!" ); diff --git a/packages/astro/test/units/dev/restart.test.js b/packages/astro/test/units/dev/restart.nodetest.js similarity index 88% rename from packages/astro/test/units/dev/restart.test.js rename to packages/astro/test/units/dev/restart.nodetest.js index 1b00d5c6a825..0fad93de4b9b 100644 --- a/packages/astro/test/units/dev/restart.test.js +++ b/packages/astro/test/units/dev/restart.nodetest.js @@ -1,4 +1,5 @@ -import { expect } from 'chai'; +import { describe, it } from 'node:test'; +import * as assert from 'node:assert/strict'; import * as cheerio from 'cheerio'; import { fileURLToPath } from 'node:url'; @@ -46,8 +47,8 @@ describe('dev container restarts', () => { restart.container.handle(r.req, r.res); let html = await r.text(); const $ = cheerio.load(html); - expect(r.res.statusCode).to.equal(200); - expect($('h1')).to.have.a.lengthOf(1); + assert.equal(r.res.statusCode, 200); + assert.equal($('h1').length, 1); // Create an error let restartComplete = restart.restarted(); @@ -61,7 +62,7 @@ describe('dev container restarts', () => { // Wait for the restart to finish let hmrError = await restartComplete; - expect(hmrError).to.not.be.a('undefined'); + assert.notEqual(typeof hmrError, 'undefined'); // Do it a second time to make sure we are still watching @@ -75,7 +76,7 @@ describe('dev container restarts', () => { ); hmrError = await restartComplete; - expect(hmrError).to.not.be.a('undefined'); + assert.notEqual(typeof hmrError, 'undefined'); } finally { await restart.container.close(); } @@ -102,7 +103,7 @@ describe('dev container restarts', () => { inlineConfig: { root: fileURLToPath(root), logLevel: 'silent' }, }); await startContainer(restart.container); - expect(isStarted(restart.container)).to.equal(true); + assert.equal(isStarted(restart.container), true); try { // Trigger a change @@ -110,7 +111,7 @@ describe('dev container restarts', () => { triggerFSEvent(restart.container, fs, '/astro.config.mjs', 'change'); await restartComplete; - expect(isStarted(restart.container)).to.equal(true); + assert.equal(isStarted(restart.container), true); } finally { await restart.container.close(); } @@ -131,7 +132,7 @@ describe('dev container restarts', () => { inlineConfig: { root: fileURLToPath(root), logLevel: 'silent' }, }); await startContainer(restart.container); - expect(isStarted(restart.container)).to.equal(true); + assert.equal(isStarted(restart.container), true); try { // Trigger a change @@ -139,7 +140,7 @@ describe('dev container restarts', () => { triggerFSEvent(restart.container, fs, '/astro.config.ts', 'change'); await restartComplete; - expect(isStarted(restart.container)).to.equal(true); + assert.equal(isStarted(restart.container), true); } finally { await restart.container.close(); } @@ -158,7 +159,7 @@ describe('dev container restarts', () => { inlineConfig: { root: fileURLToPath(root), logLevel: 'silent' }, }); await startContainer(restart.container); - expect(isStarted(restart.container)).to.equal(true); + assert.equal(isStarted(restart.container), true); try { let restartComplete = restart.restarted(); @@ -183,7 +184,7 @@ describe('dev container restarts', () => { inlineConfig: { root: fileURLToPath(root), logLevel: 'silent' }, }); await startContainer(restart.container); - expect(isStarted(restart.container)).to.equal(true); + assert.equal(isStarted(restart.container), true); try { let restartComplete = restart.restarted(); diff --git a/packages/astro/test/units/dev/styles.test.js b/packages/astro/test/units/dev/styles.nodetest.js similarity index 94% rename from packages/astro/test/units/dev/styles.test.js rename to packages/astro/test/units/dev/styles.nodetest.js index 526b8fbef9f8..a1ab6b94264a 100644 --- a/packages/astro/test/units/dev/styles.test.js +++ b/packages/astro/test/units/dev/styles.nodetest.js @@ -1,5 +1,5 @@ -import { expect } from 'chai'; - +import { describe, it, before } from 'node:test'; +import * as assert from 'node:assert/strict'; import { getStylesForURL } from '../../../dist/vite-plugin-astro-server/css.js'; import { viteID } from '../../../dist/core/util.js'; @@ -76,6 +76,6 @@ describe('Crawling graph for CSS', () => { // In dev mode, HMR modules tracked are added to importedModules. We use `importers` // to verify that they are true importers. const res = await getStylesForURL(new URL('./src/pages/index.astro', root), loader); - expect(res.styles.length).to.equal(1); + assert.equal(res.styles.length, 1); }); }); diff --git a/packages/astro/test/units/i18n/astro_i18n.test.js b/packages/astro/test/units/i18n/astro_i18n.nodetest.js similarity index 75% rename from packages/astro/test/units/i18n/astro_i18n.test.js rename to packages/astro/test/units/i18n/astro_i18n.nodetest.js index 1e0d0475c975..56be06194b0b 100644 --- a/packages/astro/test/units/i18n/astro_i18n.test.js +++ b/packages/astro/test/units/i18n/astro_i18n.nodetest.js @@ -5,8 +5,11 @@ import { getLocaleAbsoluteUrlList, } from '../../../dist/i18n/index.js'; import { parseLocale } from '../../../dist/core/render/context.js'; -import { expect } from 'chai'; +import { describe, it } from 'node:test'; +import * as assert from 'node:assert/strict'; import { validateConfig } from '../../../dist/core/config/config.js'; +import { AstroError } from '#astro/core/errors/index'; +import { MissingLocale } from '#astro/core/errors/errors-data'; describe('getLocaleRelativeUrl', () => { it('should correctly return the URL with the base', () => { @@ -33,74 +36,59 @@ describe('getLocaleRelativeUrl', () => { }; // directory format - expect( + assert.equal( getLocaleRelativeUrl({ locale: 'en', base: '/blog/', trailingSlash: 'always', format: 'directory', ...config.experimental.i18n, - }) - ).to.eq('/blog/'); - expect( + }), + '/blog/' + ); + assert.equal( getLocaleRelativeUrl({ locale: 'es', base: '/blog/', ...config.experimental.i18n, trailingSlash: 'always', format: 'directory', - }) - ).to.eq('/blog/es/'); - - expect( - getLocaleRelativeUrl({ - locale: 'en_US', - base: '/blog/', - ...config.experimental.i18n, - trailingSlash: 'always', - format: 'directory', - }) - ).to.throw; + }), + '/blog/es/' + ); // file format - expect( + assert.equal( getLocaleRelativeUrl({ locale: 'en', base: '/blog/', ...config.experimental.i18n, trailingSlash: 'always', format: 'file', - }) - ).to.eq('/blog/'); - expect( + }), + '/blog/' + ); + assert.equal( getLocaleRelativeUrl({ locale: 'es', base: '/blog/', ...config.experimental.i18n, trailingSlash: 'always', format: 'file', - }) - ).to.eq('/blog/es/'); - - expect( - getLocaleRelativeUrl({ - locale: 'en_US', - base: '/blog/', - ...config.experimental.i18n, - trailingSlash: 'always', - format: 'file', - }) - ).to.throw; + }), + '/blog/es/' + ); - expect( + assert.equal( getLocaleRelativeUrl({ locale: 'it-VA', base: '/blog/', ...config.experimental.i18n, trailingSlash: 'always', format: 'file', - }) - ).to.eq('/blog/italiano/'); + }), + '/blog/italiano/' + ); }); it('should correctly return the URL without base', () => { @@ -117,24 +105,26 @@ describe('getLocaleRelativeUrl', () => { }, }; - expect( + assert.equal( getLocaleRelativeUrl({ locale: 'en', base: '/', ...config.experimental.i18n, trailingSlash: 'always', format: 'directory', - }) - ).to.eq('/'); - expect( + }), + '/' + ); + assert.equal( getLocaleRelativeUrl({ locale: 'es', base: '/', ...config.experimental.i18n, trailingSlash: 'always', format: 'directory', - }) - ).to.eq('/es/'); + }), + '/es/' + ); }); it('should correctly handle the trailing slash', () => { @@ -156,66 +146,72 @@ describe('getLocaleRelativeUrl', () => { }, }; // directory format - expect( + assert.equal( getLocaleRelativeUrl({ locale: 'en', base: '/blog', ...config.i18n, trailingSlash: 'never', format: 'directory', - }) - ).to.eq('/blog'); - expect( + }), + '/blog' + ); + assert.equal( getLocaleRelativeUrl({ locale: 'es', base: '/blog/', ...config.i18n, trailingSlash: 'always', format: 'directory', - }) - ).to.eq('/blog/es/'); + }), + '/blog/es/' + ); - expect( + assert.equal( getLocaleRelativeUrl({ locale: 'it-VA', base: '/blog/', ...config.i18n, trailingSlash: 'always', format: 'file', - }) - ).to.eq('/blog/italiano/'); + }), + '/blog/italiano/' + ); - expect( + assert.equal( getLocaleRelativeUrl({ locale: 'en', base: '/blog/', ...config.i18n, trailingSlash: 'ignore', format: 'directory', - }) - ).to.eq('/blog/'); + }), + '/blog/' + ); // directory file - expect( + assert.equal( getLocaleRelativeUrl({ locale: 'en', base: '/blog', ...config.i18n, trailingSlash: 'never', format: 'file', - }) - ).to.eq('/blog'); - expect( + }), + '/blog' + ); + assert.equal( getLocaleRelativeUrl({ locale: 'es', base: '/blog/', ...config.i18n, trailingSlash: 'always', format: 'file', - }) - ).to.eq('/blog/es/'); + }), + '/blog/es/' + ); - expect( + assert.equal( getLocaleRelativeUrl({ locale: 'en', // ignore + file => no trailing slash @@ -223,8 +219,9 @@ describe('getLocaleRelativeUrl', () => { ...config.i18n, trailingSlash: 'ignore', format: 'file', - }) - ).to.eq('/blog'); + }), + '/blog' + ); }); it('should normalize locales by default', () => { @@ -242,17 +239,18 @@ describe('getLocaleRelativeUrl', () => { }, }; - expect( + assert.equal( getLocaleRelativeUrl({ locale: 'en_US', base: '/blog/', ...config.experimental.i18n, trailingSlash: 'always', format: 'directory', - }) - ).to.eq('/blog/en-us/'); + }), + '/blog/en-us/' + ); - expect( + assert.equal( getLocaleRelativeUrl({ locale: 'en_US', base: '/blog/', @@ -260,18 +258,20 @@ describe('getLocaleRelativeUrl', () => { trailingSlash: 'always', format: 'directory', normalizeLocale: false, - }) - ).to.eq('/blog/en_US/'); + }), + '/blog/en_US/' + ); - expect( + assert.equal( getLocaleRelativeUrl({ locale: 'en_AU', base: '/blog/', ...config.experimental.i18n, trailingSlash: 'always', format: 'directory', - }) - ).to.eq('/blog/en-au/'); + }), + '/blog/en-au/' + ); }); it('should return the default locale when routing strategy is [pathname-prefix-always]', () => { @@ -291,64 +291,48 @@ describe('getLocaleRelativeUrl', () => { }; // directory format - expect( + assert.equal( getLocaleRelativeUrl({ locale: 'en', base: '/blog/', trailingSlash: 'always', format: 'directory', ...config.experimental.i18n, - }) - ).to.eq('/blog/en/'); - expect( + }), + '/blog/en/' + ); + assert.equal( getLocaleRelativeUrl({ locale: 'es', base: '/blog/', ...config.experimental.i18n, trailingSlash: 'always', format: 'directory', - }) - ).to.eq('/blog/es/'); - - expect( - getLocaleRelativeUrl({ - locale: 'en_US', - base: '/blog/', - ...config.experimental.i18n, - trailingSlash: 'always', - format: 'directory', - }) - ).to.throw; + }), + '/blog/es/' + ); // file format - expect( + assert.equal( getLocaleRelativeUrl({ locale: 'en', base: '/blog/', ...config.experimental.i18n, trailingSlash: 'always', format: 'file', - }) - ).to.eq('/blog/en/'); - expect( + }), + '/blog/en/' + ); + assert.equal( getLocaleRelativeUrl({ locale: 'es', base: '/blog/', ...config.experimental.i18n, trailingSlash: 'always', format: 'file', - }) - ).to.eq('/blog/es/'); - - expect( - getLocaleRelativeUrl({ - locale: 'en_US', - base: '/blog/', - ...config.experimental.i18n, - trailingSlash: 'always', - format: 'file', - }) - ).to.throw; + }), + '/blog/es/' + ); }); it('should return the default locale when routing strategy is [pathname-prefix-always-no-redirect]', () => { @@ -368,64 +352,48 @@ describe('getLocaleRelativeUrl', () => { }; // directory format - expect( + assert.equal( getLocaleRelativeUrl({ locale: 'en', base: '/blog/', trailingSlash: 'always', format: 'directory', ...config.experimental.i18n, - }) - ).to.eq('/blog/en/'); - expect( + }), + '/blog/en/' + ); + assert.equal( getLocaleRelativeUrl({ locale: 'es', base: '/blog/', ...config.experimental.i18n, trailingSlash: 'always', format: 'directory', - }) - ).to.eq('/blog/es/'); - - expect( - getLocaleRelativeUrl({ - locale: 'en_US', - base: '/blog/', - ...config.experimental.i18n, - trailingSlash: 'always', - format: 'directory', - }) - ).to.throw; + }), + '/blog/es/' + ); // file format - expect( + assert.equal( getLocaleRelativeUrl({ locale: 'en', base: '/blog/', ...config.experimental.i18n, trailingSlash: 'always', format: 'file', - }) - ).to.eq('/blog/en/'); - expect( + }), + '/blog/en/' + ); + assert.equal( getLocaleRelativeUrl({ locale: 'es', base: '/blog/', ...config.experimental.i18n, trailingSlash: 'always', format: 'file', - }) - ).to.eq('/blog/es/'); - - expect( - getLocaleRelativeUrl({ - locale: 'en_US', - base: '/blog/', - ...config.experimental.i18n, - trailingSlash: 'always', - format: 'file', - }) - ).to.throw; + }), + '/blog/es/' + ); }); }); @@ -452,15 +420,16 @@ describe('getLocaleRelativeUrlList', () => { }, }; // directory format - expect( + assert.deepEqual( getLocaleRelativeUrlList({ locale: 'en', base: '/blog', ...config.experimental.i18n, trailingSlash: 'never', format: 'directory', - }) - ).to.have.members(['/blog', '/blog/en-us', '/blog/es', '/blog/italiano']); + }), + ['/blog', '/blog/en-us', '/blog/es', '/blog/italiano'] + ); }); it('should retrieve the correct list of base URL with locales [format: directory, trailingSlash: always]', () => { @@ -485,15 +454,16 @@ describe('getLocaleRelativeUrlList', () => { }, }; // directory format - expect( + assert.deepEqual( getLocaleRelativeUrlList({ locale: 'en', base: '/blog/', ...config.experimental.i18n, trailingSlash: 'always', format: 'directory', - }) - ).to.have.members(['/blog/', '/blog/en-us/', '/blog/es/', '/blog/italiano/']); + }), + ['/blog/', '/blog/en-us/', '/blog/es/', '/blog/italiano/'] + ); }); it('should retrieve the correct list of base URL with locales [format: file, trailingSlash: always]', () => { @@ -510,15 +480,16 @@ describe('getLocaleRelativeUrlList', () => { }, }; // directory format - expect( + assert.deepEqual( getLocaleRelativeUrlList({ locale: 'en', base: '/blog/', ...config.experimental.i18n, trailingSlash: 'always', format: 'file', - }) - ).to.have.members(['/blog/', '/blog/en-us/', '/blog/es/']); + }), + ['/blog/', '/blog/en-us/', '/blog/es/'] + ); }); it('should retrieve the correct list of base URL with locales [format: file, trailingSlash: never]', () => { @@ -535,15 +506,16 @@ describe('getLocaleRelativeUrlList', () => { }, }; // directory format - expect( + assert.deepEqual( getLocaleRelativeUrlList({ locale: 'en', base: '/blog', ...config.experimental.i18n, trailingSlash: 'never', format: 'file', - }) - ).to.have.members(['/blog', '/blog/en-us', '/blog/es']); + }), + ['/blog', '/blog/en-us', '/blog/es'] + ); }); it('should retrieve the correct list of base URL with locales [format: file, trailingSlash: ignore]', () => { @@ -560,15 +532,16 @@ describe('getLocaleRelativeUrlList', () => { }, }; // directory format - expect( + assert.deepEqual( getLocaleRelativeUrlList({ locale: 'en', base: '/blog', ...config.experimental.i18n, trailingSlash: 'ignore', format: 'file', - }) - ).to.have.members(['/blog', '/blog/en-us', '/blog/es']); + }), + ['/blog', '/blog/en-us', '/blog/es'] + ); }); it('should retrieve the correct list of base URL with locales [format: directory, trailingSlash: ignore]', () => { @@ -585,15 +558,16 @@ describe('getLocaleRelativeUrlList', () => { }, }; // directory format - expect( + assert.deepEqual( getLocaleRelativeUrlList({ locale: 'en', base: '/blog/', ...config.experimental.i18n, trailingSlash: 'ignore', format: 'directory', - }) - ).to.have.members(['/blog/', '/blog/en-us/', '/blog/es/']); + }), + ['/blog/', '/blog/en-us/', '/blog/es/'] + ); }); it('should retrieve the correct list of base URL with locales [format: directory, trailingSlash: never, routingStategy: pathname-prefix-always]', () => { @@ -611,15 +585,16 @@ describe('getLocaleRelativeUrlList', () => { }, }; // directory format - expect( + assert.deepEqual( getLocaleRelativeUrlList({ locale: 'en', base: '/blog', ...config.experimental.i18n, trailingSlash: 'never', format: 'directory', - }) - ).to.have.members(['/blog/en', '/blog/en-us', '/blog/es']); + }), + ['/blog/en', '/blog/en-us', '/blog/es'] + ); }); it('should retrieve the correct list of base URL with locales [format: directory, trailingSlash: never, routingStategy: pathname-prefix-always-no-redirect]', () => { @@ -637,15 +612,16 @@ describe('getLocaleRelativeUrlList', () => { }, }; // directory format - expect( + assert.deepEqual( getLocaleRelativeUrlList({ locale: 'en', base: '/blog', ...config.experimental.i18n, trailingSlash: 'never', format: 'directory', - }) - ).to.have.members(['/blog/en', '/blog/en-us', '/blog/es']); + }), + ['/blog/en', '/blog/en-us', '/blog/es'] + ); }); }); @@ -677,7 +653,7 @@ describe('getLocaleAbsoluteUrl', () => { }; // directory format - expect( + assert.equal( getLocaleAbsoluteUrl({ locale: 'en', base: '/blog/', @@ -685,9 +661,10 @@ describe('getLocaleAbsoluteUrl', () => { format: 'directory', site: 'https://example.com', ...config.i18n, - }) - ).to.eq('https://example.com/blog/'); - expect( + }), + 'https://example.com/blog/' + ); + assert.equal( getLocaleAbsoluteUrl({ locale: 'es', base: '/blog/', @@ -695,10 +672,11 @@ describe('getLocaleAbsoluteUrl', () => { trailingSlash: 'always', format: 'directory', site: 'https://example.com', - }) - ).to.eq('https://example.com/blog/es/'); + }), + 'https://example.com/blog/es/' + ); - expect( + assert.equal( getLocaleAbsoluteUrl({ locale: 'es', base: '/blog/', @@ -707,22 +685,29 @@ describe('getLocaleAbsoluteUrl', () => { format: 'directory', site: 'https://example.com', isBuild: true, + }), + 'https://es.example.com/blog/' + ); + + assert.throws( + () => + getLocaleAbsoluteUrl({ + locale: 'ff', + base: '/blog/', + ...config.i18n, + trailingSlash: 'always', + format: 'directory', + site: 'https://example.com', + }), + + new AstroError({ + ...MissingLocale, + message: MissingLocale.message('ff'), }) - ).to.eq('https://es.example.com/blog/'); - - expect( - getLocaleAbsoluteUrl({ - locale: 'en_US', - base: '/blog/', - ...config.i18n, - trailingSlash: 'always', - format: 'directory', - site: 'https://example.com', - }) - ).to.throw; + ); // file format - expect( + assert.equal( getLocaleAbsoluteUrl({ locale: 'en', base: '/blog/', @@ -730,9 +715,10 @@ describe('getLocaleAbsoluteUrl', () => { trailingSlash: 'always', format: 'file', site: 'https://example.com', - }) - ).to.eq('https://example.com/blog/'); - expect( + }), + 'https://example.com/blog/' + ); + assert.equal( getLocaleAbsoluteUrl({ locale: 'es', base: '/blog/', @@ -740,20 +726,11 @@ describe('getLocaleAbsoluteUrl', () => { trailingSlash: 'always', format: 'file', site: 'https://example.com', - }) - ).to.eq('https://example.com/blog/es/'); + }), + 'https://example.com/blog/es/' + ); - expect( - getLocaleAbsoluteUrl({ - locale: 'en_US', - base: '/blog/', - ...config.i18n, - trailingSlash: 'always', - format: 'file', - site: 'https://example.com', - }) - ).to.throw; - expect( + assert.equal( getLocaleAbsoluteUrl({ locale: 'it-VA', base: '/blog/', @@ -761,21 +738,11 @@ describe('getLocaleAbsoluteUrl', () => { trailingSlash: 'always', format: 'file', site: 'https://example.com', - }) - ).to.eq('https://example.com/blog/italiano/'); - - expect( - getLocaleAbsoluteUrl({ - locale: 'en_US', - base: '/blog/', - ...config.i18n, - trailingSlash: 'always', - format: 'file', - site: 'https://example.com', - }) - ).to.throw; + }), + 'https://example.com/blog/italiano/' + ); - expect( + assert.equal( getLocaleAbsoluteUrl({ locale: 'es', base: '/blog/', @@ -784,10 +751,11 @@ describe('getLocaleAbsoluteUrl', () => { format: 'file', site: 'https://example.com', isBuild: true, - }) - ).to.eq('https://es.example.com/blog/'); + }), + 'https://es.example.com/blog/' + ); - expect( + assert.equal( getLocaleAbsoluteUrl({ locale: 'es', base: '/blog/', @@ -798,11 +766,12 @@ describe('getLocaleAbsoluteUrl', () => { site: 'https://example.com', path: 'first-post', isBuild: true, - }) - ).to.eq('https://es.example.com/blog/some-name/first-post/'); + }), + 'https://es.example.com/blog/some-name/first-post/' + ); // en isn't mapped to a domain - expect( + assert.equal( getLocaleAbsoluteUrl({ locale: 'en', base: '/blog/', @@ -813,8 +782,9 @@ describe('getLocaleAbsoluteUrl', () => { site: 'https://example.com', path: 'first-post', isBuild: true, - }) - ).to.eq('https://example.com/blog/some-name/first-post/'); + }), + 'https://example.com/blog/some-name/first-post/' + ); }); }); describe('with [prefix-always]', () => { @@ -838,7 +808,7 @@ describe('getLocaleAbsoluteUrl', () => { }; // directory format - expect( + assert.equal( getLocaleAbsoluteUrl({ locale: 'en', base: '/blog/', @@ -846,10 +816,11 @@ describe('getLocaleAbsoluteUrl', () => { format: 'directory', site: 'https://example.com', ...config.experimental.i18n, - }) - ).to.eq('https://example.com/blog/en/'); + }), + 'https://example.com/blog/en/' + ); - expect( + assert.equal( getLocaleAbsoluteUrl({ locale: 'es', base: '/blog/', @@ -857,22 +828,12 @@ describe('getLocaleAbsoluteUrl', () => { trailingSlash: 'always', format: 'directory', site: 'https://example.com', - }) - ).to.eq('https://example.com/blog/es/'); - - expect( - getLocaleAbsoluteUrl({ - locale: 'en_US', - base: '/blog/', - ...config.experimental.i18n, - trailingSlash: 'always', - format: 'directory', - site: 'https://example.com', - }) - ).to.throw; + }), + 'https://example.com/blog/es/' + ); // file format - expect( + assert.equal( getLocaleAbsoluteUrl({ locale: 'en', base: '/blog/', @@ -880,9 +841,10 @@ describe('getLocaleAbsoluteUrl', () => { trailingSlash: 'always', format: 'file', site: 'https://example.com', - }) - ).to.eq('https://example.com/blog/en/'); - expect( + }), + 'https://example.com/blog/en/' + ); + assert.equal( getLocaleAbsoluteUrl({ locale: 'es', base: '/blog/', @@ -890,21 +852,11 @@ describe('getLocaleAbsoluteUrl', () => { trailingSlash: 'always', format: 'file', site: 'https://example.com', - }) - ).to.eq('https://example.com/blog/es/'); + }), + 'https://example.com/blog/es/' + ); - expect( - getLocaleAbsoluteUrl({ - locale: 'en_US', - base: '/blog/', - ...config.experimental.i18n, - trailingSlash: 'always', - format: 'file', - site: 'https://example.com', - }) - ).to.throw; - - expect( + assert.equal( getLocaleAbsoluteUrl({ locale: 'es', base: '/blog/', @@ -913,10 +865,11 @@ describe('getLocaleAbsoluteUrl', () => { format: 'file', site: 'https://example.com', isBuild: true, - }) - ).to.eq('https://es.example.com/blog/'); + }), + 'https://es.example.com/blog/' + ); - expect( + assert.equal( getLocaleAbsoluteUrl({ locale: 'es', base: '/blog/', @@ -927,8 +880,9 @@ describe('getLocaleAbsoluteUrl', () => { site: 'https://example.com', path: 'first-post', isBuild: true, - }) - ).to.eq('https://es.example.com/blog/some-name/first-post/'); + }), + 'https://es.example.com/blog/some-name/first-post/' + ); }); it('should correctly return the URL without base', () => { /** @@ -945,7 +899,7 @@ describe('getLocaleAbsoluteUrl', () => { }, }; - expect( + assert.equal( getLocaleAbsoluteUrl({ locale: 'en', base: '/', @@ -953,9 +907,10 @@ describe('getLocaleAbsoluteUrl', () => { trailingSlash: 'always', format: 'directory', site: 'https://example.com', - }) - ).to.eq('https://example.com/en/'); - expect( + }), + 'https://example.com/en/' + ); + assert.equal( getLocaleAbsoluteUrl({ locale: 'es', base: '/', @@ -963,8 +918,9 @@ describe('getLocaleAbsoluteUrl', () => { trailingSlash: 'always', format: 'directory', site: 'https://example.com', - }) - ).to.eq('https://example.com/es/'); + }), + 'https://example.com/es/' + ); }); it('should correctly handle the trailing slash', () => { @@ -980,7 +936,7 @@ describe('getLocaleAbsoluteUrl', () => { }, }; // directory format - expect( + assert.equal( getLocaleAbsoluteUrl({ locale: 'en', base: '/blog', @@ -988,9 +944,10 @@ describe('getLocaleAbsoluteUrl', () => { trailingSlash: 'never', format: 'directory', site: 'https://example.com', - }) - ).to.eq('https://example.com/blog/en'); - expect( + }), + 'https://example.com/blog/en' + ); + assert.equal( getLocaleAbsoluteUrl({ locale: 'es', base: '/blog/', @@ -998,10 +955,11 @@ describe('getLocaleAbsoluteUrl', () => { trailingSlash: 'always', format: 'directory', site: 'https://example.com', - }) - ).to.eq('https://example.com/blog/es/'); + }), + 'https://example.com/blog/es/' + ); - expect( + assert.equal( getLocaleAbsoluteUrl({ locale: 'en', base: '/blog/', @@ -1009,11 +967,12 @@ describe('getLocaleAbsoluteUrl', () => { trailingSlash: 'ignore', format: 'directory', site: 'https://example.com', - }) - ).to.eq('https://example.com/blog/en/'); + }), + 'https://example.com/blog/en/' + ); // directory file - expect( + assert.equal( getLocaleAbsoluteUrl({ locale: 'en', base: '/blog', @@ -1021,9 +980,10 @@ describe('getLocaleAbsoluteUrl', () => { trailingSlash: 'never', format: 'file', site: 'https://example.com', - }) - ).to.eq('https://example.com/blog/en'); - expect( + }), + 'https://example.com/blog/en' + ); + assert.equal( getLocaleAbsoluteUrl({ locale: 'es', base: '/blog/', @@ -1031,10 +991,11 @@ describe('getLocaleAbsoluteUrl', () => { trailingSlash: 'always', format: 'file', site: 'https://example.com', - }) - ).to.eq('https://example.com/blog/es/'); + }), + 'https://example.com/blog/es/' + ); - expect( + assert.equal( getLocaleAbsoluteUrl({ locale: 'en', // ignore + file => no trailing slash @@ -1043,8 +1004,9 @@ describe('getLocaleAbsoluteUrl', () => { trailingSlash: 'ignore', format: 'file', site: 'https://example.com', - }) - ).to.eq('https://example.com/blog/en'); + }), + 'https://example.com/blog/en' + ); }); it('should normalize locales', () => { @@ -1063,27 +1025,29 @@ describe('getLocaleAbsoluteUrl', () => { }, }; - expect( + assert.equal( getLocaleAbsoluteUrl({ locale: 'en_US', base: '/blog/', ...config.experimental.i18n, trailingSlash: 'always', format: 'directory', - }) - ).to.eq('/blog/en-us/'); + }), + '/blog/en-us/' + ); - expect( + assert.equal( getLocaleAbsoluteUrl({ locale: 'en_AU', base: '/blog/', ...config.experimental.i18n, trailingSlash: 'always', format: 'directory', - }) - ).to.eq('/blog/en-au/'); + }), + '/blog/en-au/' + ); - expect( + assert.equal( getLocaleAbsoluteUrl({ locale: 'en_US', base: '/blog/', @@ -1091,8 +1055,9 @@ describe('getLocaleAbsoluteUrl', () => { trailingSlash: 'always', format: 'directory', normalizeLocale: true, - }) - ).to.eq('/blog/en-us/'); + }), + '/blog/en-us/' + ); }); it('should return the default locale when routing strategy is [pathname-prefix-always]', () => { @@ -1112,7 +1077,7 @@ describe('getLocaleAbsoluteUrl', () => { }; // directory format - expect( + assert.equal( getLocaleAbsoluteUrl({ locale: 'en', base: '/blog/', @@ -1120,9 +1085,10 @@ describe('getLocaleAbsoluteUrl', () => { site: 'https://example.com', format: 'directory', ...config.experimental.i18n, - }) - ).to.eq('https://example.com/blog/en/'); - expect( + }), + 'https://example.com/blog/en/' + ); + assert.equal( getLocaleAbsoluteUrl({ locale: 'es', base: '/blog/', @@ -1130,22 +1096,12 @@ describe('getLocaleAbsoluteUrl', () => { site: 'https://example.com', trailingSlash: 'always', format: 'directory', - }) - ).to.eq('https://example.com/blog/es/'); - - expect( - getLocaleAbsoluteUrl({ - locale: 'en_US', - base: '/blog/', - ...config.experimental.i18n, - site: 'https://example.com', - trailingSlash: 'always', - format: 'directory', - }) - ).to.throw; + }), + 'https://example.com/blog/es/' + ); // file format - expect( + assert.equal( getLocaleAbsoluteUrl({ locale: 'en', base: '/blog/', @@ -1153,9 +1109,10 @@ describe('getLocaleAbsoluteUrl', () => { site: 'https://example.com', trailingSlash: 'always', format: 'file', - }) - ).to.eq('https://example.com/blog/en/'); - expect( + }), + 'https://example.com/blog/en/' + ); + assert.equal( getLocaleAbsoluteUrl({ locale: 'es', base: '/blog/', @@ -1163,19 +1120,9 @@ describe('getLocaleAbsoluteUrl', () => { site: 'https://example.com', trailingSlash: 'always', format: 'file', - }) - ).to.eq('https://example.com/blog/es/'); - - expect( - getLocaleAbsoluteUrl({ - locale: 'en_US', - base: '/blog/', - ...config.experimental.i18n, - site: 'https://example.com', - trailingSlash: 'always', - format: 'file', - }) - ).to.throw; + }), + 'https://example.com/blog/es/' + ); }); it('should return the default locale when routing strategy is [pathname-prefix-always-no-redirect]', () => { @@ -1195,7 +1142,7 @@ describe('getLocaleAbsoluteUrl', () => { }; // directory format - expect( + assert.equal( getLocaleAbsoluteUrl({ locale: 'en', base: '/blog/', @@ -1203,9 +1150,10 @@ describe('getLocaleAbsoluteUrl', () => { site: 'https://example.com', format: 'directory', ...config.experimental.i18n, - }) - ).to.eq('https://example.com/blog/en/'); - expect( + }), + 'https://example.com/blog/en/' + ); + assert.equal( getLocaleAbsoluteUrl({ locale: 'es', base: '/blog/', @@ -1213,22 +1161,12 @@ describe('getLocaleAbsoluteUrl', () => { site: 'https://example.com', trailingSlash: 'always', format: 'directory', - }) - ).to.eq('https://example.com/blog/es/'); - - expect( - getLocaleAbsoluteUrl({ - locale: 'en_US', - base: '/blog/', - ...config.experimental.i18n, - site: 'https://example.com', - trailingSlash: 'always', - format: 'directory', - }) - ).to.throw; + }), + 'https://example.com/blog/es/' + ); // file format - expect( + assert.equal( getLocaleAbsoluteUrl({ locale: 'en', base: '/blog/', @@ -1236,9 +1174,10 @@ describe('getLocaleAbsoluteUrl', () => { site: 'https://example.com', trailingSlash: 'always', format: 'file', - }) - ).to.eq('https://example.com/blog/en/'); - expect( + }), + 'https://example.com/blog/en/' + ); + assert.equal( getLocaleAbsoluteUrl({ locale: 'es', base: '/blog/', @@ -1246,19 +1185,9 @@ describe('getLocaleAbsoluteUrl', () => { site: 'https://example.com', trailingSlash: 'always', format: 'file', - }) - ).to.eq('https://example.com/blog/es/'); - - expect( - getLocaleAbsoluteUrl({ - locale: 'en_US', - base: '/blog/', - ...config.experimental.i18n, - site: 'https://example.com', - trailingSlash: 'always', - format: 'file', - }) - ).to.throw; + }), + 'https://example.com/blog/es/' + ); }); it('should correctly return the URL without base', () => { /** @@ -1282,7 +1211,7 @@ describe('getLocaleAbsoluteUrl', () => { }, }; - expect( + assert.equal( getLocaleAbsoluteUrl({ locale: 'en', base: '/', @@ -1290,9 +1219,10 @@ describe('getLocaleAbsoluteUrl', () => { trailingSlash: 'always', format: 'directory', site: 'https://example.com', - }) - ).to.eq('https://example.com/'); - expect( + }), + 'https://example.com/' + ); + assert.equal( getLocaleAbsoluteUrl({ locale: 'es', base: '/', @@ -1300,9 +1230,10 @@ describe('getLocaleAbsoluteUrl', () => { trailingSlash: 'always', format: 'directory', site: 'https://example.com', - }) - ).to.eq('https://example.com/es/'); - expect( + }), + 'https://example.com/es/' + ); + assert.equal( getLocaleAbsoluteUrl({ locale: 'it-VA', base: '/', @@ -1310,8 +1241,9 @@ describe('getLocaleAbsoluteUrl', () => { trailingSlash: 'always', format: 'directory', site: 'https://example.com', - }) - ).to.eq('https://example.com/italiano/'); + }), + 'https://example.com/italiano/' + ); }); it('should correctly handle the trailing slash', () => { @@ -1329,7 +1261,7 @@ describe('getLocaleAbsoluteUrl', () => { }, }; // directory format - expect( + assert.equal( getLocaleAbsoluteUrl({ locale: 'en', base: '/blog', @@ -1337,9 +1269,10 @@ describe('getLocaleAbsoluteUrl', () => { trailingSlash: 'never', format: 'directory', site: 'https://example.com', - }) - ).to.eq('https://example.com/blog'); - expect( + }), + 'https://example.com/blog' + ); + assert.equal( getLocaleAbsoluteUrl({ locale: 'es', base: '/blog/', @@ -1347,10 +1280,11 @@ describe('getLocaleAbsoluteUrl', () => { trailingSlash: 'always', format: 'directory', site: 'https://example.com', - }) - ).to.eq('https://example.com/blog/es/'); + }), + 'https://example.com/blog/es/' + ); - expect( + assert.equal( getLocaleAbsoluteUrl({ locale: 'en', base: '/blog/', @@ -1358,11 +1292,12 @@ describe('getLocaleAbsoluteUrl', () => { trailingSlash: 'ignore', format: 'directory', site: 'https://example.com', - }) - ).to.eq('https://example.com/blog/'); + }), + 'https://example.com/blog/' + ); // directory file - expect( + assert.equal( getLocaleAbsoluteUrl({ locale: 'en', base: '/blog', @@ -1370,9 +1305,10 @@ describe('getLocaleAbsoluteUrl', () => { trailingSlash: 'never', format: 'file', site: 'https://example.com', - }) - ).to.eq('https://example.com/blog'); - expect( + }), + 'https://example.com/blog' + ); + assert.equal( getLocaleAbsoluteUrl({ locale: 'es', base: '/blog/', @@ -1380,10 +1316,11 @@ describe('getLocaleAbsoluteUrl', () => { trailingSlash: 'always', format: 'file', site: 'https://example.com', - }) - ).to.eq('https://example.com/blog/es/'); + }), + 'https://example.com/blog/es/' + ); - expect( + assert.equal( getLocaleAbsoluteUrl({ locale: 'en', // ignore + file => no trailing slash @@ -1392,8 +1329,9 @@ describe('getLocaleAbsoluteUrl', () => { trailingSlash: 'ignore', format: 'file', site: 'https://example.com', - }) - ).to.eq('https://example.com/blog'); + }), + 'https://example.com/blog' + ); }); it('should normalize locales', () => { @@ -1412,27 +1350,29 @@ describe('getLocaleAbsoluteUrl', () => { }, }; - expect( + assert.equal( getLocaleAbsoluteUrl({ locale: 'en_US', base: '/blog/', ...config.experimental.i18n, trailingSlash: 'always', format: 'directory', - }) - ).to.eq('/blog/en-us/'); + }), + '/blog/en-us/' + ); - expect( + assert.equal( getLocaleAbsoluteUrl({ locale: 'en_AU', base: '/blog/', ...config.experimental.i18n, trailingSlash: 'always', format: 'directory', - }) - ).to.eq('/blog/en-au/'); + }), + '/blog/en-au/' + ); - expect( + assert.equal( getLocaleAbsoluteUrl({ locale: 'en_US', base: '/blog/', @@ -1440,8 +1380,9 @@ describe('getLocaleAbsoluteUrl', () => { trailingSlash: 'always', format: 'directory', normalizeLocale: true, - }) - ).to.eq('/blog/en-us/'); + }), + '/blog/en-us/' + ); }); }); }); @@ -1474,19 +1415,20 @@ describe('getLocaleAbsoluteUrlList', () => { process.cwd() ); // directory format - expect( + assert.deepEqual( getLocaleAbsoluteUrlList({ locale: 'en', ...config, ...config.i18n, isBuild: true, - }) - ).to.have.members([ - 'https://example.com/blog', - 'https://example.com/blog/en-us', - 'https://example.com/blog/es', - 'https://example.com/blog/italiano', - ]); + }), + [ + 'https://example.com/blog', + 'https://example.com/blog/en-us', + 'https://example.com/blog/es', + 'https://example.com/blog/italiano', + ] + ); }); it('should retrieve the correct list of base URL with locales [format: directory, trailingSlash: always]', async () => { @@ -1508,17 +1450,18 @@ describe('getLocaleAbsoluteUrlList', () => { process.cwd() ); // directory format - expect( + assert.deepEqual( getLocaleAbsoluteUrlList({ locale: 'en', ...config, ...config.i18n, - }) - ).to.have.members([ - 'https://example.com/blog/', - 'https://example.com/blog/en-us/', - 'https://example.com/blog/es/', - ]); + }), + [ + 'https://example.com/blog/', + 'https://example.com/blog/en-us/', + 'https://example.com/blog/es/', + ] + ); }); it('should retrieve the correct list of base URL with locales and path [format: directory, trailingSlash: always]', async () => { @@ -1542,18 +1485,19 @@ describe('getLocaleAbsoluteUrlList', () => { process.cwd() ); // directory format - expect( + assert.deepEqual( getLocaleAbsoluteUrlList({ locale: 'en', path: 'download', ...config, ...config.i18n, - }) - ).to.have.members([ - 'https://example.com/en/download/', - 'https://example.com/en-us/download/', - 'https://example.com/es/download/', - ]); + }), + [ + 'https://example.com/en/download/', + 'https://example.com/en-us/download/', + 'https://example.com/es/download/', + ] + ); }); it('should retrieve the correct list of base URL with locales and path [format: directory, trailingSlash: always, domains]', async () => { @@ -1580,19 +1524,20 @@ describe('getLocaleAbsoluteUrlList', () => { process.cwd() ); // directory format - expect( + assert.deepEqual( getLocaleAbsoluteUrlList({ locale: 'en', path: 'download', ...config, ...config.i18n, isBuild: true, - }) - ).to.have.members([ - 'https://example.com/en/download/', - 'https://example.com/en-us/download/', - 'https://es.example.com/download/', - ]); + }), + [ + 'https://example.com/en/download/', + 'https://example.com/en-us/download/', + 'https://es.example.com/download/', + ] + ); }); it('should retrieve the correct list of base URL with locales [format: file, trailingSlash: always]', () => { @@ -1617,7 +1562,7 @@ describe('getLocaleAbsoluteUrlList', () => { }, }; // directory format - expect( + assert.deepEqual( getLocaleAbsoluteUrlList({ locale: 'en', base: '/blog/', @@ -1625,13 +1570,14 @@ describe('getLocaleAbsoluteUrlList', () => { trailingSlash: 'always', format: 'file', site: 'https://example.com', - }) - ).to.have.members([ - 'https://example.com/blog/', - 'https://example.com/blog/en-us/', - 'https://example.com/blog/es/', - 'https://example.com/blog/italiano/', - ]); + }), + [ + 'https://example.com/blog/', + 'https://example.com/blog/en-us/', + 'https://example.com/blog/es/', + 'https://example.com/blog/italiano/', + ] + ); }); it('should retrieve the correct list of base URL with locales [format: file, trailingSlash: never]', () => { @@ -1648,7 +1594,7 @@ describe('getLocaleAbsoluteUrlList', () => { }, }; // directory format - expect( + assert.deepEqual( getLocaleAbsoluteUrlList({ locale: 'en', base: '/blog', @@ -1656,12 +1602,9 @@ describe('getLocaleAbsoluteUrlList', () => { trailingSlash: 'never', format: 'file', site: 'https://example.com', - }) - ).to.have.members([ - 'https://example.com/blog', - 'https://example.com/blog/en-us', - 'https://example.com/blog/es', - ]); + }), + ['https://example.com/blog', 'https://example.com/blog/en-us', 'https://example.com/blog/es'] + ); }); it('should retrieve the correct list of base URL with locales [format: file, trailingSlash: ignore]', () => { @@ -1678,7 +1621,7 @@ describe('getLocaleAbsoluteUrlList', () => { }, }; // directory format - expect( + assert.deepEqual( getLocaleAbsoluteUrlList({ locale: 'en', base: '/blog', @@ -1686,12 +1629,9 @@ describe('getLocaleAbsoluteUrlList', () => { trailingSlash: 'ignore', format: 'file', site: 'https://example.com', - }) - ).to.have.members([ - 'https://example.com/blog', - 'https://example.com/blog/en-us', - 'https://example.com/blog/es', - ]); + }), + ['https://example.com/blog', 'https://example.com/blog/en-us', 'https://example.com/blog/es'] + ); }); it('should retrieve the correct list of base URL with locales [format: directory, trailingSlash: ignore]', () => { @@ -1708,7 +1648,7 @@ describe('getLocaleAbsoluteUrlList', () => { }, }; // directory format - expect( + assert.deepEqual( getLocaleAbsoluteUrlList({ locale: 'en', base: '/blog/', @@ -1716,12 +1656,13 @@ describe('getLocaleAbsoluteUrlList', () => { trailingSlash: 'ignore', format: 'directory', site: 'https://example.com', - }) - ).to.have.members([ - 'https://example.com/blog/', - 'https://example.com/blog/en-us/', - 'https://example.com/blog/es/', - ]); + }), + [ + 'https://example.com/blog/', + 'https://example.com/blog/en-us/', + 'https://example.com/blog/es/', + ] + ); }); it('should retrieve the correct list of base URL with locales [format: directory, trailingSlash: ignore, routingStategy: pathname-prefix-always]', () => { @@ -1739,7 +1680,7 @@ describe('getLocaleAbsoluteUrlList', () => { }, }; // directory format - expect( + assert.deepEqual( getLocaleAbsoluteUrlList({ locale: 'en', base: '/blog/', @@ -1747,12 +1688,13 @@ describe('getLocaleAbsoluteUrlList', () => { trailingSlash: 'ignore', format: 'directory', site: 'https://example.com', - }) - ).to.have.members([ - 'https://example.com/blog/en/', - 'https://example.com/blog/en-us/', - 'https://example.com/blog/es/', - ]); + }), + [ + 'https://example.com/blog/en/', + 'https://example.com/blog/en-us/', + 'https://example.com/blog/es/', + ] + ); }); it('should retrieve the correct list of base URL with locales [format: directory, trailingSlash: ignore, routingStategy: pathname-prefix-always-no-redirect]', () => { @@ -1770,7 +1712,7 @@ describe('getLocaleAbsoluteUrlList', () => { }, }; // directory format - expect( + assert.deepEqual( getLocaleAbsoluteUrlList({ locale: 'en', base: '/blog/', @@ -1778,12 +1720,13 @@ describe('getLocaleAbsoluteUrlList', () => { trailingSlash: 'ignore', format: 'directory', site: 'https://example.com', - }) - ).to.have.members([ - 'https://example.com/blog/en/', - 'https://example.com/blog/en-us/', - 'https://example.com/blog/es/', - ]); + }), + [ + 'https://example.com/blog/en/', + 'https://example.com/blog/en-us/', + 'https://example.com/blog/es/', + ] + ); }); it('should retrieve the correct list of base URLs, swapped with the correct domain', () => { @@ -1805,7 +1748,7 @@ describe('getLocaleAbsoluteUrlList', () => { }, }; // directory format - expect( + assert.deepEqual( getLocaleAbsoluteUrlList({ base: '/blog/', ...config.experimental.i18n, @@ -1813,26 +1756,27 @@ describe('getLocaleAbsoluteUrlList', () => { format: 'directory', site: 'https://example.com', isBuild: true, - }) - ).to.have.members([ - 'https://example.uk/blog/', - 'https://example.com/blog/en-us/', - 'https://es.example.com/blog/', - ]); + }), + [ + 'https://example.uk/blog/', + 'https://example.com/blog/en-us/', + 'https://es.example.com/blog/', + ] + ); }); }); describe('parse accept-header', () => { it('should be parsed correctly', () => { - expect(parseLocale('*')).to.have.deep.members([{ locale: '*', qualityValue: undefined }]); - expect(parseLocale('fr')).to.have.deep.members([{ locale: 'fr', qualityValue: undefined }]); - expect(parseLocale('fr;q=0.6')).to.have.deep.members([{ locale: 'fr', qualityValue: 0.6 }]); - expect(parseLocale('fr;q=0.6,fr-CA;q=0.5')).to.have.deep.members([ + assert.deepEqual(parseLocale('*'), [{ locale: '*', qualityValue: undefined }]); + assert.deepEqual(parseLocale('fr'), [{ locale: 'fr', qualityValue: undefined }]); + assert.deepEqual(parseLocale('fr;q=0.6'), [{ locale: 'fr', qualityValue: 0.6 }]); + assert.deepEqual(parseLocale('fr;q=0.6,fr-CA;q=0.5'), [ { locale: 'fr', qualityValue: 0.6 }, { locale: 'fr-CA', qualityValue: 0.5 }, ]); - expect(parseLocale('fr-CH, fr;q=0.9, en;q=0.8, de;q=0.7, *;q=0.5')).to.have.deep.members([ + assert.deepEqual(parseLocale('fr-CH, fr;q=0.9, en;q=0.8, de;q=0.7, *;q=0.5'), [ { locale: 'fr-CH', qualityValue: undefined }, { locale: 'fr', qualityValue: 0.9 }, { locale: 'en', qualityValue: 0.8 }, @@ -1842,18 +1786,9 @@ describe('parse accept-header', () => { }); it('should not return incorrect quality values', () => { - expect(parseLocale('wrong')).to.have.deep.members([ - { locale: 'wrong', qualityValue: undefined }, - ]); - expect(parseLocale('fr;f=0.7')).to.have.deep.members([ - { locale: 'fr', qualityValue: undefined }, - ]); - expect(parseLocale('fr;q=something')).to.have.deep.members([ - { locale: 'fr', qualityValue: undefined }, - ]); - - expect(parseLocale('fr;q=1000')).to.have.deep.members([ - { locale: 'fr', qualityValue: undefined }, - ]); + assert.deepEqual(parseLocale('wrong'), [{ locale: 'wrong', qualityValue: undefined }]); + assert.deepEqual(parseLocale('fr;f=0.7'), [{ locale: 'fr', qualityValue: undefined }]); + assert.deepEqual(parseLocale('fr;q=something'), [{ locale: 'fr', qualityValue: undefined }]); + assert.deepEqual(parseLocale('fr;q=1000'), [{ locale: 'fr', qualityValue: undefined }]); }); }); diff --git a/packages/astro/test/units/integrations/api.test.js b/packages/astro/test/units/integrations/api.nodetest.js similarity index 86% rename from packages/astro/test/units/integrations/api.test.js rename to packages/astro/test/units/integrations/api.nodetest.js index 882570db2589..d4b0491c3b55 100644 --- a/packages/astro/test/units/integrations/api.test.js +++ b/packages/astro/test/units/integrations/api.nodetest.js @@ -1,7 +1,8 @@ -import { expect } from 'chai'; import { runHookBuildSetup, runHookConfigSetup } from '../../../dist/integrations/index.js'; import { validateSupportedFeatures } from '../../../dist/integrations/astroFeaturesValidation.js'; import { defaultLogger } from '../test-utils.js'; +import { describe, it } from 'node:test'; +import * as assert from 'node:assert/strict'; describe('Integration API', () => { it('runHookBuildSetup should work', async () => { @@ -27,7 +28,7 @@ describe('Integration API', () => { pages: new Map(), target: 'server', }); - expect(updatedViteConfig).to.haveOwnProperty('define'); + assert.equal(updatedViteConfig.hasOwnProperty('define'), true); }); it('runHookBuildSetup should return updated config', async () => { @@ -54,7 +55,7 @@ describe('Integration API', () => { pages: new Map(), target: 'server', }); - expect(updatedViteConfig).to.be.deep.equal(updatedInternalConfig); + assert.deepEqual(updatedViteConfig, updatedInternalConfig); }); it('runHookConfigSetup can update Astro config', async () => { @@ -76,7 +77,7 @@ describe('Integration API', () => { }, }, }); - expect(updatedSettings.config.site).to.equal(site); + assert.equal(updatedSettings.config.site, site); }); it('runHookConfigSetup runs integrations added by another integration', async () => { @@ -110,8 +111,8 @@ describe('Integration API', () => { }, }, }); - expect(updatedSettings.config.site).to.equal(site); - expect(updatedSettings.config.integrations.length).to.equal(2); + assert.equal(updatedSettings.config.site, site); + assert.equal(updatedSettings.config.integrations.length, 2); }); }); @@ -128,7 +129,7 @@ describe('Astro feature map', function () { {}, defaultLogger ); - expect(result['hybridOutput']).to.be.true; + assert.equal(result['hybridOutput'], true); }); it('should not support the feature when not provided', () => { @@ -141,7 +142,7 @@ describe('Astro feature map', function () { {}, defaultLogger ); - expect(result['hybridOutput']).to.be.false; + assert.equal(result['hybridOutput'], false); }); it('should not support the feature when an empty object is provided', () => { @@ -154,7 +155,7 @@ describe('Astro feature map', function () { {}, defaultLogger ); - expect(result['hybridOutput']).to.be.false; + assert.equal(result['hybridOutput'], false); }); describe('static output', function () { @@ -168,7 +169,7 @@ describe('Astro feature map', function () { {}, defaultLogger ); - expect(result['staticOutput']).to.be.true; + assert.equal(result['staticOutput'], true); }); it("should not be valid if the config is correct, but the it's unsupported", () => { @@ -181,7 +182,7 @@ describe('Astro feature map', function () { {}, defaultLogger ); - expect(result['staticOutput']).to.be.false; + assert.equal(result['staticOutput'], false); }); }); describe('hybrid output', function () { @@ -195,7 +196,7 @@ describe('Astro feature map', function () { {}, defaultLogger ); - expect(result['hybridOutput']).to.be.true; + assert.equal(result['hybridOutput'], true); }); it("should not be valid if the config is correct, but the it's unsupported", () => { @@ -210,7 +211,7 @@ describe('Astro feature map', function () { {}, defaultLogger ); - expect(result['hybridOutput']).to.be.false; + assert.equal(result['hybridOutput'], false); }); }); describe('server output', function () { @@ -224,7 +225,7 @@ describe('Astro feature map', function () { {}, defaultLogger ); - expect(result['serverOutput']).to.be.true; + assert.equal(result['serverOutput'], true); }); it("should not be valid if the config is correct, but the it's unsupported", () => { @@ -239,7 +240,7 @@ describe('Astro feature map', function () { {}, defaultLogger ); - expect(result['serverOutput']).to.be.false; + assert.equal(result['serverOutput'], false); }); }); @@ -263,7 +264,7 @@ describe('Astro feature map', function () { {}, defaultLogger ); - expect(result['assets']).to.be.true; + assert.equal(result['assets'], true); }); it('should be supported when it is squoosh compatible', () => { let result = validateSupportedFeatures( @@ -284,7 +285,7 @@ describe('Astro feature map', function () { {}, defaultLogger ); - expect(result['assets']).to.be.true; + assert.equal(result['assets'], true); }); it("should not be valid if the config is correct, but the it's unsupported", () => { @@ -306,7 +307,7 @@ describe('Astro feature map', function () { {}, defaultLogger ); - expect(result['assets']).to.be.false; + assert.equal(result['assets'], false); }); }); }); diff --git a/packages/astro/test/units/logger/locale.test.js b/packages/astro/test/units/logger/locale.nodetest.js similarity index 78% rename from packages/astro/test/units/logger/locale.test.js rename to packages/astro/test/units/logger/locale.nodetest.js index c8e115f20f1c..ddeadfc81f7b 100644 --- a/packages/astro/test/units/logger/locale.test.js +++ b/packages/astro/test/units/logger/locale.nodetest.js @@ -1,4 +1,5 @@ -import { expect } from 'chai'; +import { describe, it, after } from 'node:test'; +import * as assert from 'node:assert/strict'; const LOCALES = ['en_US', 'sv_SE', 'es_419.UTF-8', 'es_ES@euro', 'C']; @@ -13,9 +14,9 @@ describe('logger - dateTimeFormat', () => { it(`works with process.env.LANG="${locale}"`, async () => { process.env.LANG = locale; const { dateTimeFormat } = await import('../../../dist/core/logger/core.js?cachebust=' + i); - expect(() => { + assert.doesNotThrow(() => { dateTimeFormat.format(new Date()); - }).not.to.throw(); + }); }); }); }); diff --git a/packages/astro/test/units/render/chunk.test.js b/packages/astro/test/units/render/chunk.nodetest.js similarity index 84% rename from packages/astro/test/units/render/chunk.test.js rename to packages/astro/test/units/render/chunk.nodetest.js index b623f662f449..035e98484ae8 100644 --- a/packages/astro/test/units/render/chunk.test.js +++ b/packages/astro/test/units/render/chunk.nodetest.js @@ -1,4 +1,5 @@ -import { expect } from 'chai'; +import { describe, it } from 'node:test'; +import * as assert from 'node:assert/strict'; import * as cheerio from 'cheerio'; import { fileURLToPath } from 'node:url'; import { createFs, createRequestAndResponse, runInContainer } from '../test-utils.js'; @@ -41,10 +42,10 @@ describe('core/render chunk', () => { const $ = cheerio.load(html); const target = $('#chunk'); - expect(target).not.to.be.undefined; - expect(target.text()).to.equal('[object Object]'); + assert.ok(target); + assert.equal(target.text(), '[object Object]'); } catch (e) { - expect(false).to.be.ok; + assert.fail(); } } ); diff --git a/packages/astro/test/units/render/components.test.js b/packages/astro/test/units/render/components.nodetest.js similarity index 83% rename from packages/astro/test/units/render/components.test.js rename to packages/astro/test/units/render/components.nodetest.js index cd27141f94a7..7fa36e8642ef 100644 --- a/packages/astro/test/units/render/components.test.js +++ b/packages/astro/test/units/render/components.nodetest.js @@ -1,4 +1,5 @@ -import { expect } from 'chai'; +import { describe, it } from 'node:test'; +import * as assert from 'node:assert/strict'; import * as cheerio from 'cheerio'; import { fileURLToPath } from 'node:url'; import { createFs, createRequestAndResponse, runInContainer } from '../test-utils.js'; @@ -47,11 +48,11 @@ describe('core/render components', () => { const $ = cheerio.load(html); const target = $('#target'); - expect(target).not.to.be.undefined; - expect(target.attr('id')).to.equal('target'); - expect(target.attr('style')).to.be.undefined; + assert.ok(target); + assert.equal(target.attr('id'), 'target'); + assert.equal(typeof target.attr('style'), 'undefined'); - expect($('#pwnd').length).to.equal(0); + assert.equal($('#pwnd').length, 0); } ); }); @@ -110,11 +111,11 @@ describe('core/render components', () => { const BothFlipped = check('#both-flipped'); const BothSpread = check('#both-spread'); - expect(Class).to.deep.equal({ class: 'red blue' }, '#class'); - expect(ClassList).to.deep.equal({ class: 'red blue' }, '#class-list'); - expect(BothLiteral).to.deep.equal({ class: 'red blue' }, '#both-literal'); - expect(BothFlipped).to.deep.equal({ class: 'red blue' }, '#both-flipped'); - expect(BothSpread).to.deep.equal({ class: 'red blue' }, '#both-spread'); + assert.deepEqual(Class, { class: 'red blue' }, '#class'); + assert.deepEqual(ClassList, { class: 'red blue' }, '#class-list'); + assert.deepEqual(BothLiteral, { class: 'red blue' }, '#both-literal'); + assert.deepEqual(BothFlipped, { class: 'red blue' }, '#both-flipped'); + assert.deepEqual(BothSpread, { class: 'red blue' }, '#both-spread'); } ); }); diff --git a/packages/astro/test/units/render/head.test.js b/packages/astro/test/units/render/head.nodetest.js similarity index 95% rename from packages/astro/test/units/render/head.test.js rename to packages/astro/test/units/render/head.nodetest.js index 1edd85d0dd8c..ab84534aac17 100644 --- a/packages/astro/test/units/render/head.test.js +++ b/packages/astro/test/units/render/head.nodetest.js @@ -1,5 +1,5 @@ -import { expect } from 'chai'; - +import { describe, it, before } from 'node:test'; +import * as assert from 'node:assert/strict'; import { createComponent, render, @@ -104,8 +104,8 @@ describe('core/render', () => { const html = await response.text(); const $ = cheerio.load(html); - expect($('head link')).to.have.a.lengthOf(1); - expect($('body link')).to.have.a.lengthOf(0); + assert.equal($('head link').length, 1); + assert.equal($('body link').length, 0); }); it('Multi-level layouts and head injection, without explicit head', async () => { @@ -186,8 +186,8 @@ describe('core/render', () => { const html = await response.text(); const $ = cheerio.load(html); - expect($('head link')).to.have.a.lengthOf(1); - expect($('body link')).to.have.a.lengthOf(0); + assert.equal($('head link').length, 1); + assert.equal($('body link').length, 0); }); it('Multi-level layouts and head injection, without any content in layouts', async () => { @@ -234,7 +234,7 @@ describe('core/render', () => { const html = await response.text(); const $ = cheerio.load(html); - expect($('link')).to.have.a.lengthOf(1); + assert.equal($('link').length, 1); }); }); }); diff --git a/packages/astro/test/units/render/jsx.test.js b/packages/astro/test/units/render/jsx.nodetest.js similarity index 87% rename from packages/astro/test/units/render/jsx.test.js rename to packages/astro/test/units/render/jsx.nodetest.js index 0368cc6fc6d9..757a0e35d36b 100644 --- a/packages/astro/test/units/render/jsx.test.js +++ b/packages/astro/test/units/render/jsx.nodetest.js @@ -1,4 +1,5 @@ -import { expect } from 'chai'; +import { describe, it, before } from 'node:test'; +import * as assert from 'node:assert/strict'; import { createComponent, render, @@ -51,10 +52,10 @@ describe('core/render', () => { const pipeline = new Pipeline(env); const response = await pipeline.renderRoute(ctx, mod); - expect(response.status).to.equal(200); + assert.equal(response.status, 200); const html = await response.text(); - expect(html).to.include('

works

'); + assert.equal(html.includes('

works

'), true); }); it('Can render slots with a dash in the name', async () => { @@ -97,11 +98,14 @@ describe('core/render', () => { const pipeline = new Pipeline(env); const response = await pipeline.renderRoute(ctx, mod); - expect(response.status).to.equal(200); + assert.equal(response.status, 200); const html = await response.text(); - expect(html).to.include( - '

works

works

' + assert.equal( + html.includes( + '

works

works

' + ), + true ); }); @@ -127,9 +131,9 @@ describe('core/render', () => { try { await response.text(); - expect(false).to.equal(true, 'should not have been successful'); + assert.equal(false, true, 'should not have been successful'); } catch (err) { - expect(err.message).to.equal('uh oh'); + assert.equal(err.message, 'uh oh'); } }); }); diff --git a/packages/astro/test/units/routing/endpoints.test.js b/packages/astro/test/units/routing/endpoints.nodetest.js similarity index 79% rename from packages/astro/test/units/routing/endpoints.test.js rename to packages/astro/test/units/routing/endpoints.nodetest.js index fde7a81daddb..c03a708028ab 100644 --- a/packages/astro/test/units/routing/endpoints.test.js +++ b/packages/astro/test/units/routing/endpoints.nodetest.js @@ -5,7 +5,8 @@ import { defaultLogger, } from '../test-utils.js'; import { fileURLToPath } from 'node:url'; -import { expect } from 'chai'; +import { describe, it, before, after } from 'node:test'; +import * as assert from 'node:assert/strict'; import { createContainer } from '../../../dist/core/dev/container.js'; import testAdapter from '../../test-adapter.js'; @@ -47,9 +48,9 @@ describe('endpoints', () => { container.handle(req, res); await done; const headers = res.getHeaders(); - expect(headers).to.deep.include({ location: 'https://example.com/destination' }); - expect(headers).not.to.deep.include({ 'x-astro-reroute': 'no' }); - expect(res.statusCode).to.equal(307); + assert.equal(headers['location'], 'https://example.com/destination'); + assert.equal(headers['x-astro-reroute'], undefined); + assert.equal(res.statusCode, 307); }); it('should return a response with location header', async () => { @@ -60,9 +61,9 @@ describe('endpoints', () => { container.handle(req, res); await done; const headers = res.getHeaders(); - expect(headers).to.deep.include({ location: 'https://example.com/destination' }); - expect(headers).not.to.deep.include({ 'x-astro-reroute': 'no' }); - expect(res.statusCode).to.equal(307); + assert.equal(headers['location'], 'https://example.com/destination'); + assert.equal(headers['x-astro-reroute'], undefined); + assert.equal(res.statusCode, 307); }); it('should append reroute header for HTTP status 404', async () => { @@ -73,8 +74,8 @@ describe('endpoints', () => { container.handle(req, res); await done; const headers = res.getHeaders(); - expect(headers).to.deep.include({ 'x-astro-reroute': 'no' }); - expect(res.statusCode).to.equal(404); + assert.equal(headers['x-astro-reroute'], 'no'); + assert.equal(res.statusCode, 404); }); it('should append reroute header for HTTP status 500', async () => { @@ -85,7 +86,7 @@ describe('endpoints', () => { container.handle(req, res); await done; const headers = res.getHeaders(); - expect(headers).to.deep.include({ 'x-astro-reroute': 'no' }); - expect(res.statusCode).to.equal(500); + assert.equal(headers['x-astro-reroute'], 'no'); + assert.equal(res.statusCode, 500); }); }); diff --git a/packages/astro/test/units/routing/manifest.test.js b/packages/astro/test/units/routing/manifest.nodetest.js similarity index 94% rename from packages/astro/test/units/routing/manifest.test.js rename to packages/astro/test/units/routing/manifest.nodetest.js index fe09f628b24c..d7bbc8c0fa89 100644 --- a/packages/astro/test/units/routing/manifest.test.js +++ b/packages/astro/test/units/routing/manifest.nodetest.js @@ -1,5 +1,5 @@ -import { expect } from 'chai'; - +import { describe, it } from 'node:test'; +import * as assert from 'node:assert/strict'; import { fileURLToPath } from 'node:url'; import { createRouteManifest } from '../../../dist/core/routing/manifest/create.js'; import { createBasicSettings, createFs } from '../test-utils.js'; @@ -45,8 +45,8 @@ describe('routing - createRouteManifest', () => { fsMod: fs, }); const [{ pattern }] = manifest.routes; - expect(pattern.test('')).to.equal(true); - expect(pattern.test('/')).to.equal(false); + assert.equal(pattern.test(''), true); + assert.equal(pattern.test('/'), false); }); it('endpoint routes are sorted before page routes', async () => { @@ -83,7 +83,7 @@ describe('routing - createRouteManifest', () => { fsMod: fs, }); - expect(getManifestRoutes(manifest)).to.deep.equal([ + assert.deepEqual(getManifestRoutes(manifest), [ { route: '/about', type: 'page', @@ -128,7 +128,7 @@ describe('routing - createRouteManifest', () => { fsMod: fs, }); - expect(getManifestRoutes(manifest)).to.deep.equal([ + assert.deepEqual(getManifestRoutes(manifest), [ { route: '/', type: 'page', @@ -179,7 +179,7 @@ describe('routing - createRouteManifest', () => { fsMod: fs, }); - expect(getManifestRoutes(manifest)).to.deep.equal([ + assert.deepEqual(getManifestRoutes(manifest), [ { route: '/', type: 'page', @@ -255,7 +255,7 @@ describe('routing - createRouteManifest', () => { fsMod: fs, }); - expect(getManifestRoutes(manifest)).to.deep.equal([ + assert.deepEqual(getManifestRoutes(manifest), [ { route: '/contributing', type: 'page', @@ -311,7 +311,7 @@ describe('routing - createRouteManifest', () => { fsMod: fs, }); - expect(getManifestRoutes(manifest)).to.deep.equal([ + assert.deepEqual(getManifestRoutes(manifest), [ { route: '/blog/[...slug]', type: 'page', @@ -358,7 +358,7 @@ describe('routing - createRouteManifest', () => { fsMod: fs, }); - expect(getManifestRoutes(manifest)).to.deep.equal([ + assert.deepEqual(getManifestRoutes(manifest), [ { route: '/blog/contributing', type: 'page', @@ -411,7 +411,7 @@ describe('routing - createRouteManifest', () => { fsMod: fs, }); - expect(getManifestRoutes(manifest)).to.deep.equal([ + assert.deepEqual(getManifestRoutes(manifest), [ { route: '/blog/about', type: 'redirect', @@ -466,7 +466,7 @@ describe('routing - createRouteManifest', () => { createRouteManifest(manifestOptions, logger); - expect(logs).to.deep.equal([ + assert.deepEqual(logs, [ { label: 'router', level: 'warn', @@ -512,7 +512,7 @@ describe('routing - createRouteManifest', () => { createRouteManifest(manifestOptions, logger); - expect(logs).to.deep.equal([ + assert.deepEqual(logs, [ { label: 'router', level: 'warn', diff --git a/packages/astro/test/units/routing/route-matching.test.js b/packages/astro/test/units/routing/route-matching.nodetest.js similarity index 90% rename from packages/astro/test/units/routing/route-matching.test.js rename to packages/astro/test/units/routing/route-matching.nodetest.js index 6f4724893c4a..0eeb47ca5f02 100644 --- a/packages/astro/test/units/routing/route-matching.test.js +++ b/packages/astro/test/units/routing/route-matching.nodetest.js @@ -7,7 +7,8 @@ import { import { createRouteManifest, matchAllRoutes } from '../../../dist/core/routing/index.js'; import { fileURLToPath } from 'node:url'; import { createViteLoader } from '../../../dist/core/module-loader/vite.js'; -import { expect } from 'chai'; +import { describe, it, before, after } from 'node:test'; +import * as assert from 'node:assert/strict'; import { createContainer } from '../../../dist/core/dev/container.js'; import * as cheerio from 'cheerio'; import testAdapter from '../../test-adapter.js'; @@ -166,7 +167,7 @@ describe('Route matching', () => { const preloadedMatches = await getSortedPreloadedMatches({ pipeline, matches, settings }); const sortedRouteNames = preloadedMatches.map((match) => match.route.route); - expect(sortedRouteNames).to.deep.equal([ + assert.deepEqual(sortedRouteNames, [ '/[astaticdynamic]', '/[xstaticdynamic]', '/[serverdynamic]', @@ -180,7 +181,7 @@ describe('Route matching', () => { const preloadedMatches = await getSortedPreloadedMatches({ pipeline, matches, settings }); const sortedRouteNames = preloadedMatches.map((match) => match.route.route); - expect(sortedRouteNames).to.deep.equal([ + assert.deepEqual(sortedRouteNames, [ '/nested/[...astaticrest]', '/nested/[...xstaticrest]', '/nested/[...serverrest]', @@ -200,7 +201,7 @@ describe('Route matching', () => { container.handle(req, res); const html = await text(); const $ = cheerio.load(html); - expect($('p').text()).to.equal('Prerendered dynamic route!'); + assert.equal($('p').text(), 'Prerendered dynamic route!'); }); it('should correctly match a static dynamic route II', async () => { @@ -211,7 +212,7 @@ describe('Route matching', () => { container.handle(req, res); const html = await text(); const $ = cheerio.load(html); - expect($('p').text()).to.equal('Another prerendered dynamic route!'); + assert.equal($('p').text(), 'Another prerendered dynamic route!'); }); it('should correctly match a server dynamic route', async () => { @@ -222,7 +223,7 @@ describe('Route matching', () => { container.handle(req, res); const html = await text(); const $ = cheerio.load(html); - expect($('p').text()).to.equal('Server dynamic route! slug:a-random-slug-was-matched'); + assert.equal($('p').text(), 'Server dynamic route! slug:a-random-slug-was-matched'); }); it('should correctly match a static rest route I', async () => { @@ -233,7 +234,7 @@ describe('Route matching', () => { container.handle(req, res); const html = await text(); const $ = cheerio.load(html); - expect($('p').text()).to.equal('Prerendered rest route!'); + assert.equal($('p').text(), 'Prerendered rest route!'); }); it('should correctly match a static rest route II', async () => { @@ -244,7 +245,7 @@ describe('Route matching', () => { container.handle(req, res); const html = await text(); const $ = cheerio.load(html); - expect($('p').text()).to.equal('Another prerendered rest route!'); + assert.equal($('p').text(), 'Another prerendered rest route!'); }); it('should correctly match a nested static rest route index', async () => { @@ -255,7 +256,7 @@ describe('Route matching', () => { container.handle(req, res); const html = await text(); const $ = cheerio.load(html); - expect($('p').text()).to.equal('Nested prerendered rest route!'); + assert.equal($('p').text(), 'Nested prerendered rest route!'); }); it('should correctly match a nested static rest route', async () => { @@ -266,7 +267,7 @@ describe('Route matching', () => { container.handle(req, res); const html = await text(); const $ = cheerio.load(html); - expect($('p').text()).to.equal('Another nested prerendered rest route!'); + assert.equal($('p').text(), 'Another nested prerendered rest route!'); }); it('should correctly match a nested server rest route', async () => { @@ -278,7 +279,7 @@ describe('Route matching', () => { const html = await text(); const $ = cheerio.load(html); - expect($('p').text()).to.equal('Nested server rest route! slug: a-random-slug-was-matched'); + assert.equal($('p').text(), 'Nested server rest route! slug: a-random-slug-was-matched'); }); }); }); diff --git a/packages/astro/test/units/routing/route-sanitization.test.js b/packages/astro/test/units/routing/route-sanitization.nodetest.js similarity index 90% rename from packages/astro/test/units/routing/route-sanitization.test.js rename to packages/astro/test/units/routing/route-sanitization.nodetest.js index 14c9c382962a..c2367055ab14 100644 --- a/packages/astro/test/units/routing/route-sanitization.test.js +++ b/packages/astro/test/units/routing/route-sanitization.nodetest.js @@ -5,7 +5,8 @@ import { defaultLogger, } from '../test-utils.js'; import { fileURLToPath } from 'node:url'; -import { expect } from 'chai'; +import { describe, it, before, after } from 'node:test'; +import * as assert from 'node:assert/strict'; import { createContainer } from '../../../dist/core/dev/container.js'; import * as cheerio from 'cheerio'; import testAdapter from '../../test-adapter.js'; @@ -60,7 +61,7 @@ describe('Route sanitization', () => { container.handle(req, res); const html = await text(); const $ = cheerio.load(html); - expect($('p').text()).to.equal('Success!'); + assert.equal($('p').text(), 'Success!'); }); }); }); diff --git a/packages/astro/test/units/routing/trailing-slash.test.js b/packages/astro/test/units/routing/trailing-slash.nodetest.js similarity index 86% rename from packages/astro/test/units/routing/trailing-slash.test.js rename to packages/astro/test/units/routing/trailing-slash.nodetest.js index 72eed92ddfbd..292b32ff5179 100644 --- a/packages/astro/test/units/routing/trailing-slash.test.js +++ b/packages/astro/test/units/routing/trailing-slash.nodetest.js @@ -5,7 +5,8 @@ import { defaultLogger, } from '../test-utils.js'; import { fileURLToPath } from 'node:url'; -import { expect } from 'chai'; +import { describe, it, before, after } from 'node:test'; +import * as assert from 'node:assert/strict'; import { createContainer } from '../../../dist/core/dev/container.js'; import testAdapter from '../../test-adapter.js'; @@ -44,7 +45,7 @@ describe('trailingSlash', () => { }); container.handle(req, res); const json = await text(); - expect(json).to.equal('{"success":true}'); + assert.equal(json, '{"success":true}'); }); it('should NOT match the API route when request lacks a trailing slash', async () => { @@ -53,7 +54,7 @@ describe('trailingSlash', () => { url: '/api', }); container.handle(req, res); - expect(await text()).to.equal(''); - expect(res.statusCode).to.equal(404); + assert.equal(await text(), ''); + assert.equal(res.statusCode, 404); }); }); diff --git a/packages/astro/test/units/runtime/astro-global.nodetest.js b/packages/astro/test/units/runtime/astro-global.nodetest.js new file mode 100644 index 000000000000..a7959a4ec414 --- /dev/null +++ b/packages/astro/test/units/runtime/astro-global.nodetest.js @@ -0,0 +1,29 @@ +import { describe, it } from 'node:test'; +import * as assert from 'node:assert/strict'; +import { createAstro } from '../../../dist/runtime/server/index.js'; + +describe('astro global', () => { + it('Glob should error if passed incorrect value', async () => { + const Astro = createAstro(undefined); + assert.throws( + () => { + Astro.glob('./**/*.md'); + }, + { + message: /can only be used in/, + } + ); + }); + + it('Glob should error if has no results', async () => { + const Astro = createAstro(undefined); + assert.throws( + () => { + Astro.glob([], () => './**/*.md'); + }, + { + message: /did not return any matching files/, + } + ); + }); +}); diff --git a/packages/astro/test/units/runtime/astro-global.test.js b/packages/astro/test/units/runtime/astro-global.test.js deleted file mode 100644 index 59585de3956c..000000000000 --- a/packages/astro/test/units/runtime/astro-global.test.js +++ /dev/null @@ -1,18 +0,0 @@ -import { expect } from 'chai'; -import { createAstro } from '../../../dist/runtime/server/index.js'; - -describe('astro global', () => { - it('Glob should error if passed incorrect value', async () => { - const Astro = createAstro(undefined); - expect(() => { - Astro.glob('./**/*.md'); - }).to.throw(/can only be used in/); - }); - - it('Glob should error if has no results', async () => { - const Astro = createAstro(undefined); - expect(() => { - Astro.glob([], () => './**/*.md'); - }).to.throw(/did not return any matching files/); - }); -}); diff --git a/packages/astro/test/units/vite-plugin-astro-server/controller.test.js b/packages/astro/test/units/vite-plugin-astro-server/controller.nodetest.js similarity index 85% rename from packages/astro/test/units/vite-plugin-astro-server/controller.test.js rename to packages/astro/test/units/vite-plugin-astro-server/controller.nodetest.js index 0864d8964e19..345c2009dcf5 100644 --- a/packages/astro/test/units/vite-plugin-astro-server/controller.test.js +++ b/packages/astro/test/units/vite-plugin-astro-server/controller.nodetest.js @@ -1,4 +1,5 @@ -import { expect } from 'chai'; +import { describe, it } from 'node:test'; +import * as assert from 'node:assert/strict'; import { createLoader } from '../../../dist/core/module-loader/index.js'; import { createController, @@ -20,8 +21,8 @@ describe('vite-plugin-astro-server', () => { error = err; }, }); - expect(error).to.not.be.an('undefined'); - expect(error).to.be.an.instanceOf(Error); + assert.equal(typeof error !== 'undefined', true); + assert.equal(error instanceof Error, true); }); it('sets the state to error when an error occurs in the handler', async () => { @@ -34,7 +35,7 @@ describe('vite-plugin-astro-server', () => { }, onError() {}, }); - expect(controller.state.state).to.equal('error'); + assert.equal(controller.state.state, 'error'); }); it('calls reload when a file change occurs when in an error state', async () => { @@ -47,7 +48,7 @@ describe('vite-plugin-astro-server', () => { }); const controller = createController({ loader }); loader.events.emit('file-change'); - expect(reloads).to.equal(0); + assert.equal(reloads, 0); await runWithErrorHandling({ controller, pathname: '/', @@ -56,9 +57,9 @@ describe('vite-plugin-astro-server', () => { }, onError() {}, }); - expect(reloads).to.equal(0); + assert.equal(reloads, 0); loader.events.emit('file-change'); - expect(reloads).to.equal(1); + assert.equal(reloads, 1); }); it('does not call reload on file change if not in an error state', async () => { @@ -71,7 +72,7 @@ describe('vite-plugin-astro-server', () => { }); const controller = createController({ loader }); loader.events.emit('file-change'); - expect(reloads).to.equal(0); + assert.equal(reloads, 0); await runWithErrorHandling({ controller, pathname: '/', @@ -80,11 +81,11 @@ describe('vite-plugin-astro-server', () => { }, onError() {}, }); - expect(reloads).to.equal(0); + assert.equal(reloads, 0); loader.events.emit('file-change'); - expect(reloads).to.equal(1); + assert.equal(reloads, 1); loader.events.emit('file-change'); - expect(reloads).to.equal(2); + assert.equal(reloads, 2); await runWithErrorHandling({ controller, @@ -93,7 +94,7 @@ describe('vite-plugin-astro-server', () => { run() {}, }); loader.events.emit('file-change'); - expect(reloads).to.equal(2); + assert.equal(reloads, 2); }); it('Invalidates broken modules when a change occurs in an error state', async () => { @@ -124,7 +125,7 @@ describe('vite-plugin-astro-server', () => { loader.events.emit('file-change'); - expect(mods).to.deep.equal([ + assert.deepEqual(mods, [ { id: 'one', ssrError: null }, { id: 'two', ssrError: null }, { id: 'three', ssrError: null }, diff --git a/packages/astro/test/units/vite-plugin-astro-server/request.test.js b/packages/astro/test/units/vite-plugin-astro-server/request.nodetest.js similarity index 89% rename from packages/astro/test/units/vite-plugin-astro-server/request.test.js rename to packages/astro/test/units/vite-plugin-astro-server/request.nodetest.js index d1d0cf464e84..f79c86f84717 100644 --- a/packages/astro/test/units/vite-plugin-astro-server/request.test.js +++ b/packages/astro/test/units/vite-plugin-astro-server/request.nodetest.js @@ -1,4 +1,5 @@ -import { expect } from 'chai'; +import { describe, it } from 'node:test'; +import * as assert from 'node:assert/strict'; import { createLoader } from '../../../dist/core/module-loader/index.js'; import { createRouteManifest } from '../../../dist/core/routing/index.js'; import { createComponent, render } from '../../../dist/runtime/server/index.js'; @@ -65,12 +66,12 @@ describe('vite-plugin-astro-server', () => { incomingResponse: res, }); } catch (err) { - expect(err.message).to.be.undefined(); + assert.equal(err.message, undefined); } const html = await text(); - expect(res.statusCode).to.equal(200); - expect(html).to.include('
'); + assert.equal(res.statusCode, 200); + assert.equal(html.includes('
'), true); }); }); }); diff --git a/packages/astro/test/units/vite-plugin-astro-server/response.test.js b/packages/astro/test/units/vite-plugin-astro-server/response.nodetest.js similarity index 57% rename from packages/astro/test/units/vite-plugin-astro-server/response.test.js rename to packages/astro/test/units/vite-plugin-astro-server/response.nodetest.js index a47769556e40..bb7afbc3736a 100644 --- a/packages/astro/test/units/vite-plugin-astro-server/response.test.js +++ b/packages/astro/test/units/vite-plugin-astro-server/response.nodetest.js @@ -5,7 +5,8 @@ import { defaultLogger, } from '../test-utils.js'; import { fileURLToPath } from 'node:url'; -import { expect } from 'chai'; +import { describe, it, before, after } from 'node:test'; +import * as assert from 'node:assert/strict'; import { createContainer } from '../../../dist/core/dev/container.js'; import testAdapter from '../../test-adapter.js'; @@ -21,6 +22,28 @@ const fileSystem = { headers.append('Set-Cookie', 'world'); return new Response(null, { headers }); }`, + '/src/pages/streaming.js': `export const GET = ({ locals }) => { + let sentChunks = 0; + + const readableStream = new ReadableStream({ + async pull(controller) { + if (sentChunks === 3) return controller.close(); + else sentChunks++; + + await new Promise(resolve => setTimeout(resolve, 1000)); + controller.enqueue(new TextEncoder().encode('hello')); + }, + cancel() { + locals.cancelledByTheServer = true; + } + }); + + return new Response(readableStream, { + headers: { + "Content-Type": "text/event-stream" + } + }) + }`, }; describe('endpoints', () => { @@ -53,11 +76,30 @@ describe('endpoints', () => { container.handle(req, res); await done; const headers = res.getHeaders(); - expect(headers).to.deep.equal({ + assert.deepEqual(headers, { 'access-control-allow-origin': '*', 'x-single': 'single', 'x-triple': 'one, two, three', 'set-cookie': ['hello', 'world'], }); }); + + it('Headers with multiple values (set-cookie special case)', async () => { + const { req, res, done } = createRequestAndResponse({ + method: 'GET', + url: '/streaming', + }); + + const locals = { cancelledByTheServer: false }; + req[Symbol.for('astro.locals')] = locals; + + container.handle(req, res); + + await new Promise((resolve) => setTimeout(resolve, 500)); + res.emit('close'); + + await done; + + assert.equal(locals.cancelledByTheServer, true); + }); }); diff --git a/packages/astro/test/units/vite-plugin-astro/compile.test.js b/packages/astro/test/units/vite-plugin-astro/compile.nodetest.js similarity index 78% rename from packages/astro/test/units/vite-plugin-astro/compile.test.js rename to packages/astro/test/units/vite-plugin-astro/compile.nodetest.js index c37506cfbb9a..08b6c2810a7d 100644 --- a/packages/astro/test/units/vite-plugin-astro/compile.test.js +++ b/packages/astro/test/units/vite-plugin-astro/compile.nodetest.js @@ -1,4 +1,5 @@ -import { expect } from 'chai'; +import { describe, it } from 'node:test'; +import * as assert from 'node:assert/strict'; import { resolveConfig } from 'vite'; import { compileAstro } from '../../../dist/vite-plugin-astro/compile.js'; import { init, parse } from 'es-module-lexer'; @@ -25,7 +26,7 @@ async function compile(source, id) { describe('astro full compile', () => { it('should compile a single file', async () => { const result = await compile(`

Hello World

`, '/src/components/index.astro'); - expect(result.code).to.be.ok; + assert.ok(result.code); }); it('should compile typescript', async () => { @@ -38,7 +39,7 @@ const name: string = 'world'

Hello {name}

`, '/src/components/index.astro' ); - expect(result.code).to.be.ok; + assert.ok(result.code); }); it('should error on invalid js', async () => { @@ -54,9 +55,9 @@ const name = 'world '/src/components/index.astro' ); } catch (e) { - expect(e.message).to.include('Unterminated string literal'); + assert.equal(e.message.includes('Unterminated string literal'), true); } - expect(result).to.be.undefined; + assert.equal(result, undefined); }); it('has file and url exports for markdwon compat', async () => { @@ -64,8 +65,8 @@ const name = 'world await init; const [, exports] = parse(result.code); const names = exports.map((e) => e.n); - expect(names).to.include('default'); - expect(names).to.include('file'); - expect(names).to.include('url'); + assert.equal(names.includes('default'), true); + assert.equal(names.includes('file'), true); + assert.equal(names.includes('url'), true); }); }); diff --git a/packages/astro/test/units/vite-plugin-scanner/scan.test.js b/packages/astro/test/units/vite-plugin-scanner/scan.nodetest.js similarity index 61% rename from packages/astro/test/units/vite-plugin-scanner/scan.test.js rename to packages/astro/test/units/vite-plugin-scanner/scan.nodetest.js index 3d812a893cf1..d1e389de0c55 100644 --- a/packages/astro/test/units/vite-plugin-scanner/scan.test.js +++ b/packages/astro/test/units/vite-plugin-scanner/scan.nodetest.js @@ -1,59 +1,63 @@ -import { expect } from 'chai'; +import { describe, it, before, after } from 'node:test'; +import * as assert from 'node:assert/strict'; import { scan } from '../../../dist/vite-plugin-scanner/scan.js'; describe('astro scan', () => { it('should return empty object', async () => { const result = await scan(`export {}`, '/src/components/index.astro'); - expect(Object.keys(result).length).to.equal(0); + assert.equal(Object.keys(result).length, 0); }); it('recognizes constant boolean literal (false)', async () => { const result = await scan(`export const prerender = true;`, '/src/components/index.astro'); - expect(result.prerender).to.equal(true); + assert.equal(result.prerender, true); }); it('recognizes constant boolean literal (false)', async () => { const result = await scan(`export const prerender = false;`, '/src/components/index.astro'); - expect(result.prerender).to.equal(false); + assert.equal(result.prerender, false); }); it("recognizes single quoted boolean ('true')", async () => { const result = await scan(`export const prerender = 'true';`, '/src/components/index.astro'); - expect(result.prerender).to.equal(true); + assert.equal(result.prerender, true); }); it('recognizes double quoted boolean ("true")', async () => { const result = await scan(`export const prerender = "true";`, '/src/components/index.astro'); - expect(result.prerender).to.equal(true); + assert.equal(result.prerender, true); }); it('recognizes double quoted boolean ("false")', async () => { const result = await scan(`export const prerender = "false";`, '/src/components/index.astro'); - expect(result.prerender).to.equal(false); + assert.equal(result.prerender, false); }); it("recognizes single quoted boolean ('false')", async () => { const result = await scan(`export const prerender = 'false';`, '/src/components/index.astro'); - expect(result.prerender).to.equal(false); + assert.equal(result.prerender, false); }); it('recognizes number (1)', async () => { const result = await scan(`export const prerender = 1;`, '/src/components/index.astro'); - expect(result.prerender).to.equal(true); + assert.equal(result.prerender, true); }); it('recognizes number (0)', async () => { const result = await scan(`export const prerender = 0;`, '/src/components/index.astro'); - expect(result.prerender).to.equal(false); + assert.equal(result.prerender, false); }); it('throws on let boolean literal', async () => { try { await scan(`export let prerender = true;`, '/src/components/index.astro'); - expect(false).to.be.true; + assert.equal(false).to.be.true; } catch (e) { - expect(e.message).to.contain( - `A \`prerender\` export has been detected, but its value cannot be statically analyzed.` + assert.equal( + e.message.includes( + `A \`prerender\` export has been detected, but its value cannot be statically analyzed.` + ), + true ); } }); @@ -61,10 +65,13 @@ describe('astro scan', () => { it('throws on var boolean literal', async () => { try { await scan(`export var prerender = true;`, '/src/components/index.astro'); - expect(false).to.be.true; + assert.equal(false).to.be.true; } catch (e) { - expect(e.message).to.contain( - `A \`prerender\` export has been detected, but its value cannot be statically analyzed.` + assert.equal( + e.message.includes( + `A \`prerender\` export has been detected, but its value cannot be statically analyzed.` + ), + true ); } }); @@ -72,10 +79,13 @@ describe('astro scan', () => { it('throws on unknown values I', async () => { try { await scan(`export const prerender = !!value;`, '/src/components/index.astro'); - expect(false).to.be.true; + assert.equal(false).to.be.true; } catch (e) { - expect(e.message).to.contain( - `A \`prerender\` export has been detected, but its value cannot be statically analyzed.` + assert.equal( + e.message.includes( + `A \`prerender\` export has been detected, but its value cannot be statically analyzed.` + ), + true ); } }); @@ -83,10 +93,13 @@ describe('astro scan', () => { it('throws on unknown values II', async () => { try { await scan(`export const prerender = value;`, '/src/components/index.astro'); - expect(false).to.be.true; + assert.equal(false).to.be.true; } catch (e) { - expect(e.message).to.contain( - `A \`prerender\` export has been detected, but its value cannot be statically analyzed.` + assert.equal( + e.message.includes( + `A \`prerender\` export has been detected, but its value cannot be statically analyzed.` + ), + true ); } }); @@ -97,10 +110,13 @@ describe('astro scan', () => { `export let prerender = undefined; prerender = true;`, '/src/components/index.astro' ); - expect(false).to.be.true; + assert.equal(false).to.be.true; } catch (e) { - expect(e.message).to.contain( - `A \`prerender\` export has been detected, but its value cannot be statically analyzed.` + assert.equal( + e.message.includes( + `A \`prerender\` export has been detected, but its value cannot be statically analyzed.` + ), + true ); } }); @@ -108,10 +124,13 @@ describe('astro scan', () => { it('throws on unknown values IV', async () => { try { await scan(`let prerender = true; export { prerender }`, '/src/components/index.astro'); - expect(false).to.be.true; + assert.equal(false).to.be.true; } catch (e) { - expect(e.message).to.contain( - `A \`prerender\` export has been detected, but its value cannot be statically analyzed.` + assert.equal( + e.message.includes( + `A \`prerender\` export has been detected, but its value cannot be statically analyzed.` + ), + true ); } }); diff --git a/packages/astro/test/vue-component.nodetest.js b/packages/astro/test/vue-component.nodetest.js new file mode 100644 index 000000000000..c2d753f89eca --- /dev/null +++ b/packages/astro/test/vue-component.nodetest.js @@ -0,0 +1,73 @@ +import assert from 'node:assert/strict'; +import { before, describe, it, after } from 'node:test'; +import * as cheerio from 'cheerio'; +import { isWindows, loadFixture } from './test-utils.js'; + +describe.skip('Vue component build', { todo: 'This test currently times out, investigate' }, () => { + let fixture; + + before(async () => { + fixture = await loadFixture({ + root: './fixtures/vue-component/', + }); + await fixture.build(); + }); + + it('Can load Vue', async () => { + const html = await fixture.readFile('/index.html'); + const $ = cheerio.load(html); + + const allPreValues = $('pre') + .toArray() + .map((el) => $(el).text()); + + // test 1: renders all components correctly + assert.deepEqual(allPreValues, ['0', '1', '1', '1', '10', '100', '1000']); + + // test 2: renders 3 s + assert.equal($('astro-island').length, 6); + + // test 3: all s have uid attributes + assert.equal($('astro-island[uid]').length, 6); + + // test 4: treats as a custom element + assert.equal($('my-button').length, 7); + + // test 5: components with identical render output and props have been deduplicated + const uniqueRootUIDs = $('astro-island').map((i, el) => $(el).attr('uid')); + assert.equal(new Set(uniqueRootUIDs).size, 5); + + // test 6: import public files work + assert.ok($('#vue-img')); + }); +}); + +if (!isWindows) { + describe.skip('Vue component dev', { todo: 'This test currently times out, investigate' }, () => { + let devServer; + let fixture; + + before(async () => { + fixture = await loadFixture({ + root: './fixtures/vue-component/', + }); + devServer = await fixture.startDevServer(); + }); + + after(async () => { + await devServer.stop(); + }); + + it('scripts proxy correctly', async () => { + const html = await fixture.fetch('/').then((res) => res.text()); + const $ = cheerio.load(html); + + for (const script of $('script').toArray()) { + const { src } = script.attribs; + if (!src) continue; + const response = await fixture.fetch(src); + assert.equal(response.status, 200, `404: ${src}`); + } + }); + }); +} diff --git a/packages/astro/test/vue-component.test.js b/packages/astro/test/vue-component.test.js deleted file mode 100644 index 07d2cdad7dc6..000000000000 --- a/packages/astro/test/vue-component.test.js +++ /dev/null @@ -1,72 +0,0 @@ -import { expect } from 'chai'; -import * as cheerio from 'cheerio'; -import { isWindows, loadFixture } from './test-utils.js'; - -describe('Vue component', () => { - let fixture; - - before(async () => { - fixture = await loadFixture({ - root: './fixtures/vue-component/', - }); - }); - - describe('build', () => { - before(async () => { - await fixture.build(); - }); - - it('Can load Vue', async () => { - const html = await fixture.readFile('/index.html'); - const $ = cheerio.load(html); - - const allPreValues = $('pre') - .toArray() - .map((el) => $(el).text()); - - // test 1: renders all components correctly - expect(allPreValues).to.deep.equal(['0', '1', '1', '1', '10', '100', '1000']); - - // test 2: renders 3 s - expect($('astro-island')).to.have.lengthOf(6); - - // test 3: all s have uid attributes - expect($('astro-island[uid]')).to.have.lengthOf(6); - - // test 4: treats as a custom element - expect($('my-button')).to.have.lengthOf(7); - - // test 5: components with identical render output and props have been deduplicated - const uniqueRootUIDs = $('astro-island').map((i, el) => $(el).attr('uid')); - expect(new Set(uniqueRootUIDs).size).to.equal(5); - - // test 6: import public files work - expect($('#vue-img')).to.be.ok; - }); - }); - - if (isWindows) return; - - describe('dev', () => { - let devServer; - - before(async () => { - devServer = await fixture.startDevServer(); - }); - - after(async () => { - await devServer.stop(); - }); - - it('scripts proxy correctly', async () => { - const html = await fixture.fetch('/').then((res) => res.text()); - const $ = cheerio.load(html); - - for (const script of $('script').toArray()) { - const { src } = script.attribs; - if (!src) continue; - expect((await fixture.fetch(src)).status, `404: ${src}`).to.equal(200); - } - }); - }); -}); diff --git a/packages/astro/test/vue-jsx.test.js b/packages/astro/test/vue-jsx.nodetest.js similarity index 75% rename from packages/astro/test/vue-jsx.test.js rename to packages/astro/test/vue-jsx.nodetest.js index 9307410fe8f5..5ab00da8cec3 100644 --- a/packages/astro/test/vue-jsx.test.js +++ b/packages/astro/test/vue-jsx.nodetest.js @@ -1,4 +1,5 @@ -import { expect } from 'chai'; +import assert from 'node:assert/strict'; +import { before, describe, it } from 'node:test'; import * as cheerio from 'cheerio'; import { loadFixture } from './test-utils.js'; @@ -24,7 +25,7 @@ describe('Vue JSX', () => { .toArray() .map((el) => $(el).text()); - expect(allPreValues).to.deep.equal(['2345', '0', '1', '1', '1', '10', '100', '1000']); + assert.deepEqual(allPreValues, ['2345', '0', '1', '1', '1', '10', '100', '1000']); }); }); }); diff --git a/packages/astro/test/vue-with-multi-renderer.test.js b/packages/astro/test/vue-with-multi-renderer.nodetest.js similarity index 70% rename from packages/astro/test/vue-with-multi-renderer.test.js rename to packages/astro/test/vue-with-multi-renderer.nodetest.js index 78b243d78711..fe5b0f9e1811 100644 --- a/packages/astro/test/vue-with-multi-renderer.test.js +++ b/packages/astro/test/vue-with-multi-renderer.nodetest.js @@ -1,4 +1,5 @@ -import { expect } from 'chai'; +import assert from 'node:assert/strict'; +import { before, describe, it } from 'node:test'; import { loadFixture } from './test-utils.js'; describe('Vue with multi-renderer', () => { @@ -14,7 +15,7 @@ describe('Vue with multi-renderer', () => { try { await fixture.build(); } catch (e) { - expect(e).to.equal(undefined, `Should not throw`); + assert.equal(e, undefined, `Should not throw`); } }); }); diff --git a/packages/create-astro/package.json b/packages/create-astro/package.json index e9bd0bc2390a..570b86ecde30 100644 --- a/packages/create-astro/package.json +++ b/packages/create-astro/package.json @@ -22,7 +22,7 @@ "build": "astro-scripts build \"src/index.ts\" --bundle && tsc", "build:ci": "astro-scripts build \"src/index.ts\" --bundle", "dev": "astro-scripts dev \"src/**/*.ts\"", - "test": "mocha --exit --timeout 20000 --parallel" + "test": "astro-scripts test \"test/**/*.test.js\"" }, "files": [ "dist", diff --git a/packages/create-astro/test/context.test.js b/packages/create-astro/test/context.test.js index 11341741733f..654733e6c403 100644 --- a/packages/create-astro/test/context.test.js +++ b/packages/create-astro/test/context.test.js @@ -1,62 +1,73 @@ -import { expect } from 'chai'; - +import assert from 'node:assert/strict'; +import { describe, it } from 'node:test'; import os from 'node:os'; import { getContext } from '../dist/index.js'; - describe('context', () => { it('no arguments', async () => { const ctx = await getContext([]); - expect(ctx.projectName).to.be.undefined; - expect(ctx.template).to.be.undefined; - expect(ctx.skipHouston).to.eq(os.platform() === 'win32'); - expect(ctx.dryRun).to.be.undefined; + assert.ok(!ctx.projectName); + assert.ok(!ctx.template); + assert.deepStrictEqual(ctx.skipHouston, os.platform() === 'win32'); + assert.ok(!ctx.dryRun); }); + it('project name', async () => { const ctx = await getContext(['foobar']); - expect(ctx.projectName).to.eq('foobar'); + assert.deepStrictEqual(ctx.projectName, 'foobar'); }); + it('template', async () => { const ctx = await getContext(['--template', 'minimal']); - expect(ctx.template).to.eq('minimal'); + assert.deepStrictEqual(ctx.template, 'minimal'); }); + it('skip houston (explicit)', async () => { const ctx = await getContext(['--skip-houston']); - expect(ctx.skipHouston).to.eq(true); + assert.deepStrictEqual(ctx.skipHouston, true); }); + it('skip houston (yes)', async () => { const ctx = await getContext(['-y']); - expect(ctx.skipHouston).to.eq(true); + assert.deepStrictEqual(ctx.skipHouston, true); }); + it('skip houston (no)', async () => { const ctx = await getContext(['-n']); - expect(ctx.skipHouston).to.eq(true); + assert.deepStrictEqual(ctx.skipHouston, true); }); + it('skip houston (install)', async () => { const ctx = await getContext(['--install']); - expect(ctx.skipHouston).to.eq(true); + assert.deepStrictEqual(ctx.skipHouston, true); }); + it('dry run', async () => { const ctx = await getContext(['--dry-run']); - expect(ctx.dryRun).to.eq(true); + assert.deepStrictEqual(ctx.dryRun, true); }); + it('install', async () => { const ctx = await getContext(['--install']); - expect(ctx.install).to.eq(true); + assert.deepStrictEqual(ctx.install, true); }); + it('no install', async () => { const ctx = await getContext(['--no-install']); - expect(ctx.install).to.eq(false); + assert.deepStrictEqual(ctx.install, false); }); + it('git', async () => { const ctx = await getContext(['--git']); - expect(ctx.git).to.eq(true); + assert.deepStrictEqual(ctx.git, true); }); + it('no git', async () => { const ctx = await getContext(['--no-git']); - expect(ctx.git).to.eq(false); + assert.deepStrictEqual(ctx.git, false); }); + it('typescript', async () => { const ctx = await getContext(['--typescript', 'strict']); - expect(ctx.typescript).to.eq('strict'); + assert.deepStrictEqual(ctx.typescript, 'strict'); }); }); diff --git a/packages/create-astro/test/dependencies.test.js b/packages/create-astro/test/dependencies.test.js index 705cf8354741..046e96591b91 100644 --- a/packages/create-astro/test/dependencies.test.js +++ b/packages/create-astro/test/dependencies.test.js @@ -1,8 +1,7 @@ -import { expect } from 'chai'; - +import assert from 'node:assert/strict'; import { dependencies } from '../dist/index.js'; +import { describe, it } from 'node:test'; import { setup } from './utils.js'; - describe('dependencies', () => { const fixture = setup(); @@ -14,8 +13,10 @@ describe('dependencies', () => { dryRun: true, prompt: () => ({ deps: true }), }; + await dependencies(context); - expect(fixture.hasMessage('Skipping dependency installation')).to.be.true; + + assert.ok(fixture.hasMessage('Skipping dependency installation')); }); it('prompt yes', async () => { @@ -26,22 +27,27 @@ describe('dependencies', () => { prompt: () => ({ deps: true }), install: undefined, }; + await dependencies(context); - expect(fixture.hasMessage('Skipping dependency installation')).to.be.true; - expect(context.install).to.eq(true); + + assert.ok(fixture.hasMessage('Skipping dependency installation')); + assert.equal(context.install, true); }); it('prompt no', async () => { const context = { cwd: '', + install: true, packageManager: 'npm', dryRun: true, prompt: () => ({ deps: false }), install: undefined, }; + await dependencies(context); - expect(fixture.hasMessage('Skipping dependency installation')).to.be.true; - expect(context.install).to.eq(false); + + assert.ok(fixture.hasMessage('Skipping dependency installation')); + assert.equal(context.install, false); }); it('--install', async () => { @@ -53,11 +59,11 @@ describe('dependencies', () => { prompt: () => ({ deps: false }), }; await dependencies(context); - expect(fixture.hasMessage('Skipping dependency installation')).to.be.true; - expect(context.install).to.eq(true); + assert.ok(fixture.hasMessage('Skipping dependency installation')); + assert.equal(context.install, true); }); - it('--no-install', async () => { + it('--no-install ', async () => { const context = { cwd: '', install: false, @@ -65,8 +71,10 @@ describe('dependencies', () => { dryRun: true, prompt: () => ({ deps: false }), }; + await dependencies(context); - expect(fixture.hasMessage('Skipping dependency installation')).to.be.true; - expect(context.install).to.eq(false); + + assert.ok(fixture.hasMessage('Skipping dependency installation')); + assert.equal(context.install, false); }); }); diff --git a/packages/create-astro/test/fixtures/not-empty/package.json b/packages/create-astro/test/fixtures/not-empty/package.json index dad4a5e5c0f8..20127bbd3351 100644 --- a/packages/create-astro/test/fixtures/not-empty/package.json +++ b/packages/create-astro/test/fixtures/not-empty/package.json @@ -6,4 +6,4 @@ "build": "astro check && astro build", "preview": "astro preview" } -} \ No newline at end of file +} diff --git a/packages/create-astro/test/git.test.js b/packages/create-astro/test/git.test.js index d05ad5bdc19d..f1c8eba0e8ba 100644 --- a/packages/create-astro/test/git.test.js +++ b/packages/create-astro/test/git.test.js @@ -1,4 +1,5 @@ -import { expect } from 'chai'; +import assert from 'node:assert/strict'; +import { describe, it, before, after } from 'node:test'; import { mkdir, writeFile } from 'node:fs/promises'; import { rmSync } from 'node:fs'; @@ -12,21 +13,20 @@ describe('git', () => { const context = { cwd: '', dryRun: true, prompt: () => ({ git: false }) }; await git(context); - expect(fixture.hasMessage('Skipping Git initialization')).to.be.true; + assert.ok(fixture.hasMessage('Skipping Git initialization')); }); it('yes (--dry-run)', async () => { const context = { cwd: '', dryRun: true, prompt: () => ({ git: true }) }; await git(context); - - expect(fixture.hasMessage('Skipping Git initialization')).to.be.true; + assert.ok(fixture.hasMessage('Skipping Git initialization')); }); it('no (--dry-run)', async () => { const context = { cwd: '', dryRun: true, prompt: () => ({ git: false }) }; await git(context); - expect(fixture.hasMessage('Skipping Git initialization')).to.be.true; + assert.ok(fixture.hasMessage('Skipping Git initialization')); }); }); @@ -48,7 +48,7 @@ describe('git initialized', () => { }; await git(context); - expect(fixture.hasMessage('Git has already been initialized')).to.be.true; + assert.ok(fixture.hasMessage('Git has already been initialized')); }); after(() => { diff --git a/packages/create-astro/test/intro.test.js b/packages/create-astro/test/intro.test.js index 9014da45709a..d042dad7fc6b 100644 --- a/packages/create-astro/test/intro.test.js +++ b/packages/create-astro/test/intro.test.js @@ -1,5 +1,5 @@ -import { expect } from 'chai'; - +import assert from 'node:assert/strict'; +import { describe, it } from 'node:test'; import { intro } from '../dist/index.js'; import { setup } from './utils.js'; @@ -8,13 +8,13 @@ describe('intro', () => { it('no arguments', async () => { await intro({ skipHouston: false, version: '0.0.0', username: 'user' }); - expect(fixture.hasMessage('Houston:')).to.be.true; - expect(fixture.hasMessage('Welcome to astro v0.0.0')).to.be.true; + assert.ok(fixture.hasMessage('Houston:')); + assert.ok(fixture.hasMessage('Welcome to astro v0.0.0')); }); it('--skip-houston', async () => { await intro({ skipHouston: true, version: '0.0.0', username: 'user' }); - expect(fixture.length()).to.eq(1); - expect(fixture.hasMessage('Houston:')).to.be.false; - expect(fixture.hasMessage('Launch sequence initiated')).to.be.true; + assert.equal(fixture.length(), 1); + assert.ok(!fixture.hasMessage('Houston:')); + assert.ok(fixture.hasMessage('Launch sequence initiated')); }); }); diff --git a/packages/create-astro/test/next.test.js b/packages/create-astro/test/next.test.js index 07de90d50edb..5b9b22b30632 100644 --- a/packages/create-astro/test/next.test.js +++ b/packages/create-astro/test/next.test.js @@ -1,5 +1,5 @@ -import { expect } from 'chai'; - +import assert from 'node:assert/strict'; +import { describe, it } from 'node:test'; import { next } from '../dist/index.js'; import { setup } from './utils.js'; @@ -8,13 +8,13 @@ describe('next steps', () => { it('no arguments', async () => { await next({ skipHouston: false, cwd: './it/fixtures/not-empty', packageManager: 'npm' }); - expect(fixture.hasMessage('Liftoff confirmed.')).to.be.true; - expect(fixture.hasMessage('npm run dev')).to.be.true; - expect(fixture.hasMessage('Good luck out there, astronaut!')).to.be.true; + assert.ok(fixture.hasMessage('Liftoff confirmed.')); + assert.ok(fixture.hasMessage('npm run dev')); + assert.ok(fixture.hasMessage('Good luck out there, astronaut!')); }); it('--skip-houston', async () => { await next({ skipHouston: true, cwd: './it/fixtures/not-empty', packageManager: 'npm' }); - expect(fixture.hasMessage('Good luck out there, astronaut!')).to.be.false; + assert.ok(!fixture.hasMessage('Good luck out there, astronaut!')); }); }); diff --git a/packages/create-astro/test/project-name.test.js b/packages/create-astro/test/project-name.test.js index 905f4a158d8a..74196a35ae81 100644 --- a/packages/create-astro/test/project-name.test.js +++ b/packages/create-astro/test/project-name.test.js @@ -1,5 +1,5 @@ -import { expect } from 'chai'; - +import assert from 'node:assert/strict'; +import { describe, it } from 'node:test'; import { projectName } from '../dist/index.js'; import { setup } from './utils.js'; @@ -9,25 +9,22 @@ describe('project name', async () => { it('pass in name', async () => { const context = { projectName: '', cwd: './foo/bar/baz', prompt: () => {} }; await projectName(context); - - expect(context.cwd).to.eq('./foo/bar/baz'); - expect(context.projectName).to.eq('baz'); + assert.equal(context.cwd, './foo/bar/baz'); + assert.equal(context.projectName, 'baz'); }); it('dot', async () => { const context = { projectName: '', cwd: '.', prompt: () => ({ name: 'foobar' }) }; await projectName(context); - - expect(fixture.hasMessage('"." is not empty!')).to.be.true; - expect(context.projectName).to.eq('foobar'); + assert.ok(fixture.hasMessage('"." is not empty!')); + assert.equal(context.projectName, 'foobar'); }); it('dot slash', async () => { const context = { projectName: '', cwd: './', prompt: () => ({ name: 'foobar' }) }; await projectName(context); - - expect(fixture.hasMessage('"./" is not empty!')).to.be.true; - expect(context.projectName).to.eq('foobar'); + assert.ok(fixture.hasMessage('"./" is not empty!')); + assert.equal(context.projectName, 'foobar'); }); it('empty', async () => { @@ -37,9 +34,8 @@ describe('project name', async () => { prompt: () => ({ name: 'foobar' }), }; await projectName(context); - - expect(fixture.hasMessage('"./test/fixtures/empty" is not empty!')).to.be.false; - expect(context.projectName).to.eq('empty'); + assert.ok(!fixture.hasMessage('"./test/fixtures/empty" is not empty!')); + assert.equal(context.projectName, 'empty'); }); it('not empty', async () => { @@ -49,59 +45,48 @@ describe('project name', async () => { prompt: () => ({ name: 'foobar' }), }; await projectName(context); - - expect(fixture.hasMessage('"./test/fixtures/not-empty" is not empty!')).to.be.true; - expect(context.projectName).to.eq('foobar'); + assert.ok(fixture.hasMessage('"./test/fixtures/not-empty" is not empty!')); + assert.equal(context.projectName, 'foobar'); }); it('basic', async () => { const context = { projectName: '', cwd: '', prompt: () => ({ name: 'foobar' }) }; await projectName(context); - - expect(context.cwd).to.eq('foobar'); - expect(context.projectName).to.eq('foobar'); + assert.equal(context.cwd, 'foobar'); + assert.equal(context.projectName, 'foobar'); }); it('blank space', async () => { - const context = { projectName: '', cwd: '', prompt: () => ({ name: 'foobar ' }) }; + const context = { projectName: '', cwd: '', prompt: () => ({ name: 'foobar' }) }; await projectName(context); - - expect(context.cwd).to.eq('foobar'); - expect(context.projectName).to.eq('foobar'); + assert.equal(context.cwd, 'foobar'); + assert.equal(context.projectName, 'foobar'); }); it('normalize', async () => { const context = { projectName: '', cwd: '', prompt: () => ({ name: 'Invalid Name' }) }; await projectName(context); - - expect(context.cwd).to.eq('Invalid Name'); - expect(context.projectName).to.eq('invalid-name'); + assert.equal(context.cwd, 'Invalid Name'); + assert.equal(context.projectName, 'invalid-name'); }); it('remove leading/trailing dashes', async () => { const context = { projectName: '', cwd: '', prompt: () => ({ name: '(invalid)' }) }; await projectName(context); - - expect(context.projectName).to.eq('invalid'); + assert.equal(context.projectName, 'invalid'); }); it('handles scoped packages', async () => { const context = { projectName: '', cwd: '', prompt: () => ({ name: '@astro/site' }) }; await projectName(context); - - expect(context.cwd).to.eq('@astro/site'); - expect(context.projectName).to.eq('@astro/site'); + assert.equal(context.cwd, '@astro/site'); + assert.equal(context.projectName, '@astro/site'); }); it('--yes', async () => { - const context = { - projectName: '', - cwd: './foo/bar/baz', - yes: true, - prompt: () => {}, - }; + const context = { projectName: '', cwd: './foo/bar/baz', yes: true, prompt: () => {} }; await projectName(context); - expect(context.projectName).to.eq('baz'); + assert.equal(context.projectName, 'baz'); }); it('dry run with name', async () => { @@ -112,7 +97,7 @@ describe('project name', async () => { prompt: () => {}, }; await projectName(context); - expect(context.projectName).to.eq('baz'); + assert.equal(context.projectName, 'baz'); }); it('dry run with dot', async () => { @@ -123,7 +108,7 @@ describe('project name', async () => { prompt: () => ({ name: 'foobar' }), }; await projectName(context); - expect(context.projectName).to.eq('foobar'); + assert.equal(context.projectName, 'foobar'); }); it('dry run with empty', async () => { @@ -134,6 +119,6 @@ describe('project name', async () => { prompt: () => ({ name: 'foobar' }), }; await projectName(context); - expect(context.projectName).to.eq('empty'); + assert.equal(context.projectName, 'empty'); }); }); diff --git a/packages/create-astro/test/template.test.js b/packages/create-astro/test/template.test.js index aef7e194459d..821ac9c2e9ac 100644 --- a/packages/create-astro/test/template.test.js +++ b/packages/create-astro/test/template.test.js @@ -1,43 +1,39 @@ -import { expect } from 'chai'; - +import assert from 'node:assert/strict'; +import { describe, it } from 'node:test'; import { template } from '../dist/index.js'; import { setup } from './utils.js'; -describe('template', () => { +describe('template', async () => { const fixture = setup(); it('none', async () => { const context = { template: '', cwd: '', dryRun: true, prompt: () => ({ template: 'blog' }) }; await template(context); - - expect(fixture.hasMessage('Skipping template copying')).to.be.true; - expect(context.template).to.eq('blog'); + assert.ok(fixture.hasMessage('Skipping template copying')); + assert.equal(context.template, 'blog'); }); it('minimal (--dry-run)', async () => { const context = { template: 'minimal', cwd: '', dryRun: true, prompt: () => {} }; await template(context); - expect(fixture.hasMessage('Using minimal as project template')).to.be.true; + assert.ok(fixture.hasMessage('Using minimal as project template')); }); it('basics (--dry-run)', async () => { const context = { template: 'basics', cwd: '', dryRun: true, prompt: () => {} }; await template(context); - - expect(fixture.hasMessage('Using basics as project template')).to.be.true; + assert.ok(fixture.hasMessage('Using basics as project template')); }); it('blog (--dry-run)', async () => { const context = { template: 'blog', cwd: '', dryRun: true, prompt: () => {} }; await template(context); - - expect(fixture.hasMessage('Using blog as project template')).to.be.true; + assert.ok(fixture.hasMessage('Using blog as project template')); }); it('minimal (--yes)', async () => { const context = { template: 'minimal', cwd: '', dryRun: true, yes: true, prompt: () => {} }; await template(context); - - expect(fixture.hasMessage('Using minimal as project template')).to.be.true; + assert.ok(fixture.hasMessage('Using minimal as project template')); }); }); diff --git a/packages/create-astro/test/typescript.test.js b/packages/create-astro/test/typescript.test.js index 461a3ed63745..067957676e86 100644 --- a/packages/create-astro/test/typescript.test.js +++ b/packages/create-astro/test/typescript.test.js @@ -1,26 +1,26 @@ -import { expect } from 'chai'; - +import assert from 'node:assert/strict'; +import { describe, it, beforeEach } from 'node:test'; import fs from 'node:fs'; import { fileURLToPath } from 'node:url'; import { typescript, setupTypeScript } from '../dist/index.js'; import { setup, resetFixtures } from './utils.js'; -describe('typescript', () => { +describe('typescript', async () => { const fixture = setup(); it('none', async () => { const context = { cwd: '', dryRun: true, prompt: () => ({ ts: 'strict', useTs: true }) }; await typescript(context); - expect(fixture.hasMessage('Skipping TypeScript setup')).to.be.true; + assert.ok(fixture.hasMessage('Skipping TypeScript setup')); }); it('use false', async () => { const context = { cwd: '', dryRun: true, prompt: () => ({ ts: 'strict', useTs: false }) }; await typescript(context); - expect(fixture.hasMessage('No worries')).to.be.true; + assert.ok(fixture.hasMessage('No worries')); }); it('strict', async () => { @@ -31,9 +31,8 @@ describe('typescript', () => { prompt: () => ({ ts: 'strict' }), }; await typescript(context); - - expect(fixture.hasMessage('Using strict TypeScript configuration')).to.be.true; - expect(fixture.hasMessage('Skipping TypeScript setup')).to.be.true; + assert.ok(fixture.hasMessage('Using strict TypeScript configuration')); + assert.ok(fixture.hasMessage('Skipping TypeScript setup')); }); it('default', async () => { @@ -44,9 +43,8 @@ describe('typescript', () => { prompt: () => ({ ts: 'strict' }), }; await typescript(context); - - expect(fixture.hasMessage('Using default TypeScript configuration')).to.be.true; - expect(fixture.hasMessage('Skipping TypeScript setup')).to.be.true; + assert.ok(fixture.hasMessage('Using default TypeScript configuration')); + assert.ok(fixture.hasMessage('Skipping TypeScript setup')); }); it('relaxed', async () => { @@ -57,9 +55,8 @@ describe('typescript', () => { prompt: () => ({ ts: 'strict' }), }; await typescript(context); - - expect(fixture.hasMessage('Using relaxed TypeScript configuration')).to.be.true; - expect(fixture.hasMessage('Skipping TypeScript setup')).to.be.true; + assert.ok(fixture.hasMessage('Using relaxed TypeScript configuration')); + assert.ok(fixture.hasMessage('Skipping TypeScript setup')); }); it('other', async () => { @@ -78,11 +75,11 @@ describe('typescript', () => { } catch (e) { err = e; } - expect(err).to.eq(1); + assert.equal(err, 1); }); }); -describe('typescript: setup tsconfig', () => { +describe('typescript: setup tsconfig', async () => { beforeEach(() => resetFixtures()); it('none', async () => { @@ -90,7 +87,7 @@ describe('typescript: setup tsconfig', () => { const tsconfig = new URL('./tsconfig.json', root); await setupTypeScript('strict', { cwd: fileURLToPath(root) }); - expect(JSON.parse(fs.readFileSync(tsconfig, { encoding: 'utf-8' }))).to.deep.eq({ + assert.deepEqual(JSON.parse(fs.readFileSync(tsconfig, { encoding: 'utf-8' })), { extends: 'astro/tsconfigs/strict', }); }); @@ -99,13 +96,13 @@ describe('typescript: setup tsconfig', () => { const root = new URL('./fixtures/not-empty/', import.meta.url); const tsconfig = new URL('./tsconfig.json', root); await setupTypeScript('strict', { cwd: fileURLToPath(root) }); - expect(JSON.parse(fs.readFileSync(tsconfig, { encoding: 'utf-8' }))).to.deep.eq({ + assert.deepEqual(JSON.parse(fs.readFileSync(tsconfig, { encoding: 'utf-8' })), { extends: 'astro/tsconfigs/strict', }); }); }); -describe('typescript: setup package', () => { +describe('typescript: setup package', async () => { beforeEach(() => resetFixtures()); it('none', async () => { @@ -113,23 +110,26 @@ describe('typescript: setup package', () => { const packageJson = new URL('./package.json', root); await setupTypeScript('strictest', { cwd: fileURLToPath(root), install: false }); - expect(fs.existsSync(packageJson)).to.be.false; + assert.ok(!fs.existsSync(packageJson)); }); it('none', async () => { const root = new URL('./fixtures/not-empty/', import.meta.url); const packageJson = new URL('./package.json', root); - - expect(JSON.parse(fs.readFileSync(packageJson, { encoding: 'utf-8' })).scripts.build).to.be.eq( + assert.equal( + JSON.parse(fs.readFileSync(packageJson, { encoding: 'utf-8' })).scripts.build, 'astro build' ); + await setupTypeScript('strictest', { cwd: fileURLToPath(root), install: false }); const { scripts } = JSON.parse(fs.readFileSync(packageJson, { encoding: 'utf-8' })); - expect(Object.keys(scripts)).to.deep.eq( + assert.deepEqual( + Object.keys(scripts), ['dev', 'build', 'preview'], 'does not override existing scripts' ); - expect(scripts.build).to.eq('astro check && astro build', 'prepends astro check command'); + + assert.equal(scripts.build, 'astro check && astro build', 'prepends astro check command'); }); }); diff --git a/packages/create-astro/test/utils.js b/packages/create-astro/test/utils.js index ee7f8af5b73d..6a62490e93fa 100644 --- a/packages/create-astro/test/utils.js +++ b/packages/create-astro/test/utils.js @@ -1,6 +1,7 @@ import fs from 'node:fs'; import { setStdout } from '../dist/index.js'; import stripAnsi from 'strip-ansi'; +import { before, beforeEach } from 'node:test'; export function setup() { const ctx = { messages: [] }; diff --git a/packages/create-astro/test/verify.test.js b/packages/create-astro/test/verify.test.js index ecfaba7279a5..9ec7e49e91cd 100644 --- a/packages/create-astro/test/verify.test.js +++ b/packages/create-astro/test/verify.test.js @@ -1,9 +1,9 @@ -import { expect } from 'chai'; - -import { verify } from '../dist/index.js'; +import assert from 'node:assert/strict'; +import { describe, it } from 'node:test'; import { setup } from './utils.js'; +import { verify } from '../dist/index.js'; -describe('verify', () => { +describe('verify', async () => { const fixture = setup(); const exit = (code) => { throw code; @@ -12,7 +12,7 @@ describe('verify', () => { it('basics', async () => { const context = { template: 'basics', exit }; await verify(context); - expect(fixture.messages().length).to.equal(0, 'Did not expect `verify` to log any messages'); + assert.equal(fixture.messages().length, 0, 'Did not expect `verify` to log any messages'); }); it('missing', async () => { @@ -23,19 +23,19 @@ describe('verify', () => { } catch (e) { err = e; } - expect(err).to.eq(1); - expect(fixture.hasMessage('Template missing does not exist!')); + assert.equal(err, 1); + assert.ok(!fixture.hasMessage('Template missing does not exist!')); }); it('starlight', async () => { const context = { template: 'starlight', exit }; await verify(context); - expect(fixture.messages().length).to.equal(0, 'Did not expect `verify` to log any messages'); + assert.equal(fixture.messages().length, 0, 'Did not expect `verify` to log any messages'); }); it('starlight/tailwind', async () => { const context = { template: 'starlight/tailwind', exit }; await verify(context); - expect(fixture.messages().length).to.equal(0, 'Did not expect `verify` to log any messages'); + assert.equal(fixture.messages().length, 0, 'Did not expect `verify` to log any messages'); }); }); diff --git a/packages/integrations/markdoc/CHANGELOG.md b/packages/integrations/markdoc/CHANGELOG.md index c4b877e20522..3acfb43cece9 100644 --- a/packages/integrations/markdoc/CHANGELOG.md +++ b/packages/integrations/markdoc/CHANGELOG.md @@ -1,5 +1,49 @@ # @astrojs/markdoc +## 0.9.0 + +### Minor Changes + +- [#9958](https://github.com/withastro/astro/pull/9958) [`14ce8a6ebfc9daf951d2dca54737d857c229667c`](https://github.com/withastro/astro/commit/14ce8a6ebfc9daf951d2dca54737d857c229667c) Thanks [@Princesseuh](https://github.com/Princesseuh)! - Adds support for using a custom tag (component) for optimized images + + Starting from this version, when a tag called `image` is used, its `src` attribute will automatically be resolved if it's a local image. Astro will pass the result `ImageMetadata` object to the underlying component as the `src` prop. For non-local images (i.e. images using URLs or absolute paths), Astro will continue to pass the `src` as a string. + + ```ts + // markdoc.config.mjs + import { component, defineMarkdocConfig, nodes } from '@astrojs/markdoc/config'; + + export default defineMarkdocConfig({ + tags: { + image: { + attributes: nodes.image.attributes, + render: component('./src/components/MarkdocImage.astro'), + }, + }, + }); + ``` + + ```astro + --- + // src/components/MarkdocImage.astro + import { Image } from 'astro:assets'; + + interface Props { + src: ImageMetadata | string; + alt: string; + width: number; + height: number; + } + + const { src, alt, width, height } = Astro.props; + --- + + + ``` + + ```mdoc + {% image src="./astro-logo.png" alt="Astro Logo" width="100" height="100" %} + ``` + ## 0.8.3 ### Patch Changes diff --git a/packages/integrations/markdoc/package.json b/packages/integrations/markdoc/package.json index 3b84622993f7..163388ac40ca 100644 --- a/packages/integrations/markdoc/package.json +++ b/packages/integrations/markdoc/package.json @@ -1,7 +1,7 @@ { "name": "@astrojs/markdoc", "description": "Add support for Markdoc in your Astro site", - "version": "0.8.3", + "version": "0.9.0", "type": "module", "types": "./dist/index.d.ts", "author": "withastro", diff --git a/packages/integrations/vercel/package.json b/packages/integrations/vercel/package.json index 2688791845a1..1b110b831776 100644 --- a/packages/integrations/vercel/package.json +++ b/packages/integrations/vercel/package.json @@ -46,8 +46,9 @@ "build": "astro-scripts build \"src/**/*.ts\" && tsc", "build:ci": "astro-scripts build \"src/**/*.ts\"", "dev": "astro-scripts dev \"src/**/*.ts\"", - "test": "mocha --exit --timeout 20000 --file \"./test/setup.js\" test/ --ignore test/hosted", - "test:hosted": "mocha --exit --timeout 30000 test/hosted" + "test": "astro-scripts test --timeout 50000 \"test/**/!(hosted|edge-middleware).test.js\" && pnpm run test:edge-middleware", + "test:hosted": "astro-scripts test --timeout 30000 \"test/hosted/*.test.js\"", + "test:edge-middleware": "mocha --exit --timeout 20000 --file \"./test/setup.js\" \"test/edge-middleware.test.js\"" }, "dependencies": { "@astrojs/internal-helpers": "workspace:*", diff --git a/packages/integrations/vercel/src/serverless/adapter.ts b/packages/integrations/vercel/src/serverless/adapter.ts index 0281b62d4c0f..68897c6dc9b7 100644 --- a/packages/integrations/vercel/src/serverless/adapter.ts +++ b/packages/integrations/vercel/src/serverless/adapter.ts @@ -9,6 +9,7 @@ import { AstroError } from 'astro/errors'; import glob from 'fast-glob'; import { basename } from 'node:path'; import { pathToFileURL } from 'node:url'; +import { existsSync, readFileSync } from 'node:fs'; import { getAstroImageConfig, getDefaultImageConfig, @@ -222,6 +223,26 @@ export default function vercelServerless({ injectScript('page', 'import "@astrojs/vercel/speed-insights"'); } + const vercelConfigPath = new URL('vercel.json', config.root); + if (existsSync(vercelConfigPath)) { + try { + const vercelConfig = JSON.parse(readFileSync(vercelConfigPath, 'utf-8')); + if (vercelConfig.trailingSlash === true && config.trailingSlash === 'always') { + logger.warn( + '\n' + + `\tYour "vercel.json" \`trailingSlash\` configuration (set to \`true\`) will conflict with your Astro \`trailinglSlash\` configuration (set to \`"always"\`).\n` + + `\tThis would cause infinite redirects under certain conditions and throw an \`ERR_TOO_MANY_REDIRECTS\` error.\n` + + `\tTo prevent this, your Astro configuration is updated to \`"ignore"\` during builds.\n` + ); + updateConfig({ + trailingSlash: 'ignore', + }); + } + } catch (_err) { + logger.warn(`Your "vercel.json" config is not a valid json file.`); + } + } + updateConfig({ outDir: new URL('./.vercel/output/', config.root), build: { diff --git a/packages/integrations/vercel/test/hosted/hosted.test.js b/packages/integrations/vercel/test/hosted/hosted.test.js index f53daa85ef75..547138b8c3a2 100644 --- a/packages/integrations/vercel/test/hosted/hosted.test.js +++ b/packages/integrations/vercel/test/hosted/hosted.test.js @@ -1,4 +1,5 @@ -import { expect } from 'chai'; +import assert from 'node:assert/strict'; +import { describe, it } from 'node:test'; const VERCEL_TEST_URL = 'https://astro-vercel-image-test.vercel.app'; @@ -8,6 +9,6 @@ describe('Hosted Vercel Tests', () => { VERCEL_TEST_URL + '/_image?href=%2F_astro%2Fpenguin.e9c64733.png&w=300&f=webp' ); - expect(image.status).to.equal(200); + assert.equal(image.status, 200); }); }); diff --git a/packages/integrations/vercel/test/image.test.js b/packages/integrations/vercel/test/image.test.js index b8bc3af95bd8..af99afab1a62 100644 --- a/packages/integrations/vercel/test/image.test.js +++ b/packages/integrations/vercel/test/image.test.js @@ -1,5 +1,6 @@ -import { expect } from 'chai'; import * as cheerio from 'cheerio'; +import assert from 'node:assert/strict'; +import { after, before, describe, it } from 'node:test'; import { loadFixture } from './test-utils.js'; describe('Image', () => { @@ -14,7 +15,7 @@ describe('Image', () => { }); it('build successful', async () => { - expect(await fixture.readFile('../.vercel/output/static/index.html')).to.be.ok; + assert.ok(await fixture.readFile('../.vercel/output/static/index.html')); }); it('has link to vercel in build with proper attributes', async () => { @@ -22,15 +23,15 @@ describe('Image', () => { const $ = cheerio.load(html); const img = $('#basic-image img'); - expect(img.attr('src').startsWith('/_vercel/image?url=_astr')).to.be.true; - expect(img.attr('loading')).to.equal('lazy'); - expect(img.attr('width')).to.equal('225'); + assert.equal(img.attr('src').startsWith('/_vercel/image?url=_astr'), true); + assert.equal(img.attr('loading'), 'lazy'); + assert.equal(img.attr('width'), '225'); }); it('has proper vercel config', async () => { const vercelConfig = JSON.parse(await fixture.readFile('../.vercel/output/config.json')); - expect(vercelConfig.images).to.deep.equal({ + assert.deepEqual(vercelConfig.images, { sizes: [640, 750, 828, 1080, 1200, 1920, 2048, 3840], domains: ['astro.build'], remotePatterns: [ @@ -58,9 +59,9 @@ describe('Image', () => { const $ = cheerio.load(html); const img = $('#basic-image img'); - expect(img.attr('src').startsWith('/_image?href=')).to.be.true; - expect(img.attr('loading')).to.equal('lazy'); - expect(img.attr('width')).to.equal('225'); + assert.equal(img.attr('src').startsWith('/_image?href='), true); + assert.equal(img.attr('loading'), 'lazy'); + assert.equal(img.attr('width'), '225'); }); it('supports SVGs', async () => { @@ -70,8 +71,8 @@ describe('Image', () => { const src = img.attr('src'); const res = await fixture.fetch(src); - expect(res.status).to.equal(200); - expect(res.headers.get('content-type')).to.equal('image/svg+xml'); + assert.equal(res.status, 200); + assert.equal(res.headers.get('content-type'), 'image/svg+xml'); }); }); }); diff --git a/packages/integrations/vercel/test/isr.test.js b/packages/integrations/vercel/test/isr.test.js index f2881972ce23..f6687e960b31 100644 --- a/packages/integrations/vercel/test/isr.test.js +++ b/packages/integrations/vercel/test/isr.test.js @@ -1,5 +1,6 @@ import { loadFixture } from './test-utils.js'; -import { expect } from 'chai'; +import assert from 'node:assert/strict'; +import { before, describe, it } from 'node:test'; describe('ISR', () => { /** @type {import('./test-utils.js').Fixture} */ @@ -16,7 +17,7 @@ describe('ISR', () => { const vcConfig = JSON.parse( await fixture.readFile('../.vercel/output/functions/_isr.prerender-config.json') ); - expect(vcConfig).to.deep.include({ + assert.deepEqual(vcConfig, { expiration: 120, bypassToken: '1c9e601d-9943-4e7c-9575-005556d774a8', allowQuery: ['x_astro_path'], @@ -27,7 +28,7 @@ describe('ISR', () => { it('generates expected routes', async () => { const deploymentConfig = JSON.parse(await fixture.readFile('../.vercel/output/config.json')); // the first two are /_astro/*, and filesystem routes - expect(deploymentConfig.routes.slice(2)).to.deep.equal([ + assert.deepEqual(deploymentConfig.routes.slice(2), [ { src: '^/two$', dest: '_render', diff --git a/packages/integrations/vercel/test/max-duration.test.js b/packages/integrations/vercel/test/max-duration.test.js index 79991290515c..188b4211dfa3 100644 --- a/packages/integrations/vercel/test/max-duration.test.js +++ b/packages/integrations/vercel/test/max-duration.test.js @@ -1,5 +1,6 @@ import { loadFixture } from './test-utils.js'; -import { expect } from 'chai'; +import assert from 'node:assert/strict'; +import { before, describe, it } from 'node:test'; describe('maxDuration', () => { /** @type {import('./test-utils.js').Fixture} */ @@ -16,6 +17,6 @@ describe('maxDuration', () => { const vcConfig = JSON.parse( await fixture.readFile('../.vercel/output/functions/_render.func/.vc-config.json') ); - expect(vcConfig).to.deep.include({ maxDuration: 60 }); + assert.equal(vcConfig.maxDuration, 60); }); }); diff --git a/packages/integrations/vercel/test/no-output.test.js b/packages/integrations/vercel/test/no-output.test.js index 3894ee779a9f..31708754be11 100644 --- a/packages/integrations/vercel/test/no-output.test.js +++ b/packages/integrations/vercel/test/no-output.test.js @@ -1,5 +1,6 @@ import { loadFixture } from './test-utils.js'; -import { expect } from 'chai'; +import assert from 'node:assert/strict'; +import { before, describe, it } from 'node:test'; describe('Missing output config', () => { /** @type {import('./test-utils').Fixture} */ @@ -18,7 +19,7 @@ describe('Missing output config', () => { } catch (err) { error = err; } - expect(error).to.not.be.equal(undefined); - expect(error.message).to.include('output: "server"'); + assert.notEqual(error, undefined); + assert.match(error.message, /output: "server"/); }); }); diff --git a/packages/integrations/vercel/test/prerendered-error-pages.test.js b/packages/integrations/vercel/test/prerendered-error-pages.test.js index 9085662238d8..d528972ecc27 100644 --- a/packages/integrations/vercel/test/prerendered-error-pages.test.js +++ b/packages/integrations/vercel/test/prerendered-error-pages.test.js @@ -1,5 +1,6 @@ import { loadFixture } from './test-utils.js'; -import { expect } from 'chai'; +import assert from 'node:assert/strict'; +import { before, describe, it } from 'node:test'; describe('prerendered error pages routing', () => { /** @type {import('./test-utils.js').Fixture} */ @@ -14,7 +15,7 @@ describe('prerendered error pages routing', () => { it('falls back to 404.html', async () => { const deploymentConfig = JSON.parse(await fixture.readFile('../.vercel/output/config.json')); - expect(deploymentConfig.routes.at(-1)).to.deep.include({ + assert.deepEqual(deploymentConfig.routes.at(-1), { src: '/.*', dest: '/404.html', status: 404, diff --git a/packages/integrations/vercel/test/redirects-serverless.test.js b/packages/integrations/vercel/test/redirects-serverless.test.js index f3a1a5daaf33..8d7dcf75b403 100644 --- a/packages/integrations/vercel/test/redirects-serverless.test.js +++ b/packages/integrations/vercel/test/redirects-serverless.test.js @@ -1,4 +1,5 @@ -import { expect } from 'chai'; +import assert from 'node:assert/strict'; +import { before, describe, it } from 'node:test'; import { loadFixture } from './test-utils.js'; describe('Redirects Serverless', () => { @@ -23,6 +24,6 @@ describe('Redirects Serverless', () => { } catch { hasErrored = true; } - expect(hasErrored).to.equal(true, 'this file should not exist'); + assert.equal(hasErrored, true, 'this file should not exist'); }); }); diff --git a/packages/integrations/vercel/test/redirects.test.js b/packages/integrations/vercel/test/redirects.test.js index 795529ece9de..57de308e233a 100644 --- a/packages/integrations/vercel/test/redirects.test.js +++ b/packages/integrations/vercel/test/redirects.test.js @@ -1,4 +1,5 @@ -import { expect } from 'chai'; +import assert from 'node:assert/strict'; +import { before, describe, it } from 'node:test'; import { loadFixture } from './test-utils.js'; describe('Redirects', () => { @@ -34,46 +35,49 @@ describe('Redirects', () => { const config = await getConfig(); const oneRoute = config.routes.find((r) => r.src === '/one'); - expect(oneRoute.headers.Location).to.equal('/'); - expect(oneRoute.status).to.equal(301); + assert.equal(oneRoute.headers.Location, '/'); + assert.equal(oneRoute.status, 301); const twoRoute = config.routes.find((r) => r.src === '/two'); - expect(twoRoute.headers.Location).to.equal('/'); - expect(twoRoute.status).to.equal(301); + assert.equal(twoRoute.headers.Location, '/'); + assert.equal(twoRoute.status, 301); const threeRoute = config.routes.find((r) => r.src === '/three'); - expect(threeRoute.headers.Location).to.equal('/'); - expect(threeRoute.status).to.equal(302); + assert.equal(threeRoute.headers.Location, '/'); + assert.equal(threeRoute.status, 302); }); it('define redirects for static files', async () => { const config = await getConfig(); const staticRoute = config.routes.find((r) => r.src === '/Basic/http-2-0.html'); - expect(staticRoute).to.not.be.undefined; - expect(staticRoute.headers.Location).to.equal('/posts/http2'); - expect(staticRoute.status).to.equal(301); + assert.notEqual(staticRoute, undefined); + assert.equal(staticRoute.headers.Location, '/posts/http2'); + assert.equal(staticRoute.status, 301); }); it('defines dynamic routes', async () => { const config = await getConfig(); const blogRoute = config.routes.find((r) => r.src.startsWith('/blog')); - expect(blogRoute).to.not.be.undefined; - expect(blogRoute.headers.Location.startsWith('/team/articles')).to.equal(true); - expect(blogRoute.status).to.equal(301); + assert.notEqual(blogRoute, undefined); + assert.equal(blogRoute.headers.Location.startsWith('/team/articles'), true); + assert.equal(blogRoute.status, 301); }); it('define trailingSlash redirect for sub pages', async () => { const config = await getConfig(); const subpathRoute = config.routes.find((r) => r.src === '/subpage'); - expect(subpathRoute).to.not.be.undefined; - expect(subpathRoute.headers.Location).to.equal('/subpage/'); + assert.notEqual(subpathRoute, undefined); + assert.equal(subpathRoute.headers.Location, '/subpage/'); }); it('does not define trailingSlash redirect for root page', async () => { const config = await getConfig(); - expect(config.routes.find((r) => r.src === '/')).to.be.undefined; + assert.equal( + config.routes.find((r) => r.src === '/'), + undefined + ); }); }); diff --git a/packages/integrations/vercel/test/serverless-prerender.test.js b/packages/integrations/vercel/test/serverless-prerender.test.js index 5a3c7dd7064c..475df477fe50 100644 --- a/packages/integrations/vercel/test/serverless-prerender.test.js +++ b/packages/integrations/vercel/test/serverless-prerender.test.js @@ -1,4 +1,5 @@ -import { expect } from 'chai'; +import assert from 'node:assert/strict'; +import { before, describe, it } from 'node:test'; import { loadFixture } from './test-utils.js'; describe('Serverless prerender', () => { @@ -14,16 +15,16 @@ describe('Serverless prerender', () => { }); it('build successful', async () => { - expect(await fixture.readFile('../.vercel/output/static/index.html')).to.be.ok; + assert.ok(await fixture.readFile('../.vercel/output/static/index.html')); }); // TODO: The path here seems to be inconsistent? it.skip('includeFiles work', async () => { - expect( + assert.ok( await fixture.readFile( '../.vercel/output/functions/render.func/packages/integrations/vercel/test/fixtures/serverless-prerender/dist/middleware.mjs' ) - ).to.be.ok; + ); }); }); @@ -41,6 +42,6 @@ describe('Serverless hybrid rendering', () => { }); it('build successful', async () => { - expect(await fixture.readFile('../.vercel/output/static/index.html')).to.be.ok; + assert.ok(await fixture.readFile('../.vercel/output/static/index.html')); }); }); diff --git a/packages/integrations/vercel/test/serverless-with-dynamic-routes.test.js b/packages/integrations/vercel/test/serverless-with-dynamic-routes.test.js index fae3aef956b4..0967f864ba85 100644 --- a/packages/integrations/vercel/test/serverless-with-dynamic-routes.test.js +++ b/packages/integrations/vercel/test/serverless-with-dynamic-routes.test.js @@ -1,4 +1,5 @@ -import { expect } from 'chai'; +import assert from 'node:assert/strict'; +import { before, describe, it } from 'node:test'; import { loadFixture } from './test-utils.js'; describe('Serverless with dynamic routes', () => { @@ -15,11 +16,12 @@ describe('Serverless with dynamic routes', () => { }); it('build successful', async () => { - expect(await fixture.readFile('../.vercel/output/static/index.html')).to.be.ok; - expect( + assert.ok(await fixture.readFile('../.vercel/output/static/index.html')); + assert.ok( await fixture.readFile('../.vercel/output/functions/[id]/index.astro.func/.vc-config.json') - ).to.be.ok; - expect(await fixture.readFile('../.vercel/output/functions/api/[id].js.func/.vc-config.json')) - .to.be.ok; + ); + assert.ok( + await fixture.readFile('../.vercel/output/functions/api/[id].js.func/.vc-config.json') + ); }); }); diff --git a/packages/integrations/vercel/test/speed-insights.test.js b/packages/integrations/vercel/test/speed-insights.test.js index 7cf2ae7781a5..783121600602 100644 --- a/packages/integrations/vercel/test/speed-insights.test.js +++ b/packages/integrations/vercel/test/speed-insights.test.js @@ -1,5 +1,6 @@ import { loadFixture } from './test-utils.js'; -import { expect } from 'chai'; +import assert from 'node:assert/strict'; +import { before, describe, it } from 'node:test'; describe('Vercel Speed Insights', () => { describe('output: server', () => { @@ -19,7 +20,7 @@ describe('Vercel Speed Insights', () => { const bundle = await fixture.readFile(`../.vercel/output/static/_astro/${page}`); - expect(bundle).to.contain('https://vitals.vercel-analytics.com/v1/vitals'); + assert.match(bundle, /https:\/\/vitals.vercel-analytics.com\/v1\/vitals/); }); }); @@ -40,7 +41,7 @@ describe('Vercel Speed Insights', () => { const bundle = await fixture.readFile(`../.vercel/output/static/_astro/${page}`); - expect(bundle).to.contain('https://vitals.vercel-analytics.com/v1/vitals'); + assert.match(bundle, /https:\/\/vitals.vercel-analytics.com\/v1\/vitals/); }); }); }); diff --git a/packages/integrations/vercel/test/split.test.js b/packages/integrations/vercel/test/split.test.js index 3f4e75d1b01e..172c27775e15 100644 --- a/packages/integrations/vercel/test/split.test.js +++ b/packages/integrations/vercel/test/split.test.js @@ -1,5 +1,6 @@ import { loadFixture } from './test-utils.js'; -import { expect } from 'chai'; +import assert from 'node:assert/strict'; +import { before, describe, it } from 'node:test'; describe('build: split', () => { /** @type {import('./test-utils').Fixture} */ @@ -15,12 +16,12 @@ describe('build: split', () => { it('creates separate functions for each page', async () => { const files = await fixture.readdir('../.vercel/output/functions/'); - expect(files.length).to.equal(3); + assert.equal(files.length, 3); }); it('creates the route definitions in the config.json', async () => { const json = await fixture.readFile('../.vercel/output/config.json'); const config = JSON.parse(json); - expect(config.routes).to.have.a.lengthOf(5); + assert.equal(config.routes.length, 5); }); }); diff --git a/packages/integrations/vercel/test/static-assets.test.js b/packages/integrations/vercel/test/static-assets.test.js index 606addfb3f13..37d3a057724b 100644 --- a/packages/integrations/vercel/test/static-assets.test.js +++ b/packages/integrations/vercel/test/static-assets.test.js @@ -1,4 +1,5 @@ -import { expect } from 'chai'; +import assert from 'node:assert/strict'; +import { describe, it } from 'node:test'; import { loadFixture } from './test-utils.js'; describe('Static Assets', () => { @@ -32,39 +33,40 @@ describe('Static Assets', () => { async function checkValidCacheControl(assets) { const config = await getConfig(); + const theAssets = assets ?? (await getAssets()); - const route = config.routes.find((r) => r.src === `^/${assets ?? getAssets()}/(.*)$`); - expect(route.headers['cache-control']).to.equal(VALID_CACHE_CONTROL); - expect(route.continue).to.equal(true); + const route = config.routes.find((r) => r.src === `^/${theAssets}/(.*)$`); + assert.equal(route.headers['cache-control'], VALID_CACHE_CONTROL); + assert.equal(route.continue, true); } - describe('static adapter', async () => { - const { default: vercel } = await import('@astrojs/vercel/static'); - + describe('static adapter', () => { it('has cache control', async () => { + const { default: vercel } = await import('@astrojs/vercel/static'); await build({ adapter: vercel() }); - checkValidCacheControl(); + await checkValidCacheControl(); }); it('has cache control other assets', async () => { + const { default: vercel } = await import('@astrojs/vercel/static'); const assets = '_foo'; await build({ adapter: vercel(), assets }); - checkValidCacheControl(assets); + await checkValidCacheControl(assets); }); }); - describe('serverless adapter', async () => { - const { default: vercel } = await import('@astrojs/vercel/serverless'); - + describe('serverless adapter', () => { it('has cache control', async () => { + const { default: vercel } = await import('@astrojs/vercel/serverless'); await build({ output: 'server', adapter: vercel() }); - checkValidCacheControl(); + await checkValidCacheControl(); }); it('has cache control other assets', async () => { + const { default: vercel } = await import('@astrojs/vercel/serverless'); const assets = '_foo'; await build({ output: 'server', adapter: vercel(), assets }); - checkValidCacheControl(assets); + await checkValidCacheControl(assets); }); }); }); diff --git a/packages/integrations/vercel/test/static.test.js b/packages/integrations/vercel/test/static.test.js index a3d0ea738272..7547d2475a05 100644 --- a/packages/integrations/vercel/test/static.test.js +++ b/packages/integrations/vercel/test/static.test.js @@ -1,5 +1,6 @@ import { loadFixture } from './test-utils.js'; -import { expect } from 'chai'; +import assert from 'node:assert/strict'; +import { before, describe, it } from 'node:test'; describe('static routing', () => { /** @type {import('./test-utils.js').Fixture} */ @@ -15,7 +16,7 @@ describe('static routing', () => { it('falls back to 404.html', async () => { const deploymentConfig = JSON.parse(await fixture.readFile('../.vercel/output/config.json')); // change the index if necesseary - expect(deploymentConfig.routes[2]).to.deep.include({ + assert.deepEqual(deploymentConfig.routes[2], { src: '/.*', dest: '/404.html', status: 404, diff --git a/packages/integrations/vercel/test/streaming.test.js b/packages/integrations/vercel/test/streaming.test.js index 205946973a8c..3d231478d0b6 100644 --- a/packages/integrations/vercel/test/streaming.test.js +++ b/packages/integrations/vercel/test/streaming.test.js @@ -1,5 +1,6 @@ import { loadFixture } from './test-utils.js'; -import { expect } from 'chai'; +import assert from 'node:assert/strict'; +import { before, describe, it } from 'node:test'; describe('streaming', () => { /** @type {import('./test-utils.js').Fixture} */ @@ -16,6 +17,6 @@ describe('streaming', () => { const vcConfig = JSON.parse( await fixture.readFile('../.vercel/output/functions/_render.func/.vc-config.json') ); - expect(vcConfig).to.deep.include({ supportsResponseStreaming: true }); + assert.equal(vcConfig.supportsResponseStreaming, true); }); }); diff --git a/packages/integrations/vercel/test/web-analytics.test.js b/packages/integrations/vercel/test/web-analytics.test.js index b728fae4caae..6b4efaedbcfd 100644 --- a/packages/integrations/vercel/test/web-analytics.test.js +++ b/packages/integrations/vercel/test/web-analytics.test.js @@ -1,5 +1,6 @@ import { loadFixture } from './test-utils.js'; -import { expect } from 'chai'; +import assert from 'node:assert/strict'; +import { before, describe, it } from 'node:test'; describe('Vercel Web Analytics', () => { describe('output: static', () => { @@ -18,8 +19,8 @@ describe('Vercel Web Analytics', () => { const pageOne = await fixture.readFile('../.vercel/output/static/one/index.html'); const pageTwo = await fixture.readFile('../.vercel/output/static/two/index.html'); - expect(pageOne).to.contain('/_vercel/insights/script.js'); - expect(pageTwo).to.contain('/_vercel/insights/script.js'); + assert.match(pageOne, /\/_vercel\/insights\/script.js/); + assert.match(pageTwo, /\/_vercel\/insights\/script.js/); }); }); }); diff --git a/packages/markdown/remark/package.json b/packages/markdown/remark/package.json index ee081361df04..965b057cde96 100644 --- a/packages/markdown/remark/package.json +++ b/packages/markdown/remark/package.json @@ -31,7 +31,7 @@ "build:ci": "astro-scripts build \"src/**/*.ts\"", "postbuild": "astro-scripts copy \"src/**/*.js\"", "dev": "astro-scripts dev \"src/**/*.ts\"", - "test": "mocha --exit --timeout 20000" + "test": "astro-scripts test \"test/**/*.test.js\"" }, "dependencies": { "@astrojs/prism": "^3.0.0", @@ -44,7 +44,7 @@ "remark-parse": "^11.0.0", "remark-rehype": "^11.0.0", "remark-smartypants": "^2.0.0", - "shikiji": "^0.9.18", + "shikiji": "^0.9.19", "unified": "^11.0.4", "unist-util-visit": "^5.0.0", "vfile": "^6.0.1" diff --git a/packages/markdown/remark/test/autolinking.test.js b/packages/markdown/remark/test/autolinking.test.js index 79d3ea76790a..76922e7c3731 100644 --- a/packages/markdown/remark/test/autolinking.test.js +++ b/packages/markdown/remark/test/autolinking.test.js @@ -1,37 +1,43 @@ +import assert from 'node:assert/strict'; +import { describe, it, before } from 'node:test'; import { createMarkdownProcessor } from '../dist/index.js'; -import chai from 'chai'; describe('autolinking', () => { - describe('plain md', async () => { - const processor = await createMarkdownProcessor(); + describe('plain md', () => { + let processor; + + before(async () => { + processor = await createMarkdownProcessor(); + }); it('autolinks URLs starting with a protocol in plain text', async () => { - const { code } = await processor.render(`See https://example.com for more.`); + const markdown = `See https://example.com for more.`; + const { code } = await processor.render(markdown); - chai - .expect(code.replace(/\n/g, '')) - .to.equal(`

See https://example.com for more.

`); + assert.equal( + code.replace(/\n/g, ''), + `

See https://example.com for more.

` + ); }); it('autolinks URLs starting with "www." in plain text', async () => { - const { code } = await processor.render(`See www.example.com for more.`); + const markdown = `See www.example.com for more.`; + const { code } = await processor.render(markdown); - chai - .expect(code.trim()) - .to.equal(`

See www.example.com for more.

`); + assert.equal( + code.trim(), + `

See www.example.com for more.

` + ); }); it('does not autolink URLs in code blocks', async () => { - const { code } = await processor.render( - 'See `https://example.com` or `www.example.com` for more.' - ); + const markdown = `See \`https://example.com\` or \`www.example.com\` for more.`; + const { code } = await processor.render(markdown); - chai - .expect(code.trim()) - .to.equal( - `

See https://example.com or ` + - `www.example.com for more.

` - ); + assert.equal( + code.trim(), + `

See https://example.com or www.example.com for more.

` + ); }); }); }); diff --git a/packages/markdown/remark/test/browser.test.js b/packages/markdown/remark/test/browser.test.js index d78593fca12d..c3831cca1590 100644 --- a/packages/markdown/remark/test/browser.test.js +++ b/packages/markdown/remark/test/browser.test.js @@ -1,15 +1,20 @@ import esbuild from 'esbuild'; -import { expect } from 'chai'; +import assert from 'node:assert/strict'; +import { describe, it } from 'node:test'; describe('Bundle for browsers', async () => { it('esbuild browser build should work', async () => { - const result = await esbuild.build({ - platform: 'browser', - entryPoints: ['@astrojs/markdown-remark'], - bundle: true, - write: false, - }); - // If some non-browser-safe stuff sneaks in, esbuild should error before reaching here - expect(result.outputFiles.length).to.be.greaterThan(0); + try { + const result = await esbuild.build({ + platform: 'browser', + entryPoints: ['@astrojs/markdown-remark'], + bundle: true, + write: false, + }); + assert.ok(result.outputFiles.length > 0); + } catch (error) { + // Capture any esbuild errors and fail the test + assert.fail(error.message); + } }); }); diff --git a/packages/markdown/remark/test/entities.test.js b/packages/markdown/remark/test/entities.test.js index b2dacb79f7bc..83d95f5a1238 100644 --- a/packages/markdown/remark/test/entities.test.js +++ b/packages/markdown/remark/test/entities.test.js @@ -1,12 +1,18 @@ +import assert from 'node:assert/strict'; +import { describe, it, before } from 'node:test'; import { createMarkdownProcessor } from '../dist/index.js'; -import { expect } from 'chai'; describe('entities', async () => { - const processor = await createMarkdownProcessor(); + let processor; + + before(async () => { + processor = await createMarkdownProcessor(); + }); it('should not unescape entities in regular Markdown', async () => { - const { code } = await processor.render(`<i>This should NOT be italic</i>`); + const markdown = `<i>This should NOT be italic</i>`; + const { code } = await processor.render(markdown); - expect(code).to.equal(`

<i>This should NOT be italic</i>

`); + assert.equal(code, `

<i>This should NOT be italic</i>

`); }); }); diff --git a/packages/markdown/remark/test/plugins.test.js b/packages/markdown/remark/test/plugins.test.js index ce2401047210..4afc364c875b 100644 --- a/packages/markdown/remark/test/plugins.test.js +++ b/packages/markdown/remark/test/plugins.test.js @@ -1,20 +1,18 @@ +import assert from 'node:assert/strict'; +import { describe, it } from 'node:test'; import { createMarkdownProcessor } from '../dist/index.js'; -import chai from 'chai'; - import { fileURLToPath } from 'node:url'; describe('plugins', () => { - // https://github.com/withastro/astro/issues/3264 it('should be able to get file path when passing fileURL', async () => { let context; const processor = await createMarkdownProcessor({ remarkPlugins: [ - function () { + () => { const transformer = (tree, file) => { context = file; }; - return transformer; }, ], @@ -24,7 +22,7 @@ describe('plugins', () => { fileURL: new URL('virtual.md', import.meta.url), }); - chai.expect(typeof context).to.equal('object'); - chai.expect(context.path).to.equal(fileURLToPath(new URL('virtual.md', import.meta.url))); + assert.ok(typeof context === 'object'); + assert.equal(context.path, fileURLToPath(new URL('virtual.md', import.meta.url))); }); }); diff --git a/packages/markdown/remark/test/remark-collect-images.test.js b/packages/markdown/remark/test/remark-collect-images.test.js index 259bea96e310..77f474d94440 100644 --- a/packages/markdown/remark/test/remark-collect-images.test.js +++ b/packages/markdown/remark/test/remark-collect-images.test.js @@ -1,39 +1,42 @@ +import assert from 'node:assert/strict'; +import { describe, it, before } from 'node:test'; import { createMarkdownProcessor } from '../dist/index.js'; -import chai from 'chai'; describe('collect images', async () => { - const processor = await createMarkdownProcessor(); + let processor; + + before(async () => { + processor = await createMarkdownProcessor(); + }); it('should collect inline image paths', async () => { + const markdown = `Hello ![inline image url](./img.png)`; + const fileURL = 'file.md'; + const { code, metadata: { imagePaths }, - } = await processor.render(`Hello ![inline image url](./img.png)`, { - fileURL: 'file.md', - }); + } = await processor.render(markdown, { fileURL }); - chai - .expect(code) - .to.equal( - '

Hello

' - ); + assert.equal( + code, + '

Hello

' + ); - chai.expect(Array.from(imagePaths)).to.deep.equal(['./img.png']); + assert.deepStrictEqual(Array.from(imagePaths), ['./img.png']); }); it('should add image paths from definition', async () => { - const { + const markdown = `Hello ![image ref][img-ref]\n\n[img-ref]: ./img.webp`; + const fileURL = 'file.md'; + + const { code, metadata } = await processor.render(markdown, { fileURL }); + + assert.equal( code, - metadata: { imagePaths }, - } = await processor.render(`Hello ![image ref][img-ref]\n\n[img-ref]: ./img.webp`, { - fileURL: 'file.md', - }); - - chai - .expect(code) - .to.equal( - '

Hello

' - ); - chai.expect(Array.from(imagePaths)).to.deep.equal(['./img.webp']); + '

Hello

' + ); + + assert.deepStrictEqual(Array.from(metadata.imagePaths), ['./img.webp']); }); }); diff --git a/packages/markdown/remark/test/shiki.test.js b/packages/markdown/remark/test/shiki.test.js index d6f3e8925928..2fb40c217c43 100644 --- a/packages/markdown/remark/test/shiki.test.js +++ b/packages/markdown/remark/test/shiki.test.js @@ -1,12 +1,13 @@ +import assert from 'node:assert/strict'; +import { describe, it } from 'node:test'; import { createMarkdownProcessor, createShikiHighlighter } from '../dist/index.js'; -import chai from 'chai'; describe('shiki syntax highlighting', () => { it('does not add is:raw to the output', async () => { const processor = await createMarkdownProcessor(); const { code } = await processor.render('```\ntest\n```'); - chai.expect(code).not.to.contain('is:raw'); + assert.ok(!code.includes('is:raw')); }); it('supports light/dark themes', async () => { @@ -21,11 +22,12 @@ describe('shiki syntax highlighting', () => { const { code } = await processor.render('```\ntest\n```'); // light theme is there: - chai.expect(code).to.contain('background-color:'); - chai.expect(code).to.contain('github-light'); + assert.match(code, /background-color:/); + assert.match(code, /github-light/); + // dark theme is there: - chai.expect(code).to.contain('--shiki-dark-bg:'); - chai.expect(code).to.contain('github-dark'); + assert.match(code, /--shiki-dark-bg:/); + assert.match(code, /github-dark/); }); it('createShikiHighlighter works', async () => { @@ -33,8 +35,8 @@ describe('shiki syntax highlighting', () => { const html = highlighter.highlight('const foo = "bar";', 'js'); - chai.expect(html).to.contain('astro-code github-dark'); - chai.expect(html).to.contain('background-color:#24292e;color:#e1e4e8;'); + assert.match(html, /astro-code github-dark/); + assert.match(html, /background-color:#24292e;color:#e1e4e8;/); }); it('diff +/- text has user-select: none', async () => { @@ -46,8 +48,9 @@ describe('shiki syntax highlighting', () => { + const foo = "world";`, 'diff' ); - chai.expect(html).to.contain('user-select: none'); - chai.expect(html).to.contain('>-'); - chai.expect(html).to.contain('>+'); + + assert.match(html, /user-select: none/); + assert.match(html, />-<\/span>/); + assert.match(html, />+<\/span>/); }); }); diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 2fd13891ce5b..3216e1f2a073 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -131,7 +131,7 @@ importers: examples/basics: dependencies: astro: - specifier: ^4.3.5 + specifier: ^4.3.6 version: link:../../packages/astro examples/blog: @@ -146,13 +146,13 @@ importers: specifier: ^3.0.5 version: link:../../packages/integrations/sitemap astro: - specifier: ^4.3.5 + specifier: ^4.3.6 version: link:../../packages/astro examples/component: devDependencies: astro: - specifier: ^4.3.5 + specifier: ^4.3.6 version: link:../../packages/astro examples/framework-alpine: @@ -167,7 +167,7 @@ importers: specifier: ^3.13.3 version: 3.13.3 astro: - specifier: ^4.3.5 + specifier: ^4.3.6 version: link:../../packages/astro examples/framework-lit: @@ -179,7 +179,7 @@ importers: specifier: ^0.2.1 version: 0.2.1 astro: - specifier: ^4.3.5 + specifier: ^4.3.6 version: link:../../packages/astro lit: specifier: ^3.1.2 @@ -203,7 +203,7 @@ importers: specifier: ^4.0.8 version: link:../../packages/integrations/vue astro: - specifier: ^4.3.5 + specifier: ^4.3.6 version: link:../../packages/astro preact: specifier: ^10.19.2 @@ -233,7 +233,7 @@ importers: specifier: ^1.2.1 version: 1.2.1(preact@10.19.3) astro: - specifier: ^4.3.5 + specifier: ^4.3.6 version: link:../../packages/astro preact: specifier: ^10.19.2 @@ -251,7 +251,7 @@ importers: specifier: ^18.2.15 version: 18.2.18 astro: - specifier: ^4.3.5 + specifier: ^4.3.6 version: link:../../packages/astro react: specifier: ^18.2.0 @@ -266,7 +266,7 @@ importers: specifier: ^4.0.1 version: link:../../packages/integrations/solid astro: - specifier: ^4.3.5 + specifier: ^4.3.6 version: link:../../packages/astro solid-js: specifier: ^1.8.5 @@ -278,7 +278,7 @@ importers: specifier: ^5.0.3 version: link:../../packages/integrations/svelte astro: - specifier: ^4.3.5 + specifier: ^4.3.6 version: link:../../packages/astro svelte: specifier: ^4.2.5 @@ -290,7 +290,7 @@ importers: specifier: ^4.0.8 version: link:../../packages/integrations/vue astro: - specifier: ^4.3.5 + specifier: ^4.3.6 version: link:../../packages/astro vue: specifier: ^3.3.8 @@ -302,13 +302,13 @@ importers: specifier: ^8.2.0 version: link:../../packages/integrations/node astro: - specifier: ^4.3.5 + specifier: ^4.3.6 version: link:../../packages/astro examples/integration: devDependencies: astro: - specifier: ^4.3.5 + specifier: ^4.3.6 version: link:../../packages/astro examples/middleware: @@ -317,7 +317,7 @@ importers: specifier: ^8.2.0 version: link:../../packages/integrations/node astro: - specifier: ^4.3.5 + specifier: ^4.3.6 version: link:../../packages/astro html-minifier: specifier: ^4.0.0 @@ -330,19 +330,19 @@ importers: examples/minimal: dependencies: astro: - specifier: ^4.3.5 + specifier: ^4.3.6 version: link:../../packages/astro examples/non-html-pages: dependencies: astro: - specifier: ^4.3.5 + specifier: ^4.3.6 version: link:../../packages/astro examples/portfolio: dependencies: astro: - specifier: ^4.3.5 + specifier: ^4.3.6 version: link:../../packages/astro examples/ssr: @@ -354,7 +354,7 @@ importers: specifier: ^5.0.3 version: link:../../packages/integrations/svelte astro: - specifier: ^4.3.5 + specifier: ^4.3.6 version: link:../../packages/astro svelte: specifier: ^4.2.5 @@ -363,7 +363,7 @@ importers: examples/starlog: dependencies: astro: - specifier: ^4.3.5 + specifier: ^4.3.6 version: link:../../packages/astro sass: specifier: ^1.69.5 @@ -381,16 +381,16 @@ importers: specifier: ^5.1.0 version: link:../../packages/integrations/tailwind astro: - specifier: ^4.3.5 + specifier: ^4.3.6 version: link:../../packages/astro examples/with-markdoc: dependencies: '@astrojs/markdoc': - specifier: ^0.8.3 + specifier: ^0.9.0 version: link:../../packages/integrations/markdoc astro: - specifier: ^4.3.5 + specifier: ^4.3.6 version: link:../../packages/astro examples/with-markdown-plugins: @@ -399,7 +399,7 @@ importers: specifier: ^4.2.1 version: link:../../packages/markdown/remark astro: - specifier: ^4.3.5 + specifier: ^4.3.6 version: link:../../packages/astro hast-util-select: specifier: ^6.0.2 @@ -420,7 +420,7 @@ importers: examples/with-markdown-shiki: dependencies: astro: - specifier: ^4.3.5 + specifier: ^4.3.6 version: link:../../packages/astro examples/with-mdx: @@ -432,7 +432,7 @@ importers: specifier: ^3.1.0 version: link:../../packages/integrations/preact astro: - specifier: ^4.3.5 + specifier: ^4.3.6 version: link:../../packages/astro preact: specifier: ^10.19.2 @@ -447,7 +447,7 @@ importers: specifier: ^0.5.0 version: 0.5.0(nanostores@0.9.5)(preact@10.19.3) astro: - specifier: ^4.3.5 + specifier: ^4.3.6 version: link:../../packages/astro nanostores: specifier: ^0.9.5 @@ -468,7 +468,7 @@ importers: specifier: ^1.6.3 version: 1.6.4 astro: - specifier: ^4.3.5 + specifier: ^4.3.6 version: link:../../packages/astro autoprefixer: specifier: ^10.4.15 @@ -486,7 +486,7 @@ importers: examples/with-vitest: dependencies: astro: - specifier: ^4.3.5 + specifier: ^4.3.6 version: link:../../packages/astro vitest: specifier: ^1.2.1 @@ -654,8 +654,11 @@ importers: specifier: ^1.0.1 version: 1.0.1 shikiji: - specifier: ^0.9.18 - version: 0.9.18 + specifier: ^0.9.19 + version: 0.9.19 + shikiji-core: + specifier: ^0.9.19 + version: 0.9.19 string-width: specifier: ^7.0.0 version: 7.0.0 @@ -820,9 +823,6 @@ importers: sass: specifier: ^1.69.5 version: 1.69.6 - shikiji-core: - specifier: ^0.9.18 - version: 0.9.18 srcset-parse: specifier: ^1.1.0 version: 1.1.0 @@ -5065,8 +5065,8 @@ importers: specifier: ^2.0.0 version: 2.0.0 shikiji: - specifier: ^0.9.18 - version: 0.9.18 + specifier: ^0.9.19 + version: 0.9.19 unified: specifier: ^11.0.4 version: 11.0.4 @@ -14391,13 +14391,14 @@ packages: vscode-textmate: 5.2.0 dev: true - /shikiji-core@0.9.18: - resolution: {integrity: sha512-PKTXptbrp/WEDjNHV8OFG9KkfhmR0pSd161kzlDDlgQ0HXAnqJYNDSjqsy1CYZMx5bSvLMy42yJj9oFTqmkNTQ==} + /shikiji-core@0.9.19: + resolution: {integrity: sha512-AFJu/vcNT21t0e6YrfadZ+9q86gvPum6iywRyt1OtIPjPFe25RQnYJyxHQPMLKCCWA992TPxmEmbNcOZCAJclw==} + dev: false - /shikiji@0.9.18: - resolution: {integrity: sha512-/tFMIdV7UQklzN13VjF0/XFzmii6C606Jc878hNezvB8ZR8FG8FW9j0I4J9EJre0owlnPntgLVPpHqy27Gs+DQ==} + /shikiji@0.9.19: + resolution: {integrity: sha512-Kw2NHWktdcdypCj1GkKpXH4o6Vxz8B8TykPlPuLHOGSV8VkhoCLcFOH4k19K4LXAQYRQmxg+0X/eM+m2sLhAkg==} dependencies: - shikiji-core: 0.9.18 + shikiji-core: 0.9.19 dev: false /side-channel@1.0.4: diff --git a/scripts/cmd/test.js b/scripts/cmd/test.js index 6af7d0b2fd5d..87b34987ab28 100644 --- a/scripts/cmd/test.js +++ b/scripts/cmd/test.js @@ -7,7 +7,7 @@ import arg from 'arg'; import glob from 'tiny-glob'; const isCI = !!process.env.CI; -const defaultTimeout = isCI ? 900000 : 600000; +const defaultTimeout = isCI ? 1200000 : 600000; export default async function test() { const args = arg({