Skip to content

claude: Make pre-upgrade-check and post-upgrade-check tasks public #9

claude: Make pre-upgrade-check and post-upgrade-check tasks public

claude: Make pre-upgrade-check and post-upgrade-check tasks public #9

name: Build and Test PostgreSQL Upgrade Container
on:
push:
branches: [ main ]
tags: [ 'v*' ]
pull_request:
branches: [ main ]
workflow_dispatch:
env:
REGISTRY: ghcr.io
IMAGE_NAME: ${{ github.repository }}-upgrade
jobs:
build:
runs-on: ubuntu-latest
permissions:
contents: read
packages: write
outputs:
image: ${{ steps.image.outputs.image }}
steps:
- name: Checkout repository
uses: actions/checkout@v4
- name: Set up QEMU
uses: docker/setup-qemu-action@v3
- name: Set up Docker Buildx
uses: docker/setup-buildx-action@v3
- name: Log in to the Container registry
if: github.event_name != 'pull_request'
uses: docker/login-action@v3
with:
registry: ${{ env.REGISTRY }}
username: ${{ github.actor }}
password: ${{ secrets.GITHUB_TOKEN }}
- name: Extract metadata
id: meta
uses: docker/metadata-action@v5
with:
images: ${{ env.REGISTRY }}/${{ env.IMAGE_NAME }}
tags: |
type=ref,event=branch
type=ref,event=pr
type=semver,pattern={{version}}
type=semver,pattern={{major}}.{{minor}}
type=sha
- name: Build and push Docker image
uses: docker/build-push-action@v5
with:
context: .
platforms: linux/amd64,linux/arm64
push: ${{ github.event_name != 'pull_request' }}
tags: ${{ steps.meta.outputs.tags }}
labels: ${{ steps.meta.outputs.labels }}
cache-from: type=gha
cache-to: type=gha,mode=max
- name: Output image
id: image
run: echo "image=${{ env.REGISTRY }}/${{ env.IMAGE_NAME }}:${{ steps.meta.outputs.version }}" >> $GITHUB_OUTPUT
test:
needs: build
runs-on: ubuntu-latest
strategy:
matrix:
test:
# Direct upgrades
- { from: 14, to: 15, name: "14 to 15" }
- { from: 15, to: 16, name: "15 to 16" }
- { from: 16, to: 17, name: "16 to 17" }
# Multi-step upgrades
- { from: 14, to: 16, name: "14 to 16 (multi-step)" }
- { from: 15, to: 17, name: "15 to 17 (multi-step)" }
- { from: 14, to: 17, name: "14 to 17 (full upgrade)" }
name: Test upgrade ${{ matrix.test.name }}
steps:
- name: Checkout repository
uses: actions/checkout@v4
- name: Set image name
run: |
if [ "${{ github.event_name }}" == "pull_request" ]; then
echo "TEST_IMAGE=${{ env.REGISTRY }}/${{ env.IMAGE_NAME }}:pr-${{ github.event.pull_request.number }}" >> $GITHUB_ENV
else
echo "TEST_IMAGE=${{ needs.build.outputs.image }}" >> $GITHUB_ENV
fi
- name: Create test data directory
run: |
mkdir -p test-data/${{ matrix.test.from }}
chmod 777 test-data/${{ matrix.test.from }}
- name: Initialize PostgreSQL ${{ matrix.test.from }} with test data
run: |
docker run --rm \
-v $PWD/test-data/${{ matrix.test.from }}:/var/lib/postgresql/data \
-e POSTGRES_PASSWORD=testpass \
-e POSTGRES_USER=testuser \
-e POSTGRES_DB=testdb \
postgres:${{ matrix.test.from }}-bookworm \
bash -c "
docker-entrypoint.sh postgres &
PGPID=\$!
sleep 10
# Create test data
psql -U testuser -d testdb <<EOF
CREATE TABLE test_data (
id SERIAL PRIMARY KEY,
data TEXT,
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP
);
INSERT INTO test_data (data)
SELECT 'Test record ' || generate_series(1, 1000);
CREATE INDEX idx_test_data ON test_data(created_at);
SELECT COUNT(*) as record_count FROM test_data;
EOF
# Gracefully stop PostgreSQL
pg_ctl -D /var/lib/postgresql/data stop -m smart -w
sleep 5
"
- name: Run upgrade from ${{ matrix.test.from }} to ${{ matrix.test.to }}
run: |
# Create directories for the upgrade
mkdir -p test-data/${{ matrix.test.to }}
chmod 777 test-data/${{ matrix.test.to }}
docker run --rm \
-v $PWD/test-data/${{ matrix.test.from }}:/var/lib/postgresql/${{ matrix.test.from }}/data \
-v $PWD/test-data/${{ matrix.test.to }}:/var/lib/postgresql/${{ matrix.test.to }}/data \
-e POSTGRES_PASSWORD=testpass \
-e POSTGRES_USER=testuser \
-e POSTGRES_DB=testdb \
-e POSTGRES_INITDB_ARGS="--auth-local=trust --auth-host=md5" \
${{ env.TEST_IMAGE }} \
${{ matrix.test.from }} ${{ matrix.test.to }}
- name: Verify upgraded data
run: |
docker run --rm \
-v $PWD/test-data/${{ matrix.test.to }}:/var/lib/postgresql/data \
-e POSTGRES_PASSWORD=testpass \
postgres:${{ matrix.test.to }}-bookworm \
bash -c "
docker-entrypoint.sh postgres &
PGPID=\$!
sleep 10
# Verify data
psql -U testuser -d testdb <<EOF
-- Check table exists
SELECT COUNT(*) as record_count FROM test_data;
-- Check index exists
SELECT indexname FROM pg_indexes WHERE tablename = 'test_data';
-- Verify data integrity
SELECT
CASE
WHEN COUNT(*) = 1000 THEN 'PASS: All records present'
ELSE 'FAIL: Expected 1000 records, found ' || COUNT(*)
END as result
FROM test_data;
EOF
# Stop PostgreSQL
pg_ctl -D /var/lib/postgresql/data stop -m smart -w
"
- name: Upload test artifacts on failure
if: failure()
uses: actions/upload-artifact@v4
with:
name: test-logs-${{ matrix.test.from }}-to-${{ matrix.test.to }}
path: |
test-data/**/pg_upgrade_output.d/
test-data/**/*.log
test-arm64:
needs: build
runs-on: ubuntu-latest
if: github.event_name == 'push' || github.event_name == 'workflow_dispatch'
strategy:
matrix:
platform: [linux/arm64]
test:
- { from: 14, to: 17, name: "14 to 17 (full upgrade)" }
name: Test ${{ matrix.platform }} - ${{ matrix.test.name }}
steps:
- name: Checkout repository
uses: actions/checkout@v4
- name: Set up QEMU
uses: docker/setup-qemu-action@v3
- name: Set image name
run: |
echo "TEST_IMAGE=${{ needs.build.outputs.image }}" >> $GITHUB_ENV
- name: Test upgrade on ${{ matrix.platform }}
run: |
docker run --rm \
--platform ${{ matrix.platform }} \
-e POSTGRES_PASSWORD=testpass \
-e POSTGRES_USER=testuser \
-e POSTGRES_DB=testdb \
${{ env.TEST_IMAGE }} \
bash -c "
# Initialize test data in PostgreSQL ${{ matrix.test.from }}
export PGDATA=/var/lib/postgresql/${{ matrix.test.from }}/data
export PGBIN=/usr/lib/postgresql/${{ matrix.test.from }}/bin
\$PGBIN/initdb
echo \"host all all 0.0.0.0/0 md5\" >> \$PGDATA/pg_hba.conf
\$PGBIN/pg_ctl start -w
\$PGBIN/createuser -s testuser
\$PGBIN/createdb -O testuser testdb
\$PGBIN/psql -U testuser -d testdb -c \"CREATE TABLE test (id INT); INSERT INTO test VALUES (1), (2), (3);\"
\$PGBIN/psql -U testuser -d testdb -c \"SELECT COUNT(*) FROM test;\"
\$PGBIN/pg_ctl stop -w
# Run the upgrade
/usr/local/bin/docker-upgrade-multi ${{ matrix.test.from }} ${{ matrix.test.to }}
# Verify the upgrade
export PGDATA=/var/lib/postgresql/${{ matrix.test.to }}/data
export PGBIN=/usr/lib/postgresql/${{ matrix.test.to }}/bin
\$PGBIN/pg_ctl start -w
\$PGBIN/psql -U testuser -d testdb -c \"SELECT COUNT(*) FROM test;\" | grep -q \"3\" && echo \"SUCCESS: Data verified\" || exit 1
\$PGBIN/pg_ctl stop -w
"