npx create-talorys@latest| Step | Implementation |
|---|---|
| Check Node.js ≥ 22, templates, bundled Wrangler | requirements.ts, scaffold.ts |
Detect global wrangler / cf (informational) |
requirements.ts |
Verify login or open browser OAuth (wrangler login) |
install.ts › ensureAuthenticated |
Choose account (wrangler whoami --json) |
install.ts › chooseAccount |
| Allocate collision-free names | install.ts › allocateNames |
| Prompt for password (hidden, strength-checked) | ui.ts, secrets.ts |
Write manifest talorys.json (no secrets) |
manifest.ts |
Write Worker bundle, frontend, generated wrangler.jsonc files |
scaffold.ts, config.ts |
| Check the Workers AI model exists (no inference) | wrangler ai models schema |
| Deploy the private Worker (creates the SQLite DO on first deploy) | wrangler deploy |
Store OWNER_PASSWORD_HASH, SESSION_SECRET and the Web Push keys (VAPID_PUBLIC_KEY, VAPID_PRIVATE_KEY) via stdin |
wrangler secret bulk |
| Create/reconcile the Pages project and deploy it | wrangler pages project create, wrangler pages deploy |
| Verify through the public URL | verify.ts |
The Worker is always deployed before Pages, because the Pages service binding refers to it.
{
"name": "talorys-<id>-web",
"pages_build_output_dir": "./dist",
"compatibility_date": "2026-10-01",
"services": [{ "binding": "AGENT", "service": "talorys-<id>-agent" }]
}apps/agent/wrangler.standalone.jsonc deploys the agent Worker with the web UI
as static assets, so one Worker serves both. Use it with tools that deploy a
single Worker:
npm run build -w @talorys/web
cd apps/agent
npx wrangler secret put OWNER_PASSWORD -c wrangler.standalone.jsonc
npx wrangler secret put SESSION_SECRET -c wrangler.standalone.jsonc # 32+ random characters
npx wrangler deploy -c wrangler.standalone.jsoncPush notifications are optional here; see Push notifications to add the keys.
OWNER_PASSWORD is the plain password, for deploys that cannot hash it
beforehand. It must pass the installer's strength check (10+ characters, mixed
classes or 16+ characters, no common words); a weak one counts as not configured
and /api/health reports "password": false. When OWNER_PASSWORD_HASH is set,
it takes precedence.
In this mode, changing SESSION_SECRET also discards a password changed in the
UI: login reverts to OWNER_PASSWORD, and every device is signed out.
The config names the Worker talorys, and wrangler deploy replaces any Worker
of that name in the account. Change name (or pass --name) to deploy under
another one.
Web Push needs a VAPID key pair stored as two Worker secrets. The installer
creates them on a fresh install, and npx create-talorys@latest update adds
them to an installation made before push existed. Existing keys are never
replaced, because new keys would disconnect every subscribed device.
Without the keys everything else works: /api/health reports "push": false
and Settings shows push as unavailable. To add them by hand (for example to a
one-Worker deploy), generate a P-256 pair in the usual base64url form, such as
with npx web-push generate-vapid-keys, and store both:
npx wrangler secret put VAPID_PUBLIC_KEY # add -c wrangler.standalone.jsonc for a one-Worker deploy
npx wrangler secret put VAPID_PRIVATE_KEYThe optional VAPID_SUBJECT (mailto:you@example.com or an https:// URL)
is the contact push services see. It defaults to the app's own URL as recorded
when each device subscribed. Set it with npx wrangler secret put VAPID_SUBJECT;
a plain variable would be dropped when an update regenerates the Worker config.
- The manifest records the installation id; re-runs reuse the same names.
- Secrets that already exist are never overwritten (the password is not re-asked).
- Existing Pages projects are reused; Workers are updated in place.
- Failures mark the manifest
failedwith completed steps; re-running resumes. - The installer never runs delete commands.
- A non-empty directory without a manifest is refused, so nothing unrelated is overwritten.
- New resource names are checked against existing Workers and Pages projects.
npx create-talorys@latest update refreshes artifacts, keeps the same names
and Durable Object class, appends (never edits) migrations, keeps secrets, and
re-verifies. Schema migrations run transactionally inside the Durable Object.
OAuth login (default) uses Wrangler's standard scopes. API tokens need Workers Scripts:Edit, Cloudflare Pages:Edit, Workers AI:Read and Account Settings:Read. A Global API Key is never required.
npm run build -w create-talorys # builds dist/ and templates/
npm run test:pack # verifies the tarball outside the monorepo
cd packages/create-talorys && npm publishTALORYS_VERSION in packages/shared/src/constants.ts must equal the package version.
CLOUDFLARE_API_TOKEN=… CLOUDFLARE_ACCOUNT_ID=… npm run test:smoke
# add TALORYS_SMOKE_AI=1 to include one streamed Workers AI chat turn
{ "name": "talorys-<id>-agent", "main": "worker.js", "compatibility_date": "2026-10-01", "compatibility_flags": ["nodejs_compat"], "workers_dev": false, "preview_urls": false, "ai": { "binding": "AI" }, "durable_objects": { "bindings": [{ "name": "TalorysAgent", "class_name": "TalorysAgent" }] }, "migrations": [{ "tag": "v1", "new_sqlite_classes": ["TalorysAgent"] }], "vars": { "TALORYS_INSTALLATION_ID": "…", "TALORYS_DEPLOYED_VERSION": "…", "TALORYS_DEFAULT_TIMEZONE": "…", "TALORYS_AGENT_NAME": "…" } }