nexos.yaml
One file at the root of your repo configures your entire preview environment — the Dockerfile, the port, the services, the migrations, the secrets. Nexos reads it on every push and applies it before the build starts. Every field is optional.
Open your AI assistant inside your repo and paste this link: nexos.rs/docs/nexos-yaml/ai. That page is a self-contained spec written for AI agents — it tells them exactly how to detect your stack, write your nexos.yaml, and create a Dockerfile.nexos if your repo doesn't have a Dockerfile that works for preview environments. No setup, no back-and-forth.
Where to put it
You have two options. Pick whichever fits your workflow:
- Commit it to your repo as
nexos.yamlat the root. Nexos fetches it from each pushed commit and applies it before building. Branches can have different configs — useful for testing a setting change in isolation. - Paste it in the dashboard. Open Project → Settings → YAML, paste, click Apply. Useful when you want to try a config without a commit, or to bulk-import env vars and services.
If both exist, the committed file wins for fields it sets. Anything it omits keeps the dashboard value. Treat the repo file as the source of truth for everything you want version-controlled.
Full example
Every field below is optional. Drop in just the ones you care about.
# nexos.yaml
name: my-app
build:
dockerfile: ./Dockerfile # or ./Dockerfile.nexos
context: .
args:
NODE_VERSION: "20"
app:
port: 3000 # injected as $PORT
cpu: 1 # cores
memory: 512 # MB
buildResources:
cpu: 2
memory: 2048
timeout: 600 # seconds
services:
postgres: true # shorthand: enabled with defaults
redis:
enabled: true
version: "7"
mongodb: false # explicitly disabled
hooks:
on_deploy: npx prisma migrate deploy
on_new: node scripts/seed-admin.js
env:
NODE_ENV: production
LOG_LEVEL: info
containers:
- name: worker
dockerfile: ./worker/Dockerfile
cpu: 0.5
memory: 256
command: node worker.js
depends_on: [api]
env:
QUEUE_NAME: jobs
- name: api
dockerfile: ./api/Dockerfile
port: 3001
public: true # gets its own preview subdomain
Minimal example
For a Node app with Postgres, this is all you need:
# nexos.yaml — minimum viable
app:
port: 3000
services:
postgres: true
Field reference
name
Project display name. Used in the dashboard and in preview URLs: {branch}-{name}.nexos.rs.
build
dockerfile— path to the Dockerfile. Default./Dockerfile. Use./Dockerfile.nexosif you want a Nexos-specific build alongside an existing Dockerfile.context— build context directory. Default..args— key/value pairs passed as--build-arg. Stored in plaintext; not for secrets.
app
The main container — what users hit when they open the preview URL.
port— port your app listens on. Also injected as$PORTso frameworks pick it up automatically.cpu— CPU cores (e.g.0.5,1,2). Default1.memory— RAM in MB. Default512.
buildResources
Limits applied during the image build, separate from runtime limits.
cpu— cores for the build. Default2.memory— RAM in MB during the build. Default2048.timeout— max build duration in seconds. Default600(10 minutes). Hung builds get killed.
services
Managed addons that get provisioned alongside your app. Each environment gets its own copy — push a new branch, get a fresh database. Use the boolean shorthand to enable with defaults, or an object to pin a version or storage size.
| Service | Versions | Injected env var |
|---|---|---|
postgres | 14, 15, 16 | DATABASE_URL |
redis | 6, 7 | REDIS_URL |
mongodb | 5, 6, 7 | MONGODB_URL |
elasticsearch | 7.x, 8.x | ELASTICSEARCH_URL |
minio (S3-compatible) | latest | S3_ENDPOINT, S3_ACCESS_KEY, S3_SECRET_KEY, S3_BUCKET |
mailhog (SMTP capture) | latest | SMTP_HOST, SMTP_PORT |
Object form fields:
enabled— defaults totrueif the key is present. Setfalseto disable.version— pin a specific version string.storageMb— persistent volume size in MB.
hooks
Commands that run inside your app container at deploy time.
on_deploy— runs on every deploy (new and incremental). For migrations:prisma migrate deploy,rails db:migrate,alembic upgrade head.on_new— runs only the first time an environment is created, after the database is seeded. For one-time setup: create admin user, provision an API key, etc.
env
Shared environment variables. Keys/values are upserted (existing keys not in the file are left alone). Encrypted at rest with AES-256-GCM. For real secrets you don't want in git, set them in the dashboard instead.
containers
Extra containers that deploy with your app — workers, separate APIs, background jobs. Reconciled by name: containers in the file are upserted, ones removed from the file get torn down.
name— lowercase, alphanumeric + hyphens.dockerfile,context,port,cpu,memory— same as the top-levelapp.public— iftrue, the container gets its own preview subdomain. Defaultfalse(internal-only).command— override the image CMD. Required for jobs.type—service(default, long-running) orjob(runs once per deploy, must setcommand).depends_on— list of sibling container names this one waits on. Nexos walks the DAG topologically, so independent containers build in parallel.env— per-container overrides on top of top-levelenv.default— iftrue, the preview URL routes to this container instead ofapp. At most one container can set it.run_hooks— iftrue, hooks run inside this container instead ofapp. At most one container can set it.
nodePool
Which compute pool to schedule onto.
type—shared(default, runs on the global pool) orprivate(only your or your team's nodes).
preview
Build mode for preview environments. See Dev Preview Mode.
mode—prod(default, compile every deploy),dev(always hot-reload), ordraft-based(draft PRs hot-reload, ready PRs compile).
Per-container dev overrides live on each entry in containers: dev_command, dev_install, dev_image, and dev_watch (globs that force a type: job to re-run on a sync).
Errors and safety
- A broken YAML in a commit is logged and skipped — the deploy still runs with the last good config. Check the deployment logs for the parse error.
- The dashboard editor validates before applying, so paste-and-apply is non-destructive if the file is broken.
- Real secrets belong in dashboard env vars, not committed
env:blocks.
See also
- AI agent spec — the version to hand to your AI assistant.
- Environment Variables — what gets auto-injected and how secrets are encrypted.
- Deployments — how a push becomes a live URL.