Local Development
> What Velocity does for you during local development - one command runs Go and Vite, Go changes rebuild and restart the server, frontend edits hot-reload, and new migrations compile straight into the app with no registration step.
Local development is one command. ./vel serve starts everything, watches
your source, and keeps the running app current while you work. This page
describes exactly what happens in the background so you know what you never
have to do by hand.
./vel serveOne command runs the whole app
On start, vel serve:
- Loads
.env, resolvesAPP_PORT(default4000) andAPP_ENV(defaultdevelopment);--portand--envoverride both. - Starts the Vite dev server when a
package.jsonexists, withnpm run dev, orbun run devwhenbunis on yourPATHand abun.lockfile is present. API kits have nopackage.json, so this step is skipped. - Compiles your Go app to
.vel/tmp/serverand launches it.
Ctrl-C stops the Go server and the Vite process together. --no-watch
runs the server once without the file watcher.
Go changes rebuild and restart automatically
The watcher tracks every .go file under the project, skipping vendor,
node_modules, .git, .vel, and tmp. When you save:
- Changes are debounced for 500ms, so a burst of saves triggers one rebuild.
- The running server is stopped, the app is rebuilt with
go build, and the new binary starts on the same port. - The project’s
./velbinary is rebuilt too. Go’s build cache makes this near-instant since the same source was just compiled. One-shot commands in another terminal, such as./vel routes,./vel migrate, or./vel gen ..., always see your current code.
If the build fails, the compiler output is printed and the watcher waits for your next save; there is no stale server left running on old code.
.env is read when the server process starts. It is not watched, so after
editing it restart ./vel serve or save any Go file to trigger a restart.
Frontend changes hot-reload
For the React and Vue kits, Vite serves your assets during development with hot module replacement. Editing a page, component, or stylesheet updates the browser in place without a full reload and without touching the Go process.
The wiring is automatic. The Velocity Vite plugin writes a public/hot
marker holding the dev-server origin while Vite runs, and the vite template
helper in resources/views/app.html reads it: with the marker present it
emits the @vite/client script and the dev entry; without it, in production,
it emits the hashed <link> and <script> tags from the build manifest.
The marker is removed when Vite stops.
Migrations need no registration
Migrations are Go code, compiled into your binary. Each file in
database/migrations registers itself in an init() function, and the
starter kits blank-import that package from main.go, so the package is
always linked in.
./vel gen migration create_posts_table --create postsThat is the whole workflow. The generator writes the file, vel serve
notices the new .go file and rebuilds, and the refreshed ./vel binary
already knows the migration:
./vel migrateThere is no manifest to edit, no list to append to, and nothing to cache or
clear. Ordering comes from the 14-digit timestamp in each migration’s
Version, and registering the same version twice fails at startup rather
than at migrate time.
Generators for the rest
Every other piece of an app scaffolds the same way and lands in the conventional directory, ready to compile on the next save:
./vel gen handler PostHandler
./vel gen model Post
./vel gen middleware RateLimit
./vel gen job SendDigest
./vel gen policy PostPolicyEach generator is documented on its feature’s page; the vel Commands index links them all.
Give your AI agent the same view
Arrow runs alongside the project and exposes the live app to AI coding agents: registered routes, resolved config, database schema, recent logs, and the documentation index. The agent reads the real state of your app instead of guessing from source.