District CLI
The district command deploys code from a git repository to a target. A person signs in, pushes code to a repository that District hosts, and District builds the code and serves it on a target. This page explains these objects and their relationships. The guides show commands for common tasks. The reference lists every command, its arguments, flags, output, and exit codes.
The CLI runs on macOS and Linux.
The hierarchy
Each object belongs to the object above it.
Organization
An organization is an account for a company, a team, or one person. It owns the objects below. A person can belong to several organizations. A session acts in one organization at a time.
Workspace
An organization has workspaces. Each workspace has repositories and apps and controls access to them. A person can open one or more workspaces in an organization. The person who creates a workspace is its administrator.
Repository
A repository is a standard git repository that District hosts. It has a display name, a slug, and a git remote URL. The slug is unique inside its workspace, not across workspaces. The CLI registers a git credential helper once per machine. After that, standard git commands work on the remote URL. Clone, fetch, and push each get a short-lived token from the helper, so the machine stores no long-lived token.
App
An app is a repository that is published for serving. A repository backs at most one app. The app owns the targets that serve it and the custom domains attached to those targets.
Target
A target is where a deployment goes. Its address is always a subdomain of a zone that District owns: <label>.ondistrict.net in production. Staging has its own zone, and the CLI prints the address a target has. A target serves one deployment of an app. A target has one of two kinds:
- A durable target keeps its label until it is deleted. An app holds at most 5 durable targets. Exactly one of them is the primary target, which a deploy uses when no other target is named.
- A preview target has a generated label and expires 7 days after its last successful deployment. An app holds at most 20 unexpired preview targets.
A custom domain serves a target on a name that its owner controls.
Build
A build turns one commit of a repository into a bundle that District can serve. It runs on District, not on the machine that started it, so closing the terminal does not stop it. A build has five steps: checkout, install, build, bundle, and export. It succeeds, fails at one step, or errors before a step can fail.
Deployment
A deployment serves one build on one target. A target holds its current deployment until a later deployment of the same target finishes, or until a person points the target at another deployment. Pointing a target at an earlier deployment is a rollback, and it runs no build. Each target has an environment, which selects the bindings of its deployments. A target serves only a deployment made for its environment, so a preview deployment reaches the primary target through a new deployment of the same build: district deploy --from makes it and runs no build.
Custom domain
A custom domain is a DNS name that its owner controls, such as shop.example.com, attached to one durable target of an app. The domain serves what that target serves. An app holds at most 2 custom domains. After the owner publishes the DNS records that District names, District verifies the domain and issues its certificate. The domain is pending until then. It is active while it serves the app, and failing while it serves the app but a check fails.
Addon
An addon is a resource a workspace owns: a D1 database, an R2 bucket, or a KV namespace. A workspace holds at most 10 D1 databases, 10 R2 buckets, and 3 KV namespaces. Creating an addon binds it to no app. An app binds it through its own wrangler configuration, which names the addon by its alias, a stable form of its id. Each deployment records the addons it binds. Deleting an addon destroys its data.
Environments
District runs in three environments: production, staging, and dev. Each environment has its own accounts, repositories, and apps. The CLI stores one session per environment, so a person can be signed in to several at once. The environment of the last sign-in is the current environment. A command acts in the current environment unless a flag names another. Before any sign-in, the current environment is production.
Identifiers
Each object has an id. Its prefix names the kind of object. A command accepts the id wherever it accepts a name or a slug, and the id does not change when the name or the slug changes.
| Prefix | Object |
|---|---|
org_ | Organization |
ws_ | Workspace |
repo_ | Repository |
happ_ | App |
htgt_ | Target |
hbld_ | Build |
hdep_ | Deployment |
hdom_ | Custom domain |
hadd_ | Addon |
Where to go next
- Getting started: install the CLI, sign in, create a repository, and deploy a page to a target.
- Deploy a TanStack Start app: build a server-rendered React app with Vite and serve it on a target.
- Managing deployments: previews, promotions, rollbacks, and scripts.
- Bindings and environments: bind addons, and select each target's bindings with an environment.
- Custom domains: serve an app on a domain you own.
- Command reference: every command, with its arguments, flags, output, and exit codes.