Skip to content

Commit 223fdb1

Browse files
committed
docs(deploy): add production deployment automation guide
1 parent 8a6b2ce commit 223fdb1

1 file changed

Lines changed: 104 additions & 0 deletions

File tree

docs/deployment-automation.md

Lines changed: 104 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,104 @@
1+
# Rend Production Deploy Automation
2+
3+
This workflow keeps the bare-metal control plane and edge hosts on the latest
4+
released binaries after a `main` build.
5+
6+
The GitHub Actions workflow is `.github/workflows/release-deploy.yml`.
7+
8+
## Flow
9+
10+
1. Build `rend-api`, `rend-media-worker`, and `rend-edge` Docker targets.
11+
2. Push them to GHCR under `ghcr.io/<org>/rend/<service>`.
12+
3. Write a release manifest with immutable `@sha256:` image refs.
13+
4. Wait on the GitHub `Production` environment approval if that environment is
14+
configured with required reviewers.
15+
5. SSH to the control-plane host and run:
16+
- `scripts/preflight-control-plane-host.sh --skip-bind-port-check`
17+
- `scripts/deploy-control-plane-host.sh --dry-run`
18+
- `scripts/deploy-control-plane-host.sh`
19+
- local `rend-api` `/readyz` and `/healthz`
20+
The deploy helper waits for `rend-api` `/readyz` before starting
21+
`rend-media-worker`.
22+
6. SSH to each configured edge host, serially, and run:
23+
- `scripts/preflight-edge-host.sh --skip-bind-port-check`
24+
- `scripts/deploy-edge-host.sh --dry-run`
25+
- `scripts/deploy-edge-host.sh`
26+
- local `rend-edge` `/readyz` and `/healthz`
27+
7. Check public API `/readyz`.
28+
8. Run the synthetic playback readiness gate when the required readiness secrets
29+
and edge targets are configured.
30+
31+
Preflight skips bind-port checks during automated updates because the existing
32+
service should already own the port. It still validates env files, registry
33+
pullability, image platform, host dependencies, managed dependency reachability,
34+
edge control-plane registration/heartbeat, and telemetry ingest.
35+
36+
## Required GitHub Environment
37+
38+
Create a GitHub Environment named `Production`. Configure required reviewers if
39+
production deploys should pause for human approval after the image release.
40+
41+
## Required Secrets
42+
43+
Set these as `Production` environment secrets unless noted otherwise:
44+
45+
- `REND_SSH_PRIVATE_KEY`: private key with SSH access to the control-plane and
46+
edge hosts.
47+
- `REND_SSH_KNOWN_HOSTS`: pinned host key lines for all SSH targets.
48+
- `REND_CONTROL_PLANE_SSH_HOST`
49+
- `REND_CONTROL_PLANE_SSH_USER`
50+
- `REND_CONTROL_PLANE_SSH_PORT` (optional; defaults to `22`)
51+
- `REND_EDGE_ASH_SSH_HOST`
52+
- `REND_EDGE_ASH_SSH_USER`
53+
- `REND_EDGE_ASH_SSH_PORT` (optional; defaults to `22`)
54+
- `REND_EDGE_AMS_SSH_HOST`
55+
- `REND_EDGE_AMS_SSH_USER`
56+
- `REND_EDGE_AMS_SSH_PORT` (optional; defaults to `22`)
57+
- `REND_READINESS_API_KEY`: API key with upload, read, delete, and analytics
58+
scopes for synthetic readiness media.
59+
- `REND_EDGE_INTERNAL_TOKEN`: edge internal token for readiness warm, purge, and
60+
metrics checks.
61+
62+
Generate known-hosts entries from a trusted operator machine, verify the
63+
fingerprints out of band, then paste the lines into `REND_SSH_KNOWN_HOSTS`:
64+
65+
```sh
66+
ssh-keyscan -H api-internal.play.rend.so ash-1.play.rend.so ams-1.play.rend.so
67+
```
68+
69+
Each host must already be able to pull from GHCR in the Docker daemon context
70+
used by the SSH user:
71+
72+
```sh
73+
docker login ghcr.io
74+
sudo docker login ghcr.io
75+
```
76+
77+
## Required Variables
78+
79+
Set these as `Production` environment variables:
80+
81+
- `REND_API_BASE_URL`: defaults to `https://api.rend.so` when omitted.
82+
- `REND_READINESS_EDGES`: comma-separated
83+
`edge_id=region=public_base[=private_base]` entries, for example:
84+
85+
```text
86+
rend-edge-ash-1=us-east=https://ash-1.play.rend.so=https://ash-1-private.play.rend.so,rend-edge-ams-1=amsterdam=https://ams-1.play.rend.so=https://ams-1-private.play.rend.so
87+
```
88+
89+
The readiness gate needs `private_base` values that are reachable from the
90+
GitHub runner. If those private hosts are not publicly reachable, run this
91+
workflow on a self-hosted runner or provide VPN-accessible private bases.
92+
93+
## Rollback
94+
95+
Use the previous `rend-release-manifest` artifact from a successful workflow
96+
run, then run the same host deploy helper manually in this order:
97+
98+
```sh
99+
scripts/deploy-release-over-ssh.sh --role edge --host <edge-host> --user <user> --manifest <previous-manifest>
100+
scripts/deploy-release-over-ssh.sh --role control-plane --host <control-host> --user <user> --manifest <previous-manifest>
101+
```
102+
103+
Roll back edges first, then the media worker/API control plane. Treat database
104+
migrations as forward-only unless a tested rollback migration exists.

0 commit comments

Comments
 (0)