| 99 | 99 | | | `wrangler.jsonc`, `wrangler.json` or `wrangler.toml` | Builds it as a **Workers project**: installs dependencies, runs `wrangler deploy --dry-run` to bundle it (which runs the config's own `build` command), and deploys the bundle with the config's static assets, `compatibility_date`, `compatibility_flags` and `vars`. | |
| 100 | 100 | | | A framework from the table below | Installs dependencies, builds it with the framework's command, and serves the folder it writes as a **static site**, or deploys the Worker its Cloudflare adapter writes as a **Workers project**. | |
| 101 | 101 | | | A framework set up to need a server (Next.js without a static export, Astro's `@astrojs/node`, SvelteKit's `adapter-node`, a server-rendered React Router or Remix app) | Builds it as a **container**: from its `Dockerfile`, or one g1t writes for it. | |
| 102 | | − | | A `Dockerfile` or `Containerfile`, and no framework above | Builds the image and runs it as a **container**. | |
| 103 | | − | | A Node.js, Python, Go, Ruby or PHP server, with no `Dockerfile` | Writes a Dockerfile for it, shows it in the build's log, and runs it as a **container**. See [Docker deployments](#docker-deployments). | |
| 102 | + | | A `Dockerfile` or `Containerfile` that runs a server (`CMD`, `ENTRYPOINT` or `EXPOSE`), even beside a site or a framework above | Builds the image and runs it as a **container**. | |
| 103 | + | | A `Dockerfile` and nothing else to serve | Builds the image and runs it as a **container**. | |
| 104 | + | | A Node.js, Python, Go, Ruby, PHP or Rust server, with no `Dockerfile` | Writes a Dockerfile for it, shows it in the build's log, and runs it as a **container**. See [Docker deployments](#docker-deployments). | |
| 104 | 105 | | | A `build` script in `package.json` | Installs dependencies, runs `npm run build`, and serves the output as a **static site**. | |
| 105 | 106 | | | An `index.html` and nothing to build | Serves it as it is. | |
| 106 | 107 | | | Nothing g1t recognises | Fails, saying to add a `Dockerfile`. | |
| ⋯ |
| 211 | 212 | | behind the app's Worker, at the same addresses, custom domains and |
| 212 | 213 | | previews as any other app. |
| 213 | 214 | | |
| 214 | | − | :::caution[Not switched on yet] |
| 215 | | − | Docker deployments are built but off on g1t.page until Cloudflare's |
| 216 | | − | container APIs are checked against g1t's account. Until then a container |
| 217 | | − | build fails with "Docker deployments are not switched on for g1t.page |
| 218 | | − | yet", and a project that is a container only for having a `Dockerfile`, |
| 219 | | − | beside a site g1t could serve, is built as that site, as before. |
| 220 | | − | ::: |
| 221 | | − | |
| 222 | | − | What a project is built as is decided in this order: |
| 215 | + | There is nothing to set: push a project with a `Dockerfile`, or a server |
| 216 | + | g1t recognises, and it deploys as a container. What a project is built as |
| 217 | + | is decided in this order: |
| 223 | 218 | | |
| 224 | 219 | | 1. **Build as**, under **Settings → Deployments**: **Static site**, |
| 225 | 220 | | **Workers** or **Docker** is what it is built as, whatever else it has. |
| 226 | 221 | | 2. **Auto** (the default) finds it from its files: |
| 227 | | − | 1. A Wrangler config is a Workers project. |
| 228 | | − | 2. A framework that builds a static site or a Worker is that, even |
| 229 | | − | beside a `Dockerfile`: it costs nothing while no one visits. |
| 230 | | − | 3. A framework set up to need a server is a container, from its |
| 222 | + | 1. A Wrangler config, or a framework's Cloudflare adapter, is a |
| 223 | + | Workers project. |
| 224 | + | 2. A site (a framework that builds one, a `build` script, or an |
| 225 | + | `index.html`) beside a `Dockerfile` is a container when the |
| 226 | + | Dockerfile runs a server: its last stage has `CMD` or `ENTRYPOINT`, |
| 227 | + | or `EXPOSE` on an image that is not only a file server. A |
| 228 | + | Dockerfile that only copies the site into `nginx`, `httpd`, `caddy`, |
| 229 | + | `lighttpd`, `busybox` or another file server, or says none of those, |
| 230 | + | leaves it a site, which g1t serves itself for nothing while no one |
| 231 | + | visits. |
| 232 | + | 3. A framework that builds a static site, with no such Dockerfile, is |
| 233 | + | that site. |
| 234 | + | 4. A framework set up to need a server is a container, from its |
| 231 | 235 | | `Dockerfile`, or one g1t writes for it. |
| 232 | | − | 4. A project with no framework g1t knows is a container when it has a |
| 236 | + | 5. A project with no framework g1t knows is a container when it has a |
| 233 | 237 | | `Dockerfile` (or `Containerfile`, or the path set as its |
| 234 | 238 | | **Dockerfile**), or is a server g1t recognises. |
| 235 | | − | 5. Otherwise a static site or plain HTML, as above; with nothing to |
| 239 | + | 6. Otherwise a static site or plain HTML, as above; with nothing to |
| 236 | 240 | | serve, the build fails, saying to add a `Dockerfile`. |
| 237 | 241 | | |
| 242 | + | When a project could be either, the build's log says which it chose and |
| 243 | + | why, near its top: for example, "Building it as a container from |
| 244 | + | Dockerfile, not as the static site it also has: its Dockerfile starts a |
| 245 | + | server of its own (`CMD`). Set **Build as** to Static site to serve the |
| 246 | + | site instead." |
| 247 | + | |
| 238 | 248 | | g1t writes a Dockerfile for these, when there is none: |
| 239 | 249 | | |
| 240 | 250 | | | The project has | Runs with | |
| 241 | 251 | | | --- | --- | |
| 242 | 252 | | | `package.json` with a `start` script, or a server package (`express`, `fastify`, `koa`, `@nestjs/core`, `@hono/node-server` and others) and a main file | `npm start`, or `node <main>`, on `node:22-slim` (or the major release in `.nvmrc` or `.node-version`), after `npm run build` when there is one | |
| 243 | | − | | Next.js, Astro with `@astrojs/node`, SvelteKit with `adapter-node`, React Router or Remix | `next start`, `node ./dist/server/entry.mjs`, `node build`, `react-router-serve` or `remix-serve`, after the build | |
| 253 | + | | Next.js, Astro with `@astrojs/node`, SvelteKit with `adapter-node`, React Router or Remix | `next start` (or `node .next/standalone/server.js`, with its static files beside it, for `output: 'standalone'`), `node ./dist/server/entry.mjs`, `node build`, `react-router-serve` or `remix-serve`, after the build | |
| 244 | 254 | | | `requirements.txt`, `pyproject.toml` or `Pipfile`, and `manage.py` (Django) | `gunicorn <project>.wsgi` on `python:3.12-slim` | |
| 245 | 255 | | | The same, with Flask and an `app.py`, `main.py`, `server.py`, `wsgi.py` or `asgi.py` | `gunicorn <module>:app` | |
| 246 | 256 | | | The same, with FastAPI or Starlette | `uvicorn <module>:app` | |
| ⋯ |
| 249 | 259 | | | A `Gemfile` with Rails | `rails server`, after `assets:precompile`, on `ruby:3.3-slim` | |
| 250 | 260 | | | A `Gemfile` and a `config.ru` | `rackup` | |
| 251 | 261 | | | `composer.json`, and `artisan` with `public/index.php` (Laravel), or an `index.php` | Apache with PHP 8.3, after `composer install` | |
| 262 | + | | `Cargo.toml` with one program and `axum`, `actix-web`, `rocket`, `warp`, `poem`, `salvo` or `tide` | The program, built with `rust:1` into `debian:bookworm-slim` | |
| 252 | 263 | | |
| 253 | 264 | | The Dockerfile g1t writes is printed whole in the build's log. To change |
| 254 | 265 | | how the app is built or run, commit it as `Dockerfile` and edit it. It |
| ⋯ |
| 257 | 268 | | What a container gets, and what it must do: |
| 258 | 269 | | |
| 259 | 270 | | - **Listen on `0.0.0.0` at `PORT`.** `PORT` is the port its Dockerfile's |
| 260 | | − | first `EXPOSE` names (in its last stage), else `8080`. The first request |
| 271 | + | first `EXPOSE` names (in its last stage), else the `PORT` it sets with |
| 272 | + | `ENV`, else `8080`. A Dockerfile g1t writes sets `HOST` and `HOSTNAME` |
| 273 | + | to `0.0.0.0` too. The first request |
| 261 | 274 | | waits up to 90 seconds for it to answer there; one that never does gets |
| 262 | 275 | | a 503 page saying so. |
| 263 | 276 | | - **The project's [secrets and variables](#secrets-and-variables)** are |
| ⋯ |
| 271 | 284 | | - **Its size** is **Container size** under **Settings → Deployments**: |
| 272 | 285 | | `lite` (the default) to `standard-4`, as [What it costs](#what-it-costs) |
| 273 | 286 | | lists. The image may be as large as the size's disk, 2 GB for `lite`; |
| 274 | | − | a larger image fails the build, saying how large it was. |
| 287 | + | a larger image fails the build, saying how large it was. An app keeps |
| 288 | + | the image it runs and the one before it; older ones are deleted once a |
| 289 | + | deploy is live, and all of them when the app is taken down. |
| 275 | 290 | | - **Built for `linux/amd64`**, with Docker, in the build's sandbox (or the |
| 276 | 291 | | workflow job's Docker, for [`g1t-runner deploy`](#deploying-from-a-workflow)), |
| 277 | 292 | | with network access as any build has. **Build command** is not used: |
| ⋯ |
| 864 | 879 | | | A deployment **Skipped**, saying it reached its spend limit or that new compute is paused | The build was refused before it started. Follow the link in the message: raise the spend limit, prepay, or answer the spike, on Billing. | |
| 865 | 880 | | | "Stopped: unusual CPU use" | The build looked like it was mining. Contact support if it was a real build; see [abuse and mining](/guides/guardrails/#abuse-and-mining). | |
| 866 | 881 | | | "found nothing to serve" | Add a `Dockerfile`, a `build` script, an `index.html`, or a Workers config; or set **Output directory**. | |
| 867 | | − | | "Docker deployments are not switched on for g1t.page yet" | The project is a container, which g1t.page does not run yet. Set **Build as** to Static site or Workers if it can be built as one. See [Docker deployments](#docker-deployments). | |
| 882 | + | | "Docker deployments are switched off on this g1t" | The project is a container, and this g1t (a self-hosted one) runs none. Set **Build as** to Static site or Workers if it can be built as one. See [Docker deployments](#docker-deployments). | |
| 868 | 883 | | | "**Build as** is Docker, but this project has no Dockerfile" | Add a `Dockerfile`, or set **Dockerfile** to its path. | |
| 869 | 884 | | | "The image is 2.4 GB, more than the 2.0 GB an app of its size (lite) can hold" | Make the image smaller (a slim base image, a multi-stage build), or choose a larger **Container size**. | |
| 870 | 885 | | | A container app says "The app did not start" | It did not answer on its port within 90 seconds. Make it listen on `0.0.0.0` at `PORT`, or `EXPOSE` the port it uses in its Dockerfile. Its output is in the build's log only while it builds; run the image locally with `docker run -e PORT=8080 -p 8080:8080` to see it start. | |
| ⋯ |
| 894 | 909 | | `npx wrangler secret put CLOUDFLARE_API_TOKEN` in `services/deployments`. |
| 895 | 910 | | 4. Deploy `services/deployments`, `services/pages`, and the runner. |
| 896 | 911 | | |
| 897 | | − | Docker deployments also need the token to have **Containers: Edit**, a |
| 898 | | − | Workers Paid plan with Containers, and `CONTAINERS` set to `on` in |
| 899 | | − | `services/deployments/wrangler.jsonc`; see |
| 912 | + | Docker deployments also need the token to have **Containers: Edit** and |
| 913 | + | a Workers Paid plan with Containers; `CONTAINERS` in |
| 914 | + | `services/deployments/wrangler.jsonc` is `on`, and `off` turns them off |
| 915 | + | for an account without Containers. See |
| 900 | 916 | | [Docker deployments](/guides/deploy-to-cloudflare/#docker-deployments) |
| 901 | | − | for what to check first. |
| 917 | + | for what to check on a new account. |
| 902 | 918 | | |
| 903 | 919 | | Custom domains also need Cloudflare for SaaS on the apps' zone. Turn it on |
| 904 | 920 | | under the zone's **SSL/TLS → Custom Hostnames**, give the token **SSL and |