Deployment
Deploy Nub projects through GitHub Actions, the official container image, or the installer and npm package used by managed builders.
Choose the deployment path your platform exposes:
- GitHub Actions — use
nubjs/setup-nub@v0to install Nub, provision the project's Node, and cache the store. - Containers — use
ghcr.io/nubjs/nubas the base image. It contains Node and Nub forlinux/amd64andlinux/arm64. - Managed builders — install Nub with the installer or add
@nubjs/nubas a devDependency when the platform owns the install step.
| Platform | Deployment path | Where Nub runs |
|---|---|---|
| Vercel | Installer or devDependency | Install and build; Vercel Functions still use Vercel's Node runtime |
| Cloudflare | Preinstalled in Workers Builds; devDependency on Pages | Build only; Workers use Cloudflare's runtime |
| Railway | Dockerfile | Build and runtime |
| Render | Dockerfile | Build and runtime |
| AWS Lambda | Dockerfile with Lambda Web Adapter | Build and runtime |
| Google Cloud Run | Dockerfile | Build and runtime |
Managed builders
A hosted builder that runs the install from your lockfile cannot resolve Nub until the project supplies it:
sh: nub: not foundAdd the CLI as a devDependency and call it from a package script:
{
"devDependencies": {
"@nubjs/nub": "^0.7.5"
},
"scripts": {
"build": "nubx vite build"
}
}The package exposes both nub and nubx. npm, pnpm, Yarn, Bun, and Nub all link those commands without running a dependency lifecycle script, and the Nub launcher sets its own executable bit at runtime.
Keep development dependencies enabled for the build. Use the installer or a Dockerfile when the platform installs production dependencies only.
Container services
The official image starts from Node, installs Nub, and runs as the non-root node user. A web service only needs a Dockerfile and an application that listens on 0.0.0.0 at the provider's PORT:
FROM ghcr.io/nubjs/nub:0.7.5
COPY --chown=node:node package.json package-lock.json ./
RUN nub ci
COPY --chown=node:node . .
EXPOSE 8080
CMD ["nub", "run", "start"]Change package-lock.json to the lockfile the project already uses. Nub reads npm, pnpm, Bun, and Yarn lockfiles.
See Docker for the server contract and image variants.
GitHub Actions and registries
The setup action prepares the runner for tests and build scripts. Standard Docker actions can then build the application image from the Dockerfile above and publish it to GHCR:
name: Image
on:
push:
branches: [main]
permissions:
contents: read
packages: write
jobs:
image:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
- uses: nubjs/setup-nub@v0
- run: nub ci
- run: nub run test
- uses: docker/login-action@v3
with:
registry: ghcr.io
username: ${{ github.actor }}
password: ${{ secrets.GITHUB_TOKEN }}
- uses: docker/build-push-action@v6
with:
context: .
push: true
tags: ghcr.io/${{ github.repository }}:${{ github.sha }}Railway and Render can pull an application image from GHCR directly. AWS Lambda requires ECR, while Google recommends Artifact Registry for Cloud Run; the provider pages show those registry-specific steps.
Read the full docs on docs.github.com.
Node versions
A managed builder selects Node, and Nub augments that version. Pin Node with the source the platform supports, normally .node-version, .nvmrc, or package.json#engines.node.
A container carries its own Node version. Pin the Nub image tag and update it deliberately when you want a new Nub or Node release.
Environments driven by .tool-versions can also provision the CLI through mise: mise use nub@latest puts nub and nubx on PATH.
Config referencenub.jsonc
The project file that configures Nub's runtime, dependency installs, and temporary package runs.
GitHub Action
A drop-in replacement for the official setup-node action. Swap one line in your workflow and Nub installs itself, provisions the project's pinned Node, and fronts it on PATH so every step keeps working unchanged.