Skip to content

Commit 7e0ae93

Browse files
Merge pull request #110 from BehindTheMusicTree/feature/upgrade-github-workflows
ci: upgrade to github-workflows v2.0.0 (set-image-tags, sync-env pin)
2 parents a264a89 + 84b9035 commit 7e0ae93

6 files changed

Lines changed: 43 additions & 53 deletions

File tree

.github/actionlint.yaml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -10,12 +10,12 @@ config-variables:
1010
- STATIC_FILES
1111
- STATIC_FILES_URL
1212
- SERVER_HOST
13-
- REDEPLOYMENT_ROOT
1413
- BTMT_REDEPLOYMENT_HOOK_ID_BASE
1514
- DEMO_EMAIL
1615
- SUPERADMIN_EMAIL
1716
- AFP_APP_NAME
1817
- AFP_IMAGE_REPO
18+
- IMAGE_TAGS_POOL_DIR
1919
- SPOTIFY_CLIENT_ID_STAGING
2020
- SPOTIFY_CLIENT_ID_PROD
2121
- SPOTIFY_SCOPES

.github/workflows/publish.yml

Lines changed: 16 additions & 37 deletions
Original file line numberDiff line numberDiff line change
@@ -93,26 +93,20 @@ jobs:
9393
environment: ${{ needs.determine-version.outputs.deployment_environment }}
9494
env:
9595
AFP_VERSION: ${{ vars.AFP_VERSION }}
96-
REDEPLOYMENT_ROOT: ${{ vars.REDEPLOYMENT_ROOT }}
96+
IMAGE_TAGS_POOL_DIR: ${{ vars.IMAGE_TAGS_POOL_DIR }}
9797
BTMT_REDEPLOYMENT_HOOK_ID_BASE: ${{ vars.BTMT_REDEPLOYMENT_HOOK_ID_BASE }}
98-
HTMT_API_APP_NAME: ${{ vars.HTMT_API_APP_NAME }}
99-
DB_APP_NAME_SUFFIX: ${{ vars.DB_APP_NAME_SUFFIX }}
100-
AFP_APP_NAME: ${{ vars.AFP_APP_NAME }}
10198
outputs:
10299
afp_version: ${{ steps.pinned.outputs.afp_version }}
103100
redeployment_hook_id_base: ${{ steps.pinned.outputs.redeployment_hook_id_base }}
104101
steps:
105-
- name: Require deploy and app-name vars (set-image-tag-on-server)
102+
- name: Require deploy vars (set-image-tags-on-server)
106103
run: |
107104
missing=""
108-
[ -z "${REDEPLOYMENT_ROOT}" ] && missing="${missing} REDEPLOYMENT_ROOT"
105+
[ -z "${IMAGE_TAGS_POOL_DIR}" ] && missing="${missing} IMAGE_TAGS_POOL_DIR"
109106
[ -z "${BTMT_REDEPLOYMENT_HOOK_ID_BASE}" ] && missing="${missing} BTMT_REDEPLOYMENT_HOOK_ID_BASE"
110-
[ -z "${HTMT_API_APP_NAME}" ] && missing="${missing} HTMT_API_APP_NAME"
111-
[ -z "${DB_APP_NAME_SUFFIX}" ] && missing="${missing} DB_APP_NAME_SUFFIX"
112-
[ -z "${AFP_APP_NAME}" ] && missing="${missing} AFP_APP_NAME"
113107
if [ -n "$missing" ]; then
114108
echo "ERROR: Set Variables on this job's GitHub Environment (STAGING or PROD) or at repository/org level:$missing"
115-
echo "Example: REDEPLOYMENT_ROOT=/var/webhook/redeployment, BTMT_REDEPLOYMENT_HOOK_ID_BASE=..., HTMT_API_APP_NAME=htmt-api, DB_APP_NAME_SUFFIX=-db, AFP_APP_NAME=afp (must match infrastructure)"
109+
echo "Example: IMAGE_TAGS_POOL_DIR=/srv/btmt/image-tags, BTMT_REDEPLOYMENT_HOOK_ID_BASE=... (must match infrastructure)"
116110
exit 1
117111
fi
118112
- name: Require pinned AFP image tag
@@ -129,40 +123,25 @@ jobs:
129123
echo "afp_version=$AFP_VERSION" >> "$GITHUB_OUTPUT"
130124
echo "redeployment_hook_id_base=${BTMT_REDEPLOYMENT_HOOK_ID_BASE}" >> "$GITHUB_OUTPUT"
131125
132-
set-version-api:
133-
name: Set API version on server
126+
set-image-tags:
127+
name: Set image tags on server
134128
needs: [build-and-push, determine-version, check-pinned-tags]
135-
uses: BehindTheMusicTree/github-workflows/.github/workflows/set-image-tag-on-server.yml@main
129+
uses: BehindTheMusicTree/github-workflows/.github/workflows/set-image-tags-on-server.yml@v2.0.0
136130
with:
137131
env: ${{ needs.determine-version.outputs.env }}
138-
tag: ${{ needs.determine-version.outputs.image_tag }}
139-
app_name: ${{ vars.HTMT_API_APP_NAME }}
140-
secrets: inherit
141-
142-
set-version-db:
143-
name: Set DB version on server
144-
needs: [determine-version, check-pinned-tags]
145-
uses: BehindTheMusicTree/github-workflows/.github/workflows/set-image-tag-on-server.yml@main
146-
with:
147-
env: ${{ needs.determine-version.outputs.env }}
148-
tag: '16.4'
149-
app_name: ${{ format('{0}{1}', vars.HTMT_API_APP_NAME, vars.DB_APP_NAME_SUFFIX) }}
150-
secrets: inherit
151-
152-
set-version-afp:
153-
name: Set AFP version on server
154-
needs: [determine-version, check-pinned-tags]
155-
uses: BehindTheMusicTree/github-workflows/.github/workflows/set-image-tag-on-server.yml@main
156-
with:
157-
env: ${{ needs.determine-version.outputs.env }}
158-
tag: ${{ needs.check-pinned-tags.outputs.afp_version }}
159-
app_name: ${{ vars.AFP_APP_NAME }}
132+
stack: btmt
133+
tags: |
134+
HTMT_API_TAG=${{ needs.determine-version.outputs.image_tag }}
135+
DB_TAG=16.4
136+
AFP_TAG=${{ needs.check-pinned-tags.outputs.afp_version }}
137+
release_id: ${{ needs.determine-version.outputs.image_tag }}
138+
release_sha: ${{ github.sha }}
160139
secrets: inherit
161140

