Skip to content

Connect your app server

Give Dyno the command you already use to start your app and its URL. Your server still handles routes, assets, API calls, and hot reload.

webServer: {
command: 'npm run dev',
url: 'http://127.0.0.1:3000',
ready: 'Listening on',
reuseExistingServer: !process.env.CI,
}

The server must log after it starts listening. ready can be a string or RegExp matching that message. Output triggers an HTTP HEAD check; any response, including a 401 or 404, confirms the server is up. There’s no fixed startup sleep.

Dyno reuses a responding server only with reuseExistingServer: true and leaves it running afterward. Otherwise, it starts command in cwd with env. Use a shell string or an argv array such as ['node', 'server.js'].

When a run ends or fails, Dyno stops the processes it started, including descendants. A bounded grace period comes before forceful termination. Reused servers and manually opened browsers remain yours.

The browser loads Dyno’s gateway, which forwards app requests and WebSockets to webServer.url. The app fills the main window. Tests load in a companion window and read the app’s DOM directly; a small injected script reports readiness and errors and hosts the reporter iframe. Your app needs no test imports.

Redirects to the app are rewritten to the gateway origin. Dyno translates same-origin Origin/Referer headers and matching cookie domains, preserving cookie security attributes. External redirects stay external.

The app receives DYNO_URL, the gateway origin. Use it as your public URL for OAuth or WebAuthn: browser credentials contain that origin, while the upstream receives its own Host. Root-relative URLs work best.

Dyno preserves CSP and isolation headers and uses an existing script nonce when available. Give your app an explicit test configuration if it blocks injection, the reporter iframe, or same-origin window access. Changing isolation policy or navigating cross-origin can disconnect the companion and is unsupported.

The gateway accepts UTF-8 HTML, including gzip, deflate, and Brotli, up to 10 MB decoded. See current limits for origin and browser requirements.