diff --git a/.changeset/quick-pandas-build.md b/.changeset/quick-pandas-build.md new file mode 100644 index 000000000..3c3c1e41b --- /dev/null +++ b/.changeset/quick-pandas-build.md @@ -0,0 +1,5 @@ +--- +"@solidjs/start": patch +--- + +Fix production builds shipping without client assets (and 500ing from a manifest-less server fallback) when composed with nitro, by bumping vite-plugin-solid to 3.0.0-next.20: its client-build-first `buildApp` hooks now run at normal order and defer to nitro's orchestrator instead of building the client before nitro's pre-order hook wipes `.output/`. A temporary workaround that filtered those hooks out of the solid() plugin set has been removed. diff --git a/.changeset/router-1-0-file-routes.md b/.changeset/router-1-0-file-routes.md new file mode 100644 index 000000000..39cc2e4d9 --- /dev/null +++ b/.changeset/router-1-0-file-routes.md @@ -0,0 +1,18 @@ +--- +"@solidjs/start": patch +--- + +Migrate to `@solidjs/router` 1.0.0-next.7, which removes the component API in favor of the `createRouter` factory. `@solidjs/start/router` now exports the file-system route tree as a value — `fileRoutes` — instead of the `FileRoutes` component (there is no JSX children slot to mount it in anymore); apps pass it straight to the factory: + +```tsx +import { createRouter } from "@solidjs/router"; +import { fileRoutes } from "@solidjs/start/router"; + +const Router = createRouter({ routes: fileRoutes }); + +export default function App() { + return {props => {props.children}}; +} +``` + +Routes are immutable per router instance, so one shared tree serves every request and mount: `PageEvent.routes` (and the per-request tree build in `createPageEvent`) is gone, and the single-flight collector consumes `fileRoutes` directly. The old `root` prop becomes the render-prop child and `rootPreload` becomes the factory's `preload` option; active-link styling moves from the removed `` component's `active` class to the router's anchor attribute vocabulary (`[data-active]`, `[aria-current="page"]`). diff --git a/.changeset/router-owns-single-flight-nojs.md b/.changeset/router-owns-single-flight-nojs.md new file mode 100644 index 000000000..15e0c5f4c --- /dev/null +++ b/.changeset/router-owns-single-flight-nojs.md @@ -0,0 +1,5 @@ +--- +"@solidjs/start": patch +--- + +Adopt the router's server-function integration: single-flight payload collection and the no-JS flash-cookie form convention are `@solidjs/router`'s now (its vocabulary — query cache keys, submissions — was always the payload). Start's `handleSingleFlight` (data-only app render), `createSingleFlightHeaders`, `handleNoJS`, and the flash-cookie SSR seeding are deleted; the server-function handler wires `createFlightDataCollector({ routes: createRoutes, base })` — the router's pure preload runner over the file-system route tree, no app render involved — and `createNoJSHandler({ base })` from `@solidjs/router/server` into the core handler hooks. Client-side single-flight opt-in is automatic: the router registers itself as the transport's flight-data consumer, so per-call `X-Single-Flight` headers are gone too. diff --git a/.changeset/wise-webs-hoist.md b/.changeset/wise-webs-hoist.md new file mode 100644 index 000000000..b3a6b1f3c --- /dev/null +++ b/.changeset/wise-webs-hoist.md @@ -0,0 +1,5 @@ +--- +"@solidjs/start": patch +--- + +adopt solid 2.0.0-beta.29's hoisted web APIs: `clientOnly` re-exports core's implementation (import-once dedupe, `{ lazy }`), `HttpStatusCode`/`HttpHeader` become thin deprecated wrappers over the `httpStatus`/`httpHeader` primitives, `getServerFunctionMeta` delegates to `getServerFunctionInvocation` (invocation state no longer rides on `event.locals`), the streaming handler consumes `renderToStream(...).readable` instead of a hand-rolled adapter, and the handler marks `response.committed` when the head can no longer change diff --git a/apps/fixtures/bare/package.json b/apps/fixtures/bare/package.json index 2a27260d2..0b65add24 100644 --- a/apps/fixtures/bare/package.json +++ b/apps/fixtures/bare/package.json @@ -8,8 +8,9 @@ }, "dependencies": { "@solidjs/start": "workspace:*", + "@solidjs/web": "2.0.0-beta.29", "nitro": "^3.0.260610-beta", - "solid-js": "^1.9.14", + "solid-js": "2.0.0-beta.29", "vite": "^8.1.5" }, "engines": { diff --git a/apps/fixtures/bare/tsconfig.json b/apps/fixtures/bare/tsconfig.json index 5bd3d2200..4f92bf383 100644 --- a/apps/fixtures/bare/tsconfig.json +++ b/apps/fixtures/bare/tsconfig.json @@ -6,7 +6,7 @@ "allowSyntheticDefaultImports": true, "esModuleInterop": true, "jsx": "preserve", - "jsxImportSource": "solid-js", + "jsxImportSource": "@solidjs/web", "allowJs": true, "strict": true, "noEmit": true, diff --git a/apps/fixtures/basic/package.json b/apps/fixtures/basic/package.json index d8b50ba32..db0d315e0 100644 --- a/apps/fixtures/basic/package.json +++ b/apps/fixtures/basic/package.json @@ -7,11 +7,12 @@ "build": "vite build" }, "dependencies": { - "@solidjs/meta": "^0.29.4", - "@solidjs/router": "^1.0.0", + "@solidjs/meta": "0.30.0-next.0", + "@solidjs/router": "2.0.0-next.13", "@solidjs/start": "workspace:*", + "@solidjs/web": "2.0.0-beta.29", "nitro": "^3.0.260610-beta", - "solid-js": "^1.9.14", + "solid-js": "2.0.0-beta.29", "vite": "^8.1.5" }, "engines": { diff --git a/apps/fixtures/basic/src/app.tsx b/apps/fixtures/basic/src/app.tsx index d1359c8d8..7e8871954 100644 --- a/apps/fixtures/basic/src/app.tsx +++ b/apps/fixtures/basic/src/app.tsx @@ -1,22 +1,22 @@ import { MetaProvider, Title } from "@solidjs/meta"; -import { Router } from "@solidjs/router"; -import { FileRoutes } from "@solidjs/start/router"; -import { Suspense } from "solid-js"; +import { createRouter } from "@solidjs/router"; +import { fileRoutes } from "@solidjs/start/router"; +import { Loading } from "solid-js"; import "./app.css"; +const Router = createRouter({ routes: fileRoutes }); + export default function App() { return ( - ( + + {props => ( SolidStart - Basic Index About - {props.children} + {props.children} )} - > - ); } diff --git a/apps/fixtures/basic/src/routes/[...404].tsx b/apps/fixtures/basic/src/routes/[...404].tsx index 4ea71ec7f..72c04ee2a 100644 --- a/apps/fixtures/basic/src/routes/[...404].tsx +++ b/apps/fixtures/basic/src/routes/[...404].tsx @@ -1,10 +1,8 @@ -import { Title } from "@solidjs/meta"; import { HttpStatusCode } from "@solidjs/start"; export default function NotFound() { return (
- Not Found

Page Not Found

diff --git a/apps/fixtures/basic/tsconfig.json b/apps/fixtures/basic/tsconfig.json index 5bd3d2200..4f92bf383 100644 --- a/apps/fixtures/basic/tsconfig.json +++ b/apps/fixtures/basic/tsconfig.json @@ -6,7 +6,7 @@ "allowSyntheticDefaultImports": true, "esModuleInterop": true, "jsx": "preserve", - "jsxImportSource": "solid-js", + "jsxImportSource": "@solidjs/web", "allowJs": true, "strict": true, "noEmit": true, diff --git a/apps/fixtures/basic/vite.config.ts b/apps/fixtures/basic/vite.config.ts index 10795376f..d896560c4 100644 --- a/apps/fixtures/basic/vite.config.ts +++ b/apps/fixtures/basic/vite.config.ts @@ -4,4 +4,7 @@ import { solidStart } from "../../../packages/start/src/config"; export default defineConfig({ plugins: [solidStart(), nitro()], + resolve: { + dedupe: ["solid-js", "@solidjs/web", "@solidjs/router"], + }, }); diff --git a/apps/fixtures/css/package.json b/apps/fixtures/css/package.json index aa9ac8681..62bfa7f24 100644 --- a/apps/fixtures/css/package.json +++ b/apps/fixtures/css/package.json @@ -8,11 +8,12 @@ "start": "node .output/server/index.mjs" }, "dependencies": { - "@solidjs/meta": "^0.29.4", - "@solidjs/router": "^1.0.0", + "@solidjs/meta": "0.30.0-next.0", + "@solidjs/router": "2.0.0-next.13", "@solidjs/start": "workspace:*", + "@solidjs/web": "2.0.0-beta.29", "nitro": "^3.0.260610-beta", - "solid-js": "^1.9.14", + "solid-js": "2.0.0-beta.29", "vite": "^8.1.5" }, "devDependencies": { diff --git a/apps/fixtures/css/src/app.tsx b/apps/fixtures/css/src/app.tsx index 32aeff5ec..9703db994 100644 --- a/apps/fixtures/css/src/app.tsx +++ b/apps/fixtures/css/src/app.tsx @@ -1,13 +1,15 @@ import { MetaProvider, Title } from "@solidjs/meta"; -import { Router } from "@solidjs/router"; -import { FileRoutes } from "@solidjs/start/router"; -import { Suspense } from "solid-js"; +import { createRouter } from "@solidjs/router"; +import { fileRoutes } from "@solidjs/start/router"; +import { Loading } from "solid-js"; import "./app.css"; +const Router = createRouter({ routes: fileRoutes }); + export default function App() { return ( - ( + + {props => ( SolidStart - CSS Fixture

@@ -17,12 +19,10 @@ export default function App() { Unstyled - {props.children} + {props.children}
)} - > - ); } diff --git a/apps/fixtures/css/src/components/layout.tsx b/apps/fixtures/css/src/components/layout.tsx index 99763f047..97750c3d2 100644 --- a/apps/fixtures/css/src/components/layout.tsx +++ b/apps/fixtures/css/src/components/layout.tsx @@ -1,5 +1,5 @@ -import { createSignal, FlowProps, onMount } from "solid-js"; -import { getRequestEvent } from "solid-js/web"; +import { createSignal, FlowProps, onSettled } from "solid-js"; +import { getRequestEvent } from "@solidjs/web"; const Badge = (props: FlowProps) => (
{props.children}
@@ -7,7 +7,9 @@ const Badge = (props: FlowProps) => ( const Layout = (props: FlowProps<{ title: string }>) => { const [mounted, setMounted] = createSignal(false); - onMount(() => setMounted(true)); + onSettled(() => { + setMounted(true); + }); return (
diff --git a/apps/fixtures/css/src/components/test.tsx b/apps/fixtures/css/src/components/test.tsx index 21defb028..843751851 100644 --- a/apps/fixtures/css/src/components/test.tsx +++ b/apps/fixtures/css/src/components/test.tsx @@ -1,4 +1,4 @@ -import { JSX } from "solid-js"; +import { JSX } from "@solidjs/web"; const clsx = (...args: (string | false | undefined)[]) => args.filter(Boolean).join(" "); diff --git a/apps/fixtures/css/src/routes/index.tsx b/apps/fixtures/css/src/routes/index.tsx index 3b4fa0f6e..73e33cd51 100644 --- a/apps/fixtures/css/src/routes/index.tsx +++ b/apps/fixtures/css/src/routes/index.tsx @@ -1,5 +1,5 @@ -import { createAsync, query } from "@solidjs/router"; -import { lazy, Show } from "solid-js"; +import { query } from "@solidjs/router"; +import { createMemo, lazy, Show } from "solid-js"; import "virtual:virtualModule.css"; import Layout from "../components/layout"; import { CommonTests } from "../components/test"; @@ -12,8 +12,10 @@ const Lazy = lazy(() => import("../components/lazy")); const LazyLink = lazy(() => import("../components/lazyLink")); const LazyLinkTmp = lazy(() => import("../components/lazyLinkTmp")); -const entries = import.meta.glob("../components/lazyG*.tsx"); -const LazyGlob = lazy(Object.values(entries)[0] as any); +const entries = import.meta.glob("/src/components/lazyG*.tsx"); +// Solid 2 lazy() requires an explicit moduleUrl in SSR when the loader +// isn't a static dynamic import the bundler plugin can analyze. +const LazyGlob = lazy(Object.values(entries)[0] as any, Object.keys(entries)[0]!.slice(1)); const SharedChunk = lazy(() => import("../components/sharedChunk/lazy1")); // Do not remove this. @@ -27,7 +29,7 @@ const getData = query(async () => { }, "data"); export default function Home() { - const data = createAsync(() => getData(), { deferStream: true }); + const data = createMemo(() => getData(), { deferStream: true }); return (
diff --git a/apps/fixtures/css/tsconfig.json b/apps/fixtures/css/tsconfig.json index 1fd1e25c8..c25bc6d63 100644 --- a/apps/fixtures/css/tsconfig.json +++ b/apps/fixtures/css/tsconfig.json @@ -6,7 +6,7 @@ "allowSyntheticDefaultImports": true, "esModuleInterop": true, "jsx": "preserve", - "jsxImportSource": "solid-js", + "jsxImportSource": "@solidjs/web", "allowJs": true, "strict": true, "noEmit": true, diff --git a/apps/fixtures/css/vite.config.ts b/apps/fixtures/css/vite.config.ts index 50b7117d0..f4b0c1c66 100644 --- a/apps/fixtures/css/vite.config.ts +++ b/apps/fixtures/css/vite.config.ts @@ -12,7 +12,6 @@ export default defineConfig({ /** * Creates a shared chunk with two components. Needed for the "SharedChunk" test! * The vite manifest behaves differently for such shared chunks. - * More info: packages/start/src/config/lazy.ts * * TODO: When switching to Rolldown, migrate this to advancedChunks * https://vite.dev/guide/rolldown.html#manualchunks-to-advancedchunks diff --git a/apps/fixtures/experiments/package.json b/apps/fixtures/experiments/package.json index 35a7f8de8..70c0b03bd 100644 --- a/apps/fixtures/experiments/package.json +++ b/apps/fixtures/experiments/package.json @@ -7,11 +7,12 @@ "build": "vite build" }, "dependencies": { - "@solidjs/meta": "^0.29.4", - "@solidjs/router": "^1.0.0", + "@solidjs/meta": "0.30.0-next.0", + "@solidjs/router": "2.0.0-next.13", "@solidjs/start": "workspace:*", + "@solidjs/web": "2.0.0-beta.29", "nitro": "^3.0.260610-beta", - "solid-js": "^1.9.14", + "solid-js": "2.0.0-beta.29", "vite": "^8.1.5" }, "engines": { diff --git a/apps/fixtures/experiments/src/app.tsx b/apps/fixtures/experiments/src/app.tsx index 912b2232a..af98b42d1 100644 --- a/apps/fixtures/experiments/src/app.tsx +++ b/apps/fixtures/experiments/src/app.tsx @@ -1,25 +1,25 @@ import { MetaProvider, Title } from "@solidjs/meta"; -import { Router } from "@solidjs/router"; -import { FileRoutes } from "@solidjs/start/router"; -import { Suspense } from "solid-js"; +import { createRouter } from "@solidjs/router"; +import { fileRoutes } from "@solidjs/start/router"; +import { Loading } from "solid-js"; import "./app.css"; import Provider from "./components/Provider"; +const Router = createRouter({ routes: fileRoutes }); + export default function App() { return ( - ( + + {props => ( SolidStart - Bare Index About - {props.children} + {props.children} )} - > - ); } diff --git a/apps/fixtures/experiments/src/components/Provider.tsx b/apps/fixtures/experiments/src/components/Provider.tsx index 581a6ea67..4c2e19a9d 100644 --- a/apps/fixtures/experiments/src/components/Provider.tsx +++ b/apps/fixtures/experiments/src/components/Provider.tsx @@ -3,9 +3,5 @@ import { createSignal } from "solid-js"; import counterContext from "./counterContext"; export default function Provider(props) { - return ( - - {props.children} - - ); + return {props.children}; } diff --git a/apps/fixtures/experiments/src/routes/index.tsx b/apps/fixtures/experiments/src/routes/index.tsx index 189744fb1..f68d0384c 100644 --- a/apps/fixtures/experiments/src/routes/index.tsx +++ b/apps/fixtures/experiments/src/routes/index.tsx @@ -1,8 +1,7 @@ import { Title } from "@solidjs/meta"; -import { json } from "@solidjs/router"; import { clientOnly, GET } from "@solidjs/start"; import { getServerFunctionMeta } from "@solidjs/start/server"; -import { getRequestEvent, isServer } from "solid-js/web"; +import { getRequestEvent, isServer, respond } from "@solidjs/web"; import Counter from "~/components/Counter"; const BreaksOnServer = clientOnly(() => import("~/components/BreaksOnServer")); @@ -11,7 +10,7 @@ const hello = GET(async (name: string) => { const e = getRequestEvent()!; const { id } = getServerFunctionMeta()!; console.log("ID", id, e.locals.foo); - return json( + return respond( { hello: new Promise(r => setTimeout(() => r(name), 1000)) }, { headers: { "cache-control": "max-age=60" } }, ); diff --git a/apps/fixtures/experiments/tsconfig.json b/apps/fixtures/experiments/tsconfig.json index 5bd3d2200..4f92bf383 100644 --- a/apps/fixtures/experiments/tsconfig.json +++ b/apps/fixtures/experiments/tsconfig.json @@ -6,7 +6,7 @@ "allowSyntheticDefaultImports": true, "esModuleInterop": true, "jsx": "preserve", - "jsxImportSource": "solid-js", + "jsxImportSource": "@solidjs/web", "allowJs": true, "strict": true, "noEmit": true, diff --git a/apps/fixtures/hackernews/package.json b/apps/fixtures/hackernews/package.json index c1bf92ca2..5e91dac6d 100644 --- a/apps/fixtures/hackernews/package.json +++ b/apps/fixtures/hackernews/package.json @@ -8,9 +8,10 @@ "build": "vite build" }, "dependencies": { - "@solidjs/router": "^1.0.0", + "@solidjs/router": "2.0.0-next.13", "@solidjs/start": "workspace:*", - "solid-js": "^1.9.14", + "@solidjs/web": "2.0.0-beta.29", + "solid-js": "2.0.0-beta.29", "vite": "^8.1.5" }, "engines": { diff --git a/apps/fixtures/hackernews/src/app.css b/apps/fixtures/hackernews/src/app.css index 2bf246440..e4317e072 100644 --- a/apps/fixtures/hackernews/src/app.css +++ b/apps/fixtures/hackernews/src/app.css @@ -47,7 +47,9 @@ a { color: #fff; } -.header a.active { +/* Router 1.0 marks exact-or-prefix matched anchors with `data-active` + (the root path only ever matches exactly, so "/" doesn't stay lit). */ +.header a[data-active] { color: #fff; font-weight: 400; } diff --git a/apps/fixtures/hackernews/src/app.tsx b/apps/fixtures/hackernews/src/app.tsx index 82e4c0de1..3ae5beb75 100644 --- a/apps/fixtures/hackernews/src/app.tsx +++ b/apps/fixtures/hackernews/src/app.tsx @@ -1,22 +1,20 @@ -import { Router } from "@solidjs/router"; -import { FileRoutes } from "@solidjs/start/router"; -import { Suspense } from "solid-js"; +import { createRouter } from "@solidjs/router"; +import { fileRoutes } from "@solidjs/start/router"; +import { Loading } from "solid-js"; import "./app.css"; import Nav from "./components/nav"; +const Router = createRouter({ routes: fileRoutes }); + export default function App() { return ( - ( + + {props => ( <>
}> - {props.children} - + Loading...}>{props.children} )} - > - ); } diff --git a/apps/fixtures/hackernews/src/components/comment.tsx b/apps/fixtures/hackernews/src/components/comment.tsx index 8a85eb9df..564c9664e 100644 --- a/apps/fixtures/hackernews/src/components/comment.tsx +++ b/apps/fixtures/hackernews/src/components/comment.tsx @@ -1,4 +1,3 @@ -import { A } from "@solidjs/router"; import { Component, For, Show } from "solid-js"; import { CommentDefinition } from "~/types"; import Toggle from "./toggle"; @@ -7,7 +6,7 @@ const Comment: Component<{ comment: CommentDefinition }> = props => { return (
  • - {props.comment.user} {props.comment.time_ago}{" "} + {props.comment.user} {props.comment.time_ago}{" "} ago
    diff --git a/apps/fixtures/hackernews/src/components/nav.tsx b/apps/fixtures/hackernews/src/components/nav.tsx index abf8f87c8..4803efd6c 100644 --- a/apps/fixtures/hackernews/src/components/nav.tsx +++ b/apps/fixtures/hackernews/src/components/nav.tsx @@ -1,24 +1,22 @@ -import { A } from "@solidjs/router"; - function Nav() { return (
    - 0}> + 0}> - -
    - +