Files
codex-proxy-rs/.github/workflows/_quality.yml
T
ZyyandCodex 817b0f2d6d chore(release): commit version and notes together
Allow staged or unstaged release notes and commit their final contents with the version update before tagging. Continue rejecting unrelated tracked changes and require notes to remain uncommitted.

Update the release skill, skip duplicate push CI for release metadata alone, and check the publish script syntax in CI. Validated publication behavior in temporary Git repositories, Bash syntax, and Actionlint.

Co-authored-by: Codex <noreply@openai.com>
2026-09-15 15:14:18 +08:00

211 lines
7.6 KiB
YAML

name: Reusable Quality
on:
workflow_call:
inputs:
ref:
description: Exact commit SHA to validate
required: true
type: string
upload_frontend:
description: Upload the built frontend for release jobs
required: false
default: false
type: boolean
run_backend:
description: Run backend quality checks
required: false
default: true
type: boolean
run_frontend:
description: Run frontend quality checks
required: false
default: true
type: boolean
permissions:
contents: read
jobs:
backend:
if: inputs.run_backend
runs-on: ubuntu-latest
timeout-minutes: 30
env:
CARGO_TERM_COLOR: always
# Rust 1.97 编译 AWS SDK 调试信息需要更大的 codegen 线程栈。
RUST_MIN_STACK: 16777216
CPR_TEST_DATABASE_URL: postgres://codex_proxy:codex_proxy@127.0.0.1:5432/codex_proxy
CPR_TEST_REDIS_URL: redis://127.0.0.1:6379
services:
postgres:
image: postgres:18-bookworm@sha256:d9c83446333daec3f0588cc709adb80c26090b7f9f0f7ec8d43c243385d79818
env:
POSTGRES_DB: codex_proxy
POSTGRES_USER: codex_proxy
POSTGRES_PASSWORD: codex_proxy
POSTGRES_INITDB_ARGS: --auth-local=scram-sha-256 --auth-host=scram-sha-256
ports:
- 5432:5432
options: >-
--health-cmd "pg_isready -U codex_proxy -d codex_proxy"
--health-interval 5s
--health-timeout 5s
--health-retries 10
redis:
image: redis:8-alpine@sha256:9d317178eceac8454a2284a9e6df2466b93c745529947f0cd42a0fa9609d7005
ports:
- 6379:6379
options: >-
--health-cmd "redis-cli ping"
--health-interval 5s
--health-timeout 5s
--health-retries 10
steps:
- name: Checkout
uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1
with:
ref: ${{ inputs.ref }}
# PR 场景需要 base 提交做冻结清单的 append-only 比对。
fetch-depth: ${{ github.event_name == 'pull_request' && 0 || 1 }}
# 已应用迁移的字节被 sqlx 启动校验钉死:改动已发布迁移会让所有
# 存量部署重启即失败。冻结清单保证旧文件不被改、新文件必须入册。
- name: Migration freeze check
working-directory: backend/migrations
shell: bash
env:
BASE_SHA: ${{ github.event.pull_request.base.sha }}
run: |
set -euo pipefail
sha256sum --check --strict .frozen-sha256
for file in *.sql; do
if ! awk '{print $2}' .frozen-sha256 | grep -Fxq "$file"; then
echo "::error file=backend/migrations/$file::migration $file is not frozen; append its sha256 to backend/migrations/.frozen-sha256"
exit 1
fi
done
# 清单自证不足以防「改迁移 + 同 PR 刷新清单行」:校验对新哈希通过。
# 对 PR,断言 .frozen-sha256 相对 base 只增不改——base 里的每一行
# 必须原样保留(改哈希=删行,删迁移=删行,都会被挡)。
if [ -n "${BASE_SHA:-}" ]; then
base_manifest="$(git show "${BASE_SHA}:backend/migrations/.frozen-sha256" 2>/dev/null || true)"
if [ -n "$base_manifest" ]; then
while IFS= read -r line; do
[ -z "$line" ] && continue
if ! grep -Fxq "$line" .frozen-sha256; then
file="$(printf '%s' "$line" | awk '{print $2}')"
echo "::error file=backend/migrations/.frozen-sha256::frozen migration $file was modified or removed; released migrations are append-only — add a new numbered migration instead"
exit 1
fi
done <<< "$base_manifest"
fi
fi
- name: Setup Rust
uses: dtolnay/rust-toolchain@1a3a6d54512beeaffd394f8d516ca16f2c506a20 # 1.97
with:
components: rustfmt,clippy
- name: Cache Rust
uses: Swatinem/rust-cache@6323deb102c322ba6fcbdcafc7e3dddab59af2b6 # v2.9.2
with:
workspaces: backend -> target
- name: Rust format
working-directory: backend
run: cargo fmt --check
- name: Rust clippy
working-directory: backend
run: cargo clippy --all-targets --all-features --locked -- -D warnings
- name: Configure PostgreSQL and Redis test authentication
shell: bash
run: |
set -euo pipefail
postgres_password="$(openssl rand -hex 24)"
redis_password="$(openssl rand -hex 24)"
echo "::add-mask::$postgres_password"
echo "::add-mask::$redis_password"
docker exec --env PGPASSWORD=codex_proxy "${{ job.services.postgres.id }}" psql \
--username=codex_proxy --dbname=codex_proxy \
--set=ON_ERROR_STOP=1 \
--command="ALTER USER codex_proxy WITH PASSWORD '${postgres_password}'" >/dev/null
docker exec --env PGPASSWORD="$postgres_password" "${{ job.services.postgres.id }}" psql \
--username=codex_proxy --dbname=codex_proxy \
--set=ON_ERROR_STOP=1 --command='SELECT 1' >/dev/null
docker exec "${{ job.services.redis.id }}" redis-cli CONFIG SET requirepass "$redis_password" >/dev/null
docker exec "${{ job.services.redis.id }}" redis-cli --no-auth-warning -a "$redis_password" ping >/dev/null
{
echo "CPR_TEST_DATABASE_URL=postgres://codex_proxy:${postgres_password}@127.0.0.1:5432/codex_proxy"
echo "CPR_TEST_REDIS_URL=redis://:${redis_password}@127.0.0.1:6379"
} >> "$GITHUB_ENV"
- name: Rust tests
working-directory: backend
run: cargo test --test main --locked
frontend:
if: inputs.run_frontend
runs-on: ubuntu-latest
timeout-minutes: 15
env:
CI: 'true'
steps:
- name: Checkout
uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1
with:
ref: ${{ inputs.ref }}
- name: Setup pnpm
uses: pnpm/action-setup@ea17c68df8912ef543352723c149a84f56e3d413 # v6.1.0
with:
version: 11.7.0
- name: Setup Node
uses: actions/setup-node@820762786026740c76f36085b0efc47a31fe5020 # v7.0.0
with:
node-version: 24
cache: pnpm
cache-dependency-path: frontend/pnpm-lock.yaml
- name: Install frontend dependencies
run: pnpm --dir frontend install --frozen-lockfile
- name: Frontend format
run: pnpm --dir frontend format:check
- name: Frontend build
run: pnpm --dir frontend build
- name: Upload frontend artifact
if: inputs.upload_frontend
uses: actions/upload-artifact@043fb46d1a93c77aae656e7c1c64a875d1fc6a0a # v7.0.1
with:
name: frontend-dist
path: frontend/dist
if-no-files-found: error
retention-days: 1
workflow-lint:
runs-on: ubuntu-latest
timeout-minutes: 5
steps:
- name: Checkout
uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1
with:
ref: ${{ inputs.ref }}
- name: Lint GitHub Actions workflows
run: >-
docker run --rm
--volume "$PWD:/repo"
--workdir /repo
rhysd/actionlint:1.7.7@sha256:887a259a5a534f3c4f36cb02dca341673c6089431057242cdc931e9f133147e9
-color
.github/workflows/*.yml
- name: Check release script syntax
run: bash -n release/publish