create-giojs
Scaffold a new GioJS app, add starter features to an existing one, or migrate a Next.js project - every flag, prompt and exit code.
npm create giojs@latest my-apppnpm create giojs my-appyarn create giojs my-appbun create giojs my-appnpm create giojs@latest [directory] -- [options]
npm create giojs@latest -- add <feature...> [options]
npm create giojs@latest -- migrate [dir] [options]With npm, options after the directory go behind --. pnpm, yarn and bun pass that -- on, and create-giojs skips it, so the documented form works under every package manager.
Reference
| Option | Type | Default | Description |
|---|---|---|---|
[directory] | path | my-giojs-app | Where the app goes (asked for on a terminal); . is the current directory. The npm package name is derived from its last segment. |
--ts, --typescript | boolean | true | TypeScript (.tsx, tsconfig.json). |
--js, --javascript | boolean | - | JavaScript (.jsx, jsconfig.json, no TypeScript toolchain). |
--server | boolean | true | A server app: SSR, page caching, images, route handlers; runs the GioJS server. |
--static | boolean | - | A static site: npm run build typechecks (TypeScript) and runs gio export to out/; there is no start script. |
--pm <name> | string | detected | npm, pnpm, yarn or bun: the package manager to install with and to name in the next steps. By default, the one running create-giojs. |
--install / --no-install | boolean | true | Install the dependencies. A failed install is reported, and the project is kept. |
--git / --no-git | boolean | true | Run git init and make an initial commit of the scaffolded files. |
-f, --force | boolean | false | Scaffold into a directory that is not empty. Files with the template's names are overwritten. |
-y, --yes | boolean | false | Ask nothing; every option not given takes its default. |
--tailwind, --api, --auth, --db, --docker, --ci | boolean | - | Starter features (see below). Aliases: --tailwindcss, --database, --sqlite, --drizzle, --github-actions. |
--features <list> | string | - | The same features as a list: --features auth,db. --features= adds none (and skips the question). |
-h, --help | boolean | - | Print the help and exit. |
-v, --version | boolean | - | Print the create-giojs version and exit. |
--pm and --features take their value as the next argument or after = (--pm=pnpm). Boolean flags take no value.
Prompts
On a terminal, create-giojs asks for what the flags leave open, in this order, before it writes anything:
- Project name (when no directory is given; default
my-giojs-app). A directory that is not empty is refused here and asked again. - Package name, only when the directory's name is not a valid npm name (
My Appsuggestsmy-app). - Language: TypeScript or JavaScript.
- What are you building? Server app or static site.
- Add features: a multi-select of the starter features that fit the build target.
- Install dependencies with <pm>?
Without a terminal (CI, piped input) or with --yes, nothing is asked: the directory defaults to my-giojs-app, an invalid package name is replaced by its sanitized form with a warning, and no features are added. Ctrl+C at a question exits with code 130 and nothing written; Ctrl+C while files are being written removes what this run created (except in a --force run, whose overwritten files cannot be restored).
What it writes
- The starter:
app/with a root layout, anapp/(site)/route group (home, about, a dynamic post page),errorandnot-foundpages,components/,public/with self-hosted fonts,gio.toml,tsconfig.json(orjsconfig.json),.env.example,.gitignoreandAGENTS.md. package.jsonwith@gio.js/server,@gio.js/core,@gio.js/react, React andcross-env. Its scripts runcross-env NODE_ENV=development giojs-server(dev) andcross-env NODE_ENV=production giojs-server(start).- The chosen features' files, then the install, then the git commit (so it includes the lockfile).
Over an existing directory, the initial commit holds only what this run wrote: files that were already there are left out and listed, as they may hold secrets.
The target directory
A directory that is not empty is refused, with a list of what is in it, unless --force. These do not count: .git, .gitattributes, .DS_Store, Thumbs.db, .idea, .vscode, README.md and LICENSE (.md, .txt). A path that exists and is not a directory is always refused.
Starter features
| Flag | Adds | Static site |
|---|---|---|
--tailwind | Tailwind CSS v4 via its CLI, rebuilt as you edit | yes |
--api | A JSON route.ts and a <GioForm> page action | no |
--auth | Cookie sessions, login/logout, a guarded /dashboard | no |
--db | Drizzle ORM on Node's built-in SQLite, with migrations (Node 22.16+) | no |
--docker | A production Dockerfile (gio build standalone) and compose file | no |
--ci | A GitHub Actions workflow: install, typecheck, test and build on every push | yes |
Asking a static site for a server feature is a usage error before anything is written. Each feature's next steps are printed at the end, with the commands of the package manager the app was installed with. See Starter Features.
create-giojs add
npx create-giojs add <feature...> [--cwd <dir>] [--dry-run] [-f, --force]Adds starter features to an existing project, without overwriting files you changed; gio add runs it. Features are named as arguments (tailwind auth, tailwind,auth) or with the create flags (--auth, --features auth,db). The gio add page has the behavior, conflicts and exit codes.
create-giojs migrate
npm create giojs@latest -- migrate [dir] [--dry-run | -n] [-y, --yes] [--config <file>]
npx create-giojs migrate [dir]
npx -p create-giojs gio-migrate [dir] # the standalone binMigrates a Next.js project to GioJS in place; gio migrate runs it and documents every option. A bare npx gio-migrate would fetch whatever npm package has that name: use npx -p create-giojs gio-migrate.
Exit codes
| Code | When |
|---|---|
0 | The app was created (a failed install or git commit is reported but does not fail the run), or --help / --version. |
1 | An unexpected error while writing; for add, a refused run; for migrate, a failed or refused migration. |
2 | A usage error. For every subcommand: an unknown option or feature (with a suggestion), a flag given a value it does not take, a second directory. When creating an app, also: a non-empty directory without --force, a server feature for a static site (add refuses that one with 1). |
130 | Cancelled with Ctrl+C. |
Examples
Create an app in CI
npm create giojs@latest my-app -- --yes --no-gitA JavaScript static site
npm create giojs@latest my-site -- --js --staticpnpm create giojs my-site --js --staticyarn create giojs my-site --js --staticbun create giojs my-site --js --staticA server app with features
$ npm create giojs@latest shop -- --tailwind --auth --no-install
Creating shop in /home/me/shop - TypeScript (.tsx), server app...
Template copied.
Added: Tailwind CSS, Authentication.
Initialized a git repository with an initial commit.
Done! To get started:
cd shop
npm install
npm run dev
Your features:
Tailwind CSS:
- Use Tailwind classes in any component - `npm run dev` runs the Tailwind watcher next to the server.
- The starter's own styles now load from app/tailwind.css (in Tailwind's base layer).
Authentication:
- Open /dashboard: the guard sends you to /login (demo user in .env.development).
- Before deploying, generate GIO_SESSION_SECRET: node -e "console.log(require('crypto').randomBytes(32).toString('base64url'))"
- Cross-site POSTs are refused by the server (CSRF), so forms need no tokens; keep state changes behind POST.With pnpm, in the current directory
mkdir blog && cd blog
pnpm create giojs .Mistakes it catches
$ npm create giojs@latest x -- --statc
Error: Unknown option --statc - did you mean --static?
Run create-giojs --help to see every option.
$ npm create giojs@latest site -- --static --auth
Error: auth needs a server app - a static site has no server to run it.Good to know
- The package manager is the one you ran (
npm create,pnpm create,yarn create,bun create), unless--pmsays otherwise - so a pnpm user never ends up with two lockfiles. - The package name must be a valid npm name: lowercase, URL-safe, at most 214 characters, not a Node.js built-in module. The validated name is what goes into the templates.
- Git is skipped with a note when git is not installed or the directory is already inside a repository; a failed commit (no
user.name) leaves an initialized repository for you to commit. - A mistyped option never silently scaffolds something else: unknown flags are errors. A misspelled subcommand is a plain word, though, so
npm create giojs@latest -- migratscaffolds a new app inmigrat/- check theCreating ... in ...line.
Related
- Installation
- Starter Features and
gio add - Migration from Next.js and
gio migrate - Static Export
- CLI overview
Version history
| Version | Changes |
|---|---|
v0.1.0-beta.8 | Strict flags with suggestions, --help, --version, --pm, --git / --no-git (git init and a first commit by default), --force and a positional directory; a non-empty directory is refused. Starter features (--tailwind ... --features), add and migrate subcommands. No questions without a terminal. |
v0.1.0-beta.2 | --server / --static and the build target question. |
v0.1.0-beta.1 | Introduced, with --ts / --js, --install / --no-install and -y / --yes. |