162141
redeploy-webhook-call:
163142
name: Redeploy webhook
164-
needs: [build-and-push, set-version-api, set-version-db, set-version-afp, check-pinned-tags, determine-version]
165-
uses: BehindTheMusicTree/github-workflows/.github/workflows/call-redeployment-webhook.yml@v1.0.4
143+
needs: [build-and-push, set-image-tags, check-pinned-tags, determine-version]
144+
uses: BehindTheMusicTree/github-workflows/.github/workflows/call-redeployment-webhook.yml@v2.0.0
166145
with:
167146
env: ${{ needs.determine-version.outputs.env }}
168147
hook_id_base: ${{ needs.check-pinned-tags.outputs.redeployment_hook_id_base }}

.github/workflows/sync-env-to-server.yml

Lines changed: 6 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -25,7 +25,6 @@ jobs:
2525
- name: Validate vars and build API env fragment
2626
env:
2727
SERVER_HOST: ${{ vars.SERVER_HOST }}
28-
REDEPLOYMENT_ROOT: ${{ vars.REDEPLOYMENT_ROOT }}
2928
HTMT_API_APP_NAME: ${{ vars.HTMT_API_APP_NAME }}
3029
DB_APP_NAME_SUFFIX: ${{ vars.DB_APP_NAME_SUFFIX }}
3130
DEMO_EMAIL: ${{ vars.DEMO_EMAIL }}
@@ -70,7 +69,7 @@ jobs:
7069
'LIBRARIES_DIR=/app/media/libraries/' \
7170
'TMP_UPLOADED_FILES=/tmp/uploads' >> fragment.env
7271
required=(
73-
SERVER_HOST REDEPLOYMENT_ROOT HTMT_API_APP_NAME DB_APP_NAME_SUFFIX
72+
SERVER_HOST HTMT_API_APP_NAME DB_APP_NAME_SUFFIX
7473
DEMO_EMAIL SUPERADMIN_EMAIL SPOTIFY_CLIENT_ID SPOTIFY_SCOPES GOOGLE_CLIENT_ID
7574
SERVER_DEPLOY_USERNAME SERVER_DEPLOY_SSH_PRIVATE_KEY
7675
DB_APP_DB_NAME DB_APP_USERNAME DB_APP_USER_PASSWORD DB_SUPERUSER_PASSWORD
@@ -117,7 +116,6 @@ jobs:
117116
- name: Validate vars and build DB env fragment
118117
env:
119118
SERVER_HOST: ${{ vars.SERVER_HOST }}
120-
REDEPLOYMENT_ROOT: ${{ vars.REDEPLOYMENT_ROOT }}
121119
HTMT_API_APP_NAME: ${{ vars.HTMT_API_APP_NAME }}
122120
DB_APP_NAME_SUFFIX: ${{ vars.DB_APP_NAME_SUFFIX }}
123121
DB_APP_DB_NAME: ${{ secrets.DB_APP_DB_NAME }}
@@ -139,7 +137,7 @@ jobs:
139137
printf 'POSTGRES_PASSWORD=%s\n' "${val}" >> fragment.env
140138
printf '%s\n' "POSTGRES_PORT=5432" >> fragment.env
141139
required=(
142-
SERVER_HOST REDEPLOYMENT_ROOT HTMT_API_APP_NAME DB_APP_NAME_SUFFIX
140+
SERVER_HOST HTMT_API_APP_NAME DB_APP_NAME_SUFFIX
143141
SERVER_DEPLOY_USERNAME SERVER_DEPLOY_SSH_PRIVATE_KEY
144142
DB_APP_DB_NAME DB_SUPERUSER_PASSWORD
145143
)
@@ -162,7 +160,7 @@ jobs:
162160
sync-api-staging:
163161
name: Sync API env (staging)
164162
needs: [build-api-fragment]
165-
uses: BehindTheMusicTree/github-workflows/.github/workflows/sync-env-to-server.yml@main
163+
uses: BehindTheMusicTree/github-workflows/.github/workflows/sync-env-to-server.yml@v2.0.0
166164
with:
167165
sync_env: staging
168166
fragment_artifact: sync-env-fragment-api-staging/fragment.env
@@ -172,7 +170,7 @@ jobs:
172170
sync-api-prod:
173171
name: Sync API env (prod)
174172
needs: [build-api-fragment]
175-
uses: BehindTheMusicTree/github-workflows/.github/workflows/sync-env-to-server.yml@main
173+
uses: BehindTheMusicTree/github-workflows/.github/workflows/sync-env-to-server.yml@v2.0.0
176174
with:
177175
sync_env: prod
178176
fragment_artifact: sync-env-fragment-api-prod/fragment.env
@@ -182,7 +180,7 @@ jobs:
182180
sync-db-staging:
183181
name: Sync Postgres env (staging)
184182
needs: [build-db-fragment]
185-
uses: BehindTheMusicTree/github-workflows/.github/workflows/sync-env-to-server.yml@main
183+
uses: BehindTheMusicTree/github-workflows/.github/workflows/sync-env-to-server.yml@v2.0.0
186184
with:
187185
sync_env: staging
188186
fragment_artifact: sync-env-fragment-db-staging/fragment.env
@@ -192,7 +190,7 @@ jobs:
192190
sync-db-prod:
193191
name: Sync Postgres env (prod)
194192
needs: [build-db-fragment]
195-
uses: BehindTheMusicTree/github-workflows/.github/workflows/sync-env-to-server.yml@main
193+
uses: BehindTheMusicTree/github-workflows/.github/workflows/sync-env-to-server.yml@v2.0.0
196194
with:
197195
sync_env: prod
198196
fragment_artifact: sync-env-fragment-db-prod/fragment.env

CHANGELOG.md

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -64,6 +64,12 @@ All contributors (including maintainers) should update `CHANGELOG.md` when creat
6464

6565
## [Unreleased]
6666

67+
### CI
68+
69+
- **github-workflows v2.0.0** ([`.github/workflows/publish.yml`](.github/workflows/publish.yml), [`.github/workflows/sync-env-to-server.yml`](.github/workflows/sync-env-to-server.yml)): Upgraded to **`BehindTheMusicTree/github-workflows@v2.0.0`**. **`publish.yml`**: replaced three separate **`set-image-tag-on-server`** calls (API, DB, AFP) with a single **`set-image-tags-on-server.yml@v2.0.0`** call using **`stack: btmt`** and a multiline **`tags`** block (**`HTMT_API_TAG`**, **`DB_TAG=16.4`**, **`AFP_TAG`**); **`check-pinned-tags`** now requires **`IMAGE_TAGS_POOL_DIR`** instead of **`REDEPLOYMENT_ROOT`**; **`redeploy-webhook-call`** pinned to **`@v2.0.0`**. **`sync-env-to-server.yml`**: removed **`REDEPLOYMENT_ROOT`** from fragment-building env and required-vars checks (no longer a workflow input); all four shared workflow calls pinned to **`@v2.0.0`**.
70+
71+
- **Release script** ([`scripts/prepare_release_bump.py`](scripts/prepare_release_bump.py)): Now calls [`scripts/remove_prerelease_tags.sh`](scripts/remove_prerelease_tags.sh) after the version bump to automatically delete all local and remote dev/prerelease tags for the released version.
72+
6773
## [v2.2.6] - 2026-05-04
6874

6975
### CI

docs/workflows.md

Lines changed: 5 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -72,13 +72,11 @@ Single publish workflow: collect static files, build Docker image, set image tag
7272
1. **determine-version** – from ref: tag with `-` → TEST; tag without `-` → PROD; `main` (e.g. manual dispatch) → staging + TEST
7373
2. **static** – calls `static-files.yml`, commits and pushes collected static files
7474
3. **build-and-push** – calls `build-and-push.yml` with commit hash and **environment** (TEST or PROD)
75-
4. **check-pinned-tags** – requires **`AFP_VERSION`** in Settings → Variables (no `latest`); DB image is **`postgres:16.4`** (fixed in [`docker-compose.yml`](../docker-compose.yml); publish sets server DB tag **`16.4`**)
76-
5. **set-version-api** / **set-version-db** / **set-version-afp** – shared workflows from `BehindTheMusicTree/github-workflows`
77-
6. **redeploy-webhook-call****`hook_id_base`** from **`check-pinned-tags`** (**`BTMT_REDEPLOYMENT_HOOK_ID_BASE`** validated under **Environment** **`STAGING`** / **`PROD`** there). Caller job is **`uses:`** only—**`environment`** is not allowed on that job shape in the Actions schema, so **`secrets: inherit`** supplies **repo/org** secrets (e.g. **`BTMT_REDEPLOYMENT_WEBHOOK_SECRET_*`**). Environment-only webhook secrets need a repo/org copy or support inside **`call-redeployment-webhook`**. Pinned **`@v1.0.4`**.
75+
4. **check-pinned-tags** – requires **`AFP_VERSION`** in Settings → Variables (no `latest`) and **`IMAGE_TAGS_POOL_DIR`** / **`BTMT_REDEPLOYMENT_HOOK_ID_BASE`** in the selected GitHub Environment (**STAGING**/**PROD**) or repo/org Variables; DB image is **`postgres:16.4`** (fixed in [`docker-compose.yml`](../docker-compose.yml); publish sets server DB tag **`16.4`**)
76+
5. **set-image-tags** – calls `BehindTheMusicTree/github-workflows/.github/workflows/set-image-tags-on-server.yml@v2.0.0` once with `stack: btmt` and tags for API, DB, and AFP (`HTMT_API_TAG`, `DB_TAG=16.4`, `AFP_TAG`)
77+
6. **redeploy-webhook-call**calls `BehindTheMusicTree/github-workflows/.github/workflows/call-redeployment-webhook.yml@v2.0.0` with **`hook_id_base`** from **`check-pinned-tags`** (**`BTMT_REDEPLOYMENT_HOOK_ID_BASE`**). Caller job is **`uses:`** only—**`environment`** is not allowed on that job shape in the Actions schema, so **`secrets: inherit`** supplies **repo/org** secrets (e.g. **`BTMT_REDEPLOYMENT_WEBHOOK_SECRET_*`**). Environment-only webhook secrets need a repo/org copy or support inside **`call-redeployment-webhook`**.
7878

79-
**Environment:** **TEST** for prerelease/dev tags and for manual runs from `main` (staging). **PROD** for release tags (production). DB and AFP image tags must be pinned in repo variables.
80-
81-
**Variables (org-level pool, same as Sync env):** `REDEPLOYMENT_ROOT` (e.g. `/var/webhook/redeployment`). Set once at the **organization** (Settings → Variables) so the infrastructure repo and all app repos that call set-image-tag-on-server use the same path. If unset, the tag file path is wrong and the step fails.
79+
**Environment:** **TEST** for prerelease/dev tags and for manual runs from `main` (staging). **PROD** for release tags (production). DB and AFP image tags must be pinned in repo variables, and **`IMAGE_TAGS_POOL_DIR`** must be set for **STAGING** and **PROD** (for `set-image-tags-on-server`).
8280

8381
**Versioning:** Manual dispatch from `main` uses `VERSION` file and image tag `staging`. Tag push uses tag version; `workflow_call` without a tag uses latest git tag.
8482

@@ -108,7 +106,7 @@ Manually sync app env vars and secrets for **both STAGING and PROD** in one run.
108106

109107
**Secrets (this repo, per environment):** `DB_APP_DB_NAME`, `DB_APP_USERNAME`, `DB_APP_USER_PASSWORD`, `DB_SUPERUSER_PASSWORD`, `DEMO_PASSWORD`, `DEMO_USERNAME`, `DJANGO_SECRET_KEY`, `GOOGLE_CLIENT_SECRET`, `SPOTIFY_CLIENT_SECRET`, `SUPERADMIN_PASSWORD`, `SUPERADMIN_USERNAME`, `TMTA_USERNAME`, plus deploy secrets `SERVER_DEPLOY_USERNAME`, `SERVER_DEPLOY_SSH_PRIVATE_KEY`.
110108

111-
**Variables (this repo or org, per GitHub Environment):** `SERVER_HOST`, `REDEPLOYMENT_ROOT`, `SYNC_ENV_REMOTE_FILENAME_PREFIX_BASE`, `HTMT_API_APP_NAME`, **`DB_APP_NAME_SUFFIX`** (required, non-empty; must match **BehindTheMusicTree/infrastructure**, e.g. `_db`), `DEMO_EMAIL`, `SUPERADMIN_EMAIL`, `SPOTIFY_CLIENT_ID_STAGING`, `SPOTIFY_CLIENT_ID_PROD`, `GOOGLE_CLIENT_ID_STAGING`, `GOOGLE_CLIENT_ID_PROD`, **`SPOTIFY_SCOPES`** (see `env/dev/.env.dev.example`). The compose-required API booleans above are **not** Variables—they are written as **`true`** in the workflow. Locally and in CI you still set **`FILE_UPLOAD_ENABLED`** in `.env` as needed (see `api/settings.py` / `TMP_UPLOADED_FILES`).
109+
**Variables (this repo or org, per GitHub Environment):** `SERVER_HOST`, `SYNC_ENV_REMOTE_FILENAME_PREFIX_BASE`, `HTMT_API_APP_NAME`, **`DB_APP_NAME_SUFFIX`** (required, non-empty; must match **BehindTheMusicTree/infrastructure**, e.g. `_db`), `DEMO_EMAIL`, `SUPERADMIN_EMAIL`, `SPOTIFY_CLIENT_ID_STAGING`, `SPOTIFY_CLIENT_ID_PROD`, `GOOGLE_CLIENT_ID_STAGING`, `GOOGLE_CLIENT_ID_PROD`, **`SPOTIFY_SCOPES`** (see `env/dev/.env.dev.example`). The compose-required API booleans above are **not** Variables—they are written as **`true`** in the workflow. Locally and in CI you still set **`FILE_UPLOAD_ENABLED`** in `.env` as needed (see `api/settings.py` / `TMP_UPLOADED_FILES`).
112110

113111
## Static Files
114112

scripts/prepare_release_bump.py

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -136,6 +136,13 @@ def _run_fix_changelog() -> None:
136136
sys.exit(proc.returncode)
137137

138138

139+
def _run_remove_prerelease_tags() -> None:
140+
script = REPO_ROOT / "scripts" / "remove_prerelease_tags.sh"
141+
proc = subprocess.run(["bash", str(script)], cwd=REPO_ROOT, check=False)
142+
if proc.returncode != 0:
143+
sys.exit(proc.returncode)
144+
145+
139146
def _warn_branch() -> None:
140147
proc = subprocess.run(
141148
["git", "branch", "--show-current"],
@@ -183,6 +190,8 @@ def main() -> None:
183190
if changed:
184191
CHANGELOG_PATH.write_text(updated)
185192

193+
_run_remove_prerelease_tags()
194+
186195
print(
187196
"prepare_release_bump: done. Review git diff and CHANGELOG.md, then commit "
188197
"(e.g. chore: prepare release vX.Y.Z)."

0 commit comments

Comments
 (0)