SolidStart Integration

SolidStart is the meta-framework for SolidJS, built on top of Vinxi and Vite. solidjs-bext is the adapter that targets bext: you keep SolidStart's authoring experience, and bext provides the HTTP layer, cache, WAF, HTTP/2/3, and plugin ecosystem that every adapter otherwise reinvents.

Preview release. The adapter and the Rust-side framework runtime in crates/bext-framework-solidstart ship as part of bext's E7 milestone. See the ecosystem roadmap for what's landed and what's still on the follow-up list.

Install

bun add -d solidjs-bext

Peer dependencies: solid-start ^1 or @solidjs/start ^1.

Configure

In app.config.ts (SolidStart 1.x):




export default defineConfig({
  server: {
    preset: bext({
      runtime: "bun",
    }),
  },
});

The adapter registers itself as a Vinxi server preset. SolidStart then builds with server output, producing .output/server/index.mjs plus a .output/public directory of hashed assets.

Options

Option Type Default Description
out string .output Output directory relative to the project root.
runtime "node" | "bun" "bun" Preferred runtime for the SSR worker. Informational; bext decides.

Build

bun run build

The build emits:

.output/
  public/            hashed JS, CSS, fonts
  server/
    index.mjs        SSR entry exporting { handler }
  bext-adapter.json  metadata for the bext runtime

bext-adapter.json is the contract between solidjs-bext and crates/bext-framework-solidstart. It looks like:

{
  "adapter": "solidjs-bext",
  "version": "0.1.0-preview",
  "runtime": "bun",
  "serverEntry": "server/index.mjs",
  "clientDir": "public",
  "generatedAt": "2026-04-11T12:00:00.000Z"
}

Serve

Via bext.config.toml

[framework]
type = "solidstart"
build_dir = ".output"

[build]
script = ".output/server/index.mjs"
watch_dirs = ["src"]
live_reload = true

Then:

bext serve

bext's vhost detects the project as SolidStart (on solid.config.* or vite.config.* importing solid-start + solid-start / @solidjs/start in package.json), reads the build output, and dispatches requests to the SolidStart handler through the framework runtime adapter.

Via bext new

bext new my-solid-app --template @bext/starter-solid
cd my-solid-app
bun install
bun run build
bext serve

The starter ships with app.config.ts, an app shell, two routes (/ and /about), and the bext.config.toml plumbing pre-wired.

How it fits together

Three moving parts collaborate on every SolidStart request through bext:

  1. solidjs-bext (this package) — SolidStart adapter + Vinxi preset. Runs at build time. Produces .output/ and bext-adapter.json. 2. crates/bext-framework-solidstart — Rust FrameworkAdapter implementation. Runs at server-config time. Detects the project, invokes bunx solid-start build (or npx solid-start build), normalises the output, and vends a runtime adapter. 3. bext-server vhost — per-request. Routes incoming requests to the SolidStart runtime adapter, which in turn dispatches to the Node / Bun subprocess running .output/server/index.mjs.

How it compares to the default Vinxi node-server preset

The default node-server preset produces a standalone Node server you run yourself. solidjs-bext skips the HTTP layer — bext provides that — and just emits the compiled SSR entry plus static assets. bext then adds TLS, HTTP/2/3, cache, WAF, compression, and the full plugin ecosystem without SolidStart needing to know about any of them.

What works today

- File-system routing (src/routes/*)

- Dynamic routes with [param].tsx

- Catch-all routes with [...rest].tsx

- Server functions ("use server" / createServerFn)

- Route data (createAsync / cache)

- Islands via clientOnly wrappers

- Static assets served from .output/public

Current limitations

  • Subprocess dispatch is still TODO. For the E7 preview, the runtime adapter is a descriptor only — bext-framework-solidstart's handle_request returns a not-yet-wired error. The follow-up is to teach bext-server's vhost to dispatch to the Node / Bun subprocess that imports .output/server/index.mjs, reusing the same subprocess plumbing bext already has for PHP / FastCGI. - No streaming responses yet. Solid's renderToStream can return a streaming Response. The preview buffers those. Piping them through bext's response writer lands with the streaming FrameworkAdapter::render hook. - No edge runtime support. This adapter targets Node / Bun. Edge-style Workers-compatible output is out of scope for E7. - No native Rust build. solidjs-bext shells out to solid-start build — the build is a Vite + Vinxi pipeline and rewriting it in Rust is out of scope for E7. A direct turbopack / bun pipeline is on the ecosystem roadmap.

Troubleshooting

  • solid-start build produced no .output/ directory — the build ran but didn't emit the expected layout. Double-check that your Vinxi preset is actually solidjs-bext and not the default node-server. - SolidStartRuntime::handle_request is not wired yet — you're seeing the E7 descriptor-only limitation. Build works, detection works, but per-request dispatch is scheduled for the follow-up. Until then, use the node-server preset behind bext as a reverse proxy if you need production traffic right now. - Legacy solid-start (pre-1.0) — detection handles both the classic solid.config.{js,ts} shape and the modern app.config.ts shape. If you're stuck on an older solid-start, the adapter should still register, but some Vinxi hooks may not exist — consider upgrading to @solidjs/start ^1.

Related docs

- @bext/starter-solid — starter scaffold