Garage serves all three buckets and both apps, and a last comparison found nothing in MinIO that Garage lacks. Drop the MinIO service, its bootstrap and its root credentials from the deploy, and let compose remove the leftover containers. The storage_minio_data volume is left on the host. All images can be pulled again, so the deploy goes back to failing on a pull error. Document Garage in the README and SECRETS, including the key format and how the existing secrets map to it, and swap the MinIO client in the flake for awscli and rclone. Assisted-by: Claude:fable-5-2
This commit is contained in:
parent
bdfc028ca1
commit
e9388c0b0d
6 changed files with 74 additions and 231 deletions
63
SECRETS.md
63
SECRETS.md
|
|
@ -8,20 +8,20 @@ domain-specific.
|
|||
|
||||
```sh
|
||||
openssl rand -hex 32 # 64-char hex, good for any password/key
|
||||
openssl rand -base64 24 # 32-char base64, fine for MinIO root password
|
||||
```
|
||||
|
||||
For MinIO **access keys** prefer alphanumeric, 20 chars:
|
||||
For a Garage **key pair** (an id of `GK` + 24 hex digits, a secret of 64):
|
||||
|
||||
```sh
|
||||
LC_ALL=C tr -dc 'A-Z0-9' </dev/urandom | head -c 20; echo
|
||||
printf 'GK%s\n' "$(openssl rand -hex 12)"
|
||||
openssl rand -hex 32
|
||||
```
|
||||
|
||||
For MinIO **secret keys**, 40+ chars:
|
||||
|
||||
```sh
|
||||
LC_ALL=C tr -dc 'A-Za-z0-9' </dev/urandom | head -c 40; echo
|
||||
```
|
||||
The pairs in use predate Garage and are not in that format. The bootstrap and
|
||||
the apps' deploys hash such a value into it (`garage_key_id`, `garage_secret`
|
||||
in `init/garage-bootstrap.sh`), so the key Garage knows differs from the
|
||||
secret's text. A value already in Garage's format is used as it is: use the
|
||||
snippet above whenever a pair is rotated.
|
||||
|
||||
## Required secrets
|
||||
|
||||
|
|
@ -41,13 +41,6 @@ Reuse the same key the asxpio repo uses.
|
|||
|---------------------|--------------------------------------------------------------------------------|
|
||||
| `POSTGRES_PASSWORD` | Postgres superuser password. `openssl rand -hex 32`. Used only by init/admin. |
|
||||
|
||||
### MinIO
|
||||
|
||||
| Secret | Value |
|
||||
|-------------------------|----------------------------------------------------------------------|
|
||||
| `MINIO_ROOT_USER` | Root username, e.g. `storage-admin`. Any string ≥ 3 chars. |
|
||||
| `MINIO_ROOT_PASSWORD` | Root password. ≥ 8 chars; use `openssl rand -base64 24`. |
|
||||
|
||||
### Per-app credentials provisioned for asxpio
|
||||
|
||||
These are also added (with the same values) on the **asxpio repo** so the app
|
||||
|
|
@ -56,37 +49,42 @@ can connect.
|
|||
| Secret | Value |
|
||||
|-------------------------|----------------------------------------------------------------|
|
||||
| `ASXPIO_DB_PASSWORD` | Postgres password for the `asxpio` role. `openssl rand -hex 32`.|
|
||||
| `ASXPIO_S3_ACCESS_KEY` | 20-char alphanumeric, see snippet above. |
|
||||
| `ASXPIO_S3_SECRET_KEY` | 40-char alphanumeric, see snippet above. |
|
||||
| `ASXPIO_S3_ACCESS_KEY` | S3 key id, see above. |
|
||||
| `ASXPIO_S3_SECRET_KEY` | S3 secret, see above. |
|
||||
|
||||
### Per-app credentials provisioned for datacenterbingo
|
||||
|
||||
These are read-only:
|
||||
- Role `bingo` gets SELECT on `bingo_datacenters` and `bingo_incidents` in
|
||||
the `asxpio` DB, and `default_transaction_read_only`.
|
||||
- The MinIO user may only `GetObject` in the `datacenterbingo-photos` bucket.
|
||||
asxpio's user has read-write on that bucket for the admin's uploads.
|
||||
- The S3 key may only read the `datacenterbingo-photos` bucket.
|
||||
asxpio's key has read-write on that bucket for the admin's uploads.
|
||||
|
||||
The same values go on the **datacenterbingo repo**.
|
||||
|
||||
| Secret | Value |
|
||||
|------------------------|--------------------------------------------------------|
|
||||
| `BINGO_DB_PASSWORD` | Postgres password for the `bingo` role. `openssl rand -hex 32`. |
|
||||
| `BINGO_S3_ACCESS_KEY` | 20-char alphanumeric. |
|
||||
| `BINGO_S3_SECRET_KEY` | 40-char alphanumeric. |
|
||||
| `BINGO_S3_ACCESS_KEY` | S3 key id. |
|
||||
| `BINGO_S3_SECRET_KEY` | S3 secret. |
|
||||
|
||||
### Uploader for the `public` bucket
|
||||
|
||||
Objects in `public` are readable by anyone at `https://s3.asxp.io/public/<key>`
|
||||
(no anonymous listing). This user may only put and delete there. Optional:
|
||||
without the secrets the bucket exists and only root can upload.
|
||||
(no anonymous listing). This key may only put and delete there. Optional:
|
||||
without the secrets the bucket exists and nothing can upload.
|
||||
|
||||
| Secret | Value |
|
||||
|-------------------------|-----------------------|
|
||||
| `PUBLIC_S3_ACCESS_KEY` | 20-char alphanumeric. |
|
||||
| `PUBLIC_S3_SECRET_KEY` | 40-char alphanumeric. |
|
||||
| `PUBLIC_S3_ACCESS_KEY` | S3 key id. |
|
||||
| `PUBLIC_S3_SECRET_KEY` | S3 secret. |
|
||||
|
||||
The local AWS profile needs the pair as Garage knows it. For a pair not in
|
||||
Garage's format, that is the hashed form:
|
||||
|
||||
```sh
|
||||
printf 'GK%s\n' "$(printf '%s' "$PUBLIC_S3_ACCESS_KEY" | sha256sum | cut -c1-24)"
|
||||
printf '%s' "$PUBLIC_S3_SECRET_KEY" | sha256sum | cut -c1-64
|
||||
aws --endpoint-url https://s3.asxp.io --profile asxp-public \
|
||||
s3 cp shot.png s3://public/shot.png
|
||||
```
|
||||
|
|
@ -96,13 +94,14 @@ deploy storage again after asxpio's first boot.
|
|||
|
||||
## After adding secrets
|
||||
|
||||
1. Push to `main`. The Forgejo workflow brings Postgres and MinIO up, then runs
|
||||
`postgres-init` (creates `asxpio` role + DB) and `minio-init` (creates
|
||||
`asxpio-invoices` bucket and an `asxpio`-scoped user).
|
||||
1. Push to `main`. The Forgejo workflow brings Postgres and Garage up, then runs
|
||||
`postgres-init` (creates `asxpio` role + DB) and `init/garage-bootstrap.sh`
|
||||
(creates the buckets and the per-app keys).
|
||||
2. Confirm both init containers exited 0:
|
||||
```sh
|
||||
ssh deploy@prod 'docker compose -f /opt/storage/docker-compose.yml ps'
|
||||
ssh deploy@prod 'docker logs storage-postgres-init storage-minio-init'
|
||||
ssh deploy@prod 'docker logs storage-postgres-init'
|
||||
ssh deploy@prod 'docker exec storage-garage /garage key list'
|
||||
```
|
||||
3. Add the matching `ASXPIO_DB_PASSWORD`, `ASXPIO_S3_ACCESS_KEY`,
|
||||
`ASXPIO_S3_SECRET_KEY` (plus `ADMIN_USER`, `ADMIN_PASSWORD`) on the asxpio
|
||||
|
|
@ -111,9 +110,7 @@ deploy storage again after asxpio's first boot.
|
|||
|
||||
## Rotation
|
||||
|
||||
- **`POSTGRES_PASSWORD` / `MINIO_ROOT_PASSWORD`**: update secret, push. Init
|
||||
scripts only touch *per-app* roles, so the root passwords are applied on
|
||||
container restart (Postgres) or via the env on next boot (MinIO). For MinIO
|
||||
root rotation, recreating the container is enough.
|
||||
- **`POSTGRES_PASSWORD`**: update secret, push. Init scripts only touch
|
||||
*per-app* roles, so the superuser password is applied on container restart.
|
||||
- **Per-app password / keys**: update both repos' secrets, push storage first
|
||||
(re-provisions the role/user with the new password), then push the consumer.
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue