Push Command
Tag, push, and optionally deploy an image to the Gordon registry.
gordon push
Synopsis
gordon push [image] [options]
Arguments
| Argument |
Description |
[image] |
Image name to push (optional). If omitted, auto-detected from Dockerfile labels or current directory name |
Options
| Option |
Description |
--build |
Build the image first using docker buildx |
-f, --file |
Path to Dockerfile (default: ./Dockerfile, used with --build) |
--platform |
Target platform for buildx (default: linux/amd64) |
--build-arg |
Additional build args (repeatable, KEY=VALUE) |
--tag |
Override pushed version tag (default: tag ref from CI, then git describe --tags --dirty) |
--no-confirm |
Skip deploy confirmation prompt |
--no-deploy |
Push only; skip deployment prompt |
--domain |
Explicit deploy target override |
--remote, -r |
Remote name or URL (e.g., prod, https://gordon.mydomain.com) |
--token |
Authentication token for remote |
Description
gordon push tags the selected image for the Gordon registry, pushes it, and
optionally deploys matching routes.
If you do not pass --remote and no active remote is configured, Gordon tries to
infer the correct saved remote by probing your saved remotes for a matching route.
It auto-selects only when exactly one remote matches. If multiple remotes match,
or a saved remote cannot be probed safely, the command stops and asks you to use
--remote explicitly.
Image resolution order:
--domain is the explicit deploy target override for legacy workflows
- Positional refs resolve routes by image name; tagged refs still use the image name for lookup
- Dotted positional refs probe image routes first, then fall back to legacy domain lookup
- No-arg mode auto-detects from the Dockerfile label or current directory
The pushed version still comes from --tag, CI tag refs, or git describe --tags --dirty.
To push attachment images (databases, caches, etc.), use gordon attachments push.
- For first deploys, run
gordon bootstrap first to create or update the route, attachments, and secrets, then run gordon push to upload and deploy the image.
- The registry and repository are derived from the route image on the server.
- The version tag defaults to a CI tag ref (like
refs/tags/v1.2.3) when available,
then falls back to git describe --tags --dirty (for example
v1.2.3-4-gabc1234 or v1.2.3-dirty). If no tag is found, latest is used.
- When
--build is set, the command builds with docker buildx build --load
and injects VERSION, GIT_TAG, GIT_SHA, and BUILD_TIME into the build
environment plus any --build-arg values. To use these in your Dockerfile,
declare them with ARG (e.g., ARG VERSION) then reference via ENV or
in build steps.
- Use
-f/--file to build from a Dockerfile outside the current directory root.
- The version tag and
latest are both pushed (unless the version is latest).
Authentication
When used with --remote, gordon push authenticates in two ways:
- Admin API (route resolution, deploy): uses
--token or $GORDON_TOKEN as Bearer token
- Registry push: automatically exchanges the token for a short-lived (5 min) registry access token via
/auth/token -- no docker login required
This means CI/CD pipelines only need a single secret (GORDON_TOKEN).
Deploy Modes
When the token has admin:config:write scope, the CLI manages deployment explicitly
(DeployIntent → push → Deploy). This gives the CLI control over deploy timing.
When the token lacks admin:config:write, the CLI pushes the image and the server
auto-deploys when it receives it via its event listener. The CLI logs:
info: deploy intent skipped (insufficient scope), server will auto-deploy on image receive
Version Auto-Detection
Gordon reads version tags from CI environment variables (in priority order):
| CI System |
Variable |
Example |
| GitHub Actions |
$GITHUB_REF |
refs/tags/v1.2.0 |
| GitHub Actions |
$GITHUB_REF_TYPE + $GITHUB_REF_NAME |
tag + v1.2.0 |
| GitLab CI |
$CI_COMMIT_TAG |
v1.2.0 |
| Azure DevOps |
$BUILD_SOURCEBRANCH |
refs/tags/v1.2.0 |
| Any |
git describe --tags |
v1.2.3-4-gabc1234 |
| Fallback |
- |
latest |
Examples
# Build, push, and deploy (auto-detect image name)
gordon push --build --remote https://gordon.example.com --no-confirm
# Push an image and deploy it
gordon push myapp --remote https://gordon.example.com --no-confirm
# Push and deploy to an explicit domain
gordon push myapp:latest --domain app.example.com --remote https://gordon.example.com --no-confirm
# Tagged refs still resolve routes by image name
gordon push myapp:v1.2.3 --tag v1.2.3 --no-deploy
# Push existing local image, skip deploy
gordon push myapp --tag v1.2.0 --no-deploy
# Build for ARM and pass build args
gordon push myapp --build --platform linux/arm64 --build-arg CGO_ENABLED=0
# Build from a custom Dockerfile path
gordon push myapp --build -f docker/app/Dockerfile
# Legacy compatibility: domain-looking positional target
gordon push app.example.com --no-confirm
# CI/CD usage (single env var, no docker login needed)
export GORDON_TOKEN="your-token"
gordon push myapp --build --remote https://gordon.example.com --no-confirm
Notes
- Remote mode required. See CLI Overview for targeting options.
gordon push requires the target route to already exist so it can resolve the deploy target.
Use gordon bootstrap for first deploys.
--build requires Docker with Buildx. Docker Desktop includes it; on Linux,
install the docker-buildx-plugin package.
- Gordon uses native registry uploads instead of shelling out to
docker push.
Image layers are sent in 50MB chunks, which stays under Cloudflare's 100MB
per-request limit so proxied pushes keep working. Keep the server's
max_blob_chunk_size larger than the client chunk size; the default 95MB
works out of the box.
source
1# Push Command
2
3Tag, push, and optionally deploy an image to the Gordon registry.
4
5## gordon push
6
7### Synopsis
8
9```bash
10gordon push [image] [options]
11```
12
13### Arguments
14
15| Argument | Description |
16|----------|-------------|
17| `[image]` | Image name to push (optional). If omitted, auto-detected from Dockerfile labels or current directory name |
18
19### Options
20
21| Option | Description |
22|--------|-------------|
23| `--build` | Build the image first using `docker buildx` |
24| `-f, --file` | Path to Dockerfile (default: `./Dockerfile`, used with `--build`) |
25| `--platform` | Target platform for buildx (default: `linux/amd64`) |
26| `--build-arg` | Additional build args (repeatable, `KEY=VALUE`) |
27| `--tag` | Override pushed version tag (default: tag ref from CI, then `git describe --tags --dirty`) |
28| `--no-confirm` | Skip deploy confirmation prompt |
29| `--no-deploy` | Push only; skip deployment prompt |
30| `--domain` | Explicit deploy target override |
31| `--remote, -r` | Remote name or URL (e.g., prod, https://gordon.mydomain.com) |
32| `--token` | Authentication token for remote |
33
34### Description
35
36`gordon push` tags the selected image for the Gordon registry, pushes it, and
37optionally deploys matching routes.
38
39If you do not pass `--remote` and no active remote is configured, Gordon tries to
40infer the correct saved remote by probing your saved remotes for a matching route.
41It auto-selects only when exactly one remote matches. If multiple remotes match,
42or a saved remote cannot be probed safely, the command stops and asks you to use
43`--remote` explicitly.
44
45Image resolution order:
461. `--domain` is the explicit deploy target override for legacy workflows
472. Positional refs resolve routes by image name; tagged refs still use the image name for lookup
483. Dotted positional refs probe image routes first, then fall back to legacy domain lookup
494. No-arg mode auto-detects from the Dockerfile label or current directory
50
51The pushed version still comes from `--tag`, CI tag refs, or `git describe --tags --dirty`.
52
53To push attachment images (databases, caches, etc.), use `gordon attachments push`.
54
55- For first deploys, run `gordon bootstrap` first to create or update the route, attachments, and secrets, then run `gordon push` to upload and deploy the image.
56- The registry and repository are derived from the route image on the server.
57- The version tag defaults to a CI tag ref (like `refs/tags/v1.2.3`) when available,
58 then falls back to `git describe --tags --dirty` (for example
59 `v1.2.3-4-gabc1234` or `v1.2.3-dirty`). If no tag is found, `latest` is used.
60- When `--build` is set, the command builds with `docker buildx build --load`
61 and injects `VERSION`, `GIT_TAG`, `GIT_SHA`, and `BUILD_TIME` into the build
62 environment plus any `--build-arg` values. To use these in your Dockerfile,
63 declare them with `ARG` (e.g., `ARG VERSION`) then reference via `ENV` or
64 in build steps.
65- Use `-f/--file` to build from a Dockerfile outside the current directory root.
66- The version tag and `latest` are both pushed (unless the version is `latest`).
67
68### Authentication
69
70When used with `--remote`, gordon push authenticates in two ways:
71
72- **Admin API** (route resolution, deploy): uses `--token` or `$GORDON_TOKEN` as Bearer token
73- **Registry push**: automatically exchanges the token for a short-lived (5 min) registry access token via `/auth/token` -- no `docker login` required
74
75This means CI/CD pipelines only need a single secret (`GORDON_TOKEN`).
76
77### Deploy Modes
78
79When the token has `admin:config:write` scope, the CLI manages deployment explicitly
80(DeployIntent → push → Deploy). This gives the CLI control over deploy timing.
81
82When the token lacks `admin:config:write`, the CLI pushes the image and the server
83auto-deploys when it receives it via its event listener. The CLI logs:
84`info: deploy intent skipped (insufficient scope), server will auto-deploy on image receive`
85
86### Version Auto-Detection
87
88Gordon reads version tags from CI environment variables (in priority order):
89
90| CI System | Variable | Example |
91|-----------|----------|---------|
92| GitHub Actions | `$GITHUB_REF` | `refs/tags/v1.2.0` |
93| GitHub Actions | `$GITHUB_REF_TYPE` + `$GITHUB_REF_NAME` | `tag` + `v1.2.0` |
94| GitLab CI | `$CI_COMMIT_TAG` | `v1.2.0` |
95| Azure DevOps | `$BUILD_SOURCEBRANCH` | `refs/tags/v1.2.0` |
96| Any | `git describe --tags` | `v1.2.3-4-gabc1234` |
97| Fallback | - | `latest` |
98
99### Examples
100
101```bash
102# Build, push, and deploy (auto-detect image name)
103gordon push --build --remote https://gordon.example.com --no-confirm
104
105# Push an image and deploy it
106gordon push myapp --remote https://gordon.example.com --no-confirm
107
108# Push and deploy to an explicit domain
109gordon push myapp:latest --domain app.example.com --remote https://gordon.example.com --no-confirm
110
111# Tagged refs still resolve routes by image name
112gordon push myapp:v1.2.3 --tag v1.2.3 --no-deploy
113
114# Push existing local image, skip deploy
115gordon push myapp --tag v1.2.0 --no-deploy
116
117# Build for ARM and pass build args
118gordon push myapp --build --platform linux/arm64 --build-arg CGO_ENABLED=0
119
120# Build from a custom Dockerfile path
121gordon push myapp --build -f docker/app/Dockerfile
122
123# Legacy compatibility: domain-looking positional target
124gordon push app.example.com --no-confirm
125
126# CI/CD usage (single env var, no docker login needed)
127export GORDON_TOKEN="your-token"
128gordon push myapp --build --remote https://gordon.example.com --no-confirm
129```
130
131### Notes
132
133- Remote mode required. See [CLI Overview](./index.md) for targeting options.
134- `gordon push` requires the target route to already exist so it can resolve the deploy target.
135 Use `gordon bootstrap` for first deploys.
136- `--build` requires Docker with Buildx. Docker Desktop includes it; on Linux,
137 install the `docker-buildx-plugin` package.
138- Gordon uses native registry uploads instead of shelling out to `docker push`.
139 Image layers are sent in 50MB chunks, which stays under Cloudflare's 100MB
140 per-request limit so proxied pushes keep working. Keep the server's
141 `max_blob_chunk_size` larger than the client chunk size; the default `95MB`
142 works out of the box.
143
144## Related
145
146- [CLI Overview](./index.md)
147- [Deployment Overview](../deployment/index.md)
148- [GitHub Actions](../deployment/github-actions.md)
149- [Attachments Commands](./attachments.md)
150- [Routes Command](./routes.md)
151- [Authentication](../config/auth.md)