Skip to content

feat: PGQ enhancement - fulltext search, cursor pollution fix, and PG 19 compatibility #345

feat: PGQ enhancement - fulltext search, cursor pollution fix, and PG 19 compatibility

feat: PGQ enhancement - fulltext search, cursor pollution fix, and PG 19 compatibility #345

Workflow file for this run

# .github/workflows/test.yml
name: Python Test and Coverage with postgres
on:
push:
branches:
- main
- 'release/v**'
- 'maint/**'
pull_request:
branches:
- main
- 'release/v**'
- 'maint/**'
workflow_dispatch:
permissions:
contents: read
jobs:
benchmark-python-314-postgres-18:
name: Run benchmarks with Python 3.14 / postgres 18
runs-on: ubuntu-latest
permissions:
contents: read
services:
postgres:
image: postgres:18
env:
POSTGRES_DB: test_db
POSTGRES_USER: root
POSTGRES_PASSWORD: password
ports:
- 5432:5432
options: >-
--health-cmd pg_isready
--health-interval 10s
--health-timeout 5s
--health-retries 5
postgres-exts:
image: vistart/postgres-exts:18
env:
POSTGRES_DB: test_db
POSTGRES_USER: root
POSTGRES_PASSWORD: password
ports:
- 5433:5432
options: >-
--health-cmd pg_isready
--health-interval 10s
--health-timeout 5s
--health-retries 5
steps:
- name: Check out the repository
uses: actions/checkout@v6
- name: Set up Python 3.14
uses: actions/setup-python@v6
with:
python-version: "3.14"
- name: Install dependencies
run: |
pip install -r requirements.txt
pip install -r requirements-dev.txt
- name: Install activerecord and testsuite
run: |
pip install git+https://github.com/rhosocial/python-activerecord.git@release/v1.0.0.dev29#egg=rhosocial-activerecord
pip install git+https://github.com/rhosocial/python-activerecord-testsuite.git@release/v1.0.0.dev16#egg=rhosocial-activerecord-testsuite
- name: Create postgres scenario config
run: |
cat > postgres_scenarios.yaml << EOF
scenarios:
postgres_default:
host: 127.0.0.1
port: 5432
database: test_db
username: root
password: password
postgres_exts:
host: 127.0.0.1
port: 5433
database: test_db
username: root
password: password
EOF
echo "POSTGRES_SCENARIOS_CONFIG_PATH=$(pwd)/postgres_scenarios.yaml" >> $GITHUB_ENV
- name: Install postgres client for health check
run: |
sudo apt-get update
sudo apt-get install --yes postgresql-client
- name: Wait for postgres service
run: |
until pg_isready -h 127.0.0.1 -p 5432 -U root; do
echo "Waiting for postgres..."
sleep 2
done
echo "postgres is ready!"
until pg_isready -h 127.0.0.1 -p 5433 -U root; do
echo "Waiting for postgres-exts..."
sleep 2
done
echo "postgres-exts is ready!"
- name: Run benchmark suite
run: |
set -o pipefail
export PYTHONPATH=src:tests
TESTSUITE_DIR=$(python - <<'PY'
import pathlib
import rhosocial.activerecord.testsuite as testsuite
print(pathlib.Path(testsuite.__file__).parent)
PY
)
python -m pytest \
--rootdir=. \
--confcutdir=. \
"$TESTSUITE_DIR/benchmark/crud/test_delete_async.py" \
"$TESTSUITE_DIR/benchmark/crud/test_delete.py" \
"$TESTSUITE_DIR/benchmark/crud/test_insert_async.py" \
"$TESTSUITE_DIR/benchmark/crud/test_insert.py" \
"$TESTSUITE_DIR/benchmark/crud/test_query_async.py" \
"$TESTSUITE_DIR/benchmark/crud/test_query.py" \
"$TESTSUITE_DIR/benchmark/crud/test_update_async.py" \
"$TESTSUITE_DIR/benchmark/crud/test_update.py" \
"$TESTSUITE_DIR/benchmark/query" \
"$TESTSUITE_DIR/benchmark/transaction" \
"$TESTSUITE_DIR/benchmark/mixin" \
-m benchmark \
--benchmark-size=small \
--benchmark-sort=mean \
--strict-markers \
--tb=short | tee benchmark-output.txt
python -m pytest \
--rootdir=. \
--confcutdir=. \
tests/benchmark/activerecord_bulk \
-m benchmark \
--benchmark-size=small \
--benchmark-sort=mean \
--strict-markers \
--tb=short | tee -a benchmark-output.txt
python -m pytest \
--rootdir=. \
--confcutdir=. \
tests/benchmark/backend \
-m benchmark \
--benchmark-size=small \
--benchmark-sort=mean \
--strict-markers \
--tb=short | tee -a benchmark-output.txt
- name: Run FastAPI benchmark suite
run: |
set -o pipefail
export PYTHONPATH=src:tests
TESTSUITE_DIR=$(python - <<'PY'
import pathlib
import rhosocial.activerecord.testsuite as testsuite
print(pathlib.Path(testsuite.__file__).parent)
PY
)
python -m pytest \
--rootdir=. \
--confcutdir=. \
"$TESTSUITE_DIR/benchmark/fastapi" \
-m benchmark_fastapi \
--benchmark-size=small \
--benchmark-sort=mean \
--tb=short | tee fastapi-benchmark-output.txt
- name: Write benchmark conclusion
if: always()
run: |
{
echo "## Python 3.14 / postgres 18 Benchmark Conclusion"
echo
echo "- Python: 3.14"
echo "- postgres: 18"
echo "- Scope: testsuite generic benchmarks + ActiveRecord bulk benchmarks + PostgreSQL backend direct benchmarks"
echo "- Size: small"
echo "- Result: benchmark job fails only when benchmark execution or correctness checks fail."
echo
echo '```text'
if [ -f benchmark-output.txt ]; then
grep -A 120 "benchmark:" benchmark-output.txt || tail -n 200 benchmark-output.txt
else
echo "benchmark-output.txt was not generated."
fi
echo '```'
} >> "$GITHUB_STEP_SUMMARY"
- name: Write FastAPI benchmark conclusion
if: always()
run: |
{
echo "## Python 3.14 / postgres 18 FastAPI Benchmark Conclusion"
echo
echo "- Python: 3.14"
echo "- postgres: 18"
echo "- Scope: testsuite FastAPI database benchmarks"
echo "- Size: small"
echo "- Result: benchmark job fails only when FastAPI benchmark execution or correctness checks fail."
echo
echo '```text'
if [ -f fastapi-benchmark-output.txt ]; then
grep -A 120 "benchmark:" fastapi-benchmark-output.txt || tail -n 200 fastapi-benchmark-output.txt
else
echo "fastapi-benchmark-output.txt was not generated."
fi
echo '```'
} >> "$GITHUB_STEP_SUMMARY"
test-experimental-python-315:
# Temporarily disabled until Python 3.15 beta/toolchain compatibility stabilizes.
if: ${{ false }}
name: Python ${{ matrix.python-version }} / postgres ${{ matrix.postgres-version }} (experimental)
runs-on: ubuntu-latest
permissions:
contents: read
continue-on-error: true
strategy:
fail-fast: false
matrix:
include:
- { python-version: '3.15.0-beta.2', postgres-version: '18', freethreaded: false }
- { python-version: '3.15.0-beta.2', postgres-version: '18', freethreaded: true }
services:
postgres:
image: postgres:${{ matrix.postgres-version }}
env:
POSTGRES_DB: test_db
POSTGRES_USER: root
POSTGRES_PASSWORD: password
ports:
- 5432:5432
options: >-
--health-cmd pg_isready
--health-interval 10s
--health-timeout 5s
--health-retries 5
postgres-exts:
image: vistart/postgres-exts:${{ matrix.postgres-version }}
env:
POSTGRES_DB: test_db
POSTGRES_USER: root
POSTGRES_PASSWORD: password
ports:
- 5433:5432
options: >-
--health-cmd pg_isready
--health-interval 10s
--health-timeout 5s
--health-retries 5
steps:
- name: Check out the repository
uses: actions/checkout@v6
- name: Set up Python ${{ matrix.python-version }}${{ matrix.freethreaded && ' free-threaded' || '' }}
uses: actions/setup-python@v6
with:
python-version: ${{ matrix.python-version }}
freethreaded: ${{ matrix.freethreaded }}
- name: Install dependencies
run: |
pip install -r requirements.txt
pip install -r requirements-dev.txt
- name: Install activerecord and testsuite
run: |
pip install git+https://github.com/rhosocial/python-activerecord.git@release/v1.0.0.dev29#egg=rhosocial-activerecord
pip install git+https://github.com/rhosocial/python-activerecord-testsuite.git@release/v1.0.0.dev16#egg=rhosocial-activerecord-testsuite
- name: Create postgres scenario config
run: |
cat > postgres_scenarios.yaml << EOF
scenarios:
postgres_default:
host: 127.0.0.1
port: 5432
database: test_db
username: root
password: password
postgres_exts:
host: 127.0.0.1
port: 5433
database: test_db
username: root
password: password
EOF
echo "POSTGRES_SCENARIOS_CONFIG_PATH=$(pwd)/postgres_scenarios.yaml" >> $GITHUB_ENV
- name: Install postgres client for health check
run: |
sudo apt-get update
sudo apt-get install --yes postgresql-client
- name: Wait for postgres service
run: |
until pg_isready -h 127.0.0.1 -p 5432 -U root; do
echo "Waiting for postgres..."
sleep 2
done
echo "postgres is ready!"
until pg_isready -h 127.0.0.1 -p 5433 -U root; do
echo "Waiting for postgres-exts..."
sleep 2
done
echo "postgres-exts is ready!"
- name: Run tests
run: |
export PYTHONPATH=src:tests
python -m pytest tests/ --tb=short --scenario-parallel -n 2 --dist=loadgroup
test:
name: Python ${{ matrix.python-version }} / postgres ${{ matrix.postgres-version }}
runs-on: ubuntu-latest
strategy:
fail-fast: false
matrix:
include:
- { python-version: '3.8', postgres-version: '9' }
- { python-version: '3.8', postgres-version: '10' }
- { python-version: '3.9', postgres-version: '11' }
- { python-version: '3.10', postgres-version: '12' }
- { python-version: '3.11', postgres-version: '13' }
- { python-version: '3.12', postgres-version: '14' }
- { python-version: '3.13', postgres-version: '15' }
- { python-version: '3.13', postgres-version: '16' }
- { python-version: '3.14', postgres-version: '17' }
- { python-version: '3.14', postgres-version: '18' }
services:
postgres:
image: postgres:${{ matrix.postgres-version }}
env:
POSTGRES_DB: test_db
POSTGRES_USER: root
POSTGRES_PASSWORD: password
ports:
- 5432:5432
options: >-
--health-cmd pg_isready
--health-interval 10s
--health-timeout 5s
--health-retries 5
postgres-exts:
image: vistart/postgres-exts:${{ matrix.postgres-version }}
env:
POSTGRES_DB: test_db
POSTGRES_USER: root
POSTGRES_PASSWORD: password
ports:
- 5433:5432
options: >-
--health-cmd pg_isready
--health-interval 10s
--health-timeout 5s
--health-retries 5
steps:
- name: Check out the repository
uses: actions/checkout@v6
- name: Set up Python ${{ matrix.python-version }}
uses: actions/setup-python@v6
with:
python-version: ${{ matrix.python-version }}
- name: Install dependencies
run: |
if [ "${{ matrix.python-version }}" == "3.8" ]; then
pip install -r requirements-3.8.txt
pip install -r requirements-dev-3.8.txt
else
pip install -r requirements.txt
pip install -r requirements-dev.txt
fi
- name: Install activerecord and testsuite
run: |
pip install git+https://github.com/rhosocial/python-activerecord.git@release/v1.0.0.dev29#egg=rhosocial-activerecord
pip install git+https://github.com/rhosocial/python-activerecord-testsuite.git@release/v1.0.0.dev16#egg=rhosocial-activerecord-testsuite
- name: Create postgres scenario config
run: |
cat > postgres_scenarios.yaml << EOF
scenarios:
postgres_default:
host: 127.0.0.1
port: 5432
database: test_db
username: root
password: password
postgres_exts:
host: 127.0.0.1
port: 5433
database: test_db
username: root
password: password
EOF
echo "POSTGRES_SCENARIOS_CONFIG_PATH=$(pwd)/postgres_scenarios.yaml" >> $GITHUB_ENV
- name: Install postgres client for health check
run: |
sudo apt-get update
sudo apt-get install --yes postgresql-client
- name: Wait for postgres service
run: |
until pg_isready -h 127.0.0.1 -p 5432 -U root; do
echo "Waiting for postgres..."
sleep 2
done
echo "postgres is ready!"
until pg_isready -h 127.0.0.1 -p 5433 -U root; do
echo "Waiting for postgres-exts..."
sleep 2
done
echo "postgres-exts is ready!"
- name: Run tests (skip for postgres 18)
if: matrix.postgres-version != '18'
run: |
export PYTHONPATH=src:tests
python -m pytest tests/ --tb=short --scenario-parallel -n 2 --dist=loadgroup
- name: Run tests with coverage (only for postgres 18)
if: matrix.postgres-version == '18'
run: |
export PYTHONPATH=src:tests
pip install codecov
python -m pytest tests/ --tb=short --scenario-parallel -n 2 --dist=loadgroup --cov=src --cov-report=xml
- name: Upload coverage to Codecov
if: matrix.postgres-version == '18'
uses: codecov/codecov-action@v4
with:
token: ${{ secrets.CODECOV_TOKEN }}
files: ./coverage.xml
flags: unittests,python-${{ matrix.python-version }},postgres-${{ matrix.postgres-version }}
name: codecov-postgres-${{ matrix.python-version }}-${{ matrix.postgres-version }}
fail_ci_if_error: false
test-postgres-19:
name: Python 3.14 / postgres 19beta1 (PGQ)
runs-on: ubuntu-latest
continue-on-error: true
services:
postgres:
image: postgres:19beta1
env:
POSTGRES_DB: test_db
POSTGRES_USER: root
POSTGRES_PASSWORD: password
ports:
- 5432:5432
options: >-
--health-cmd pg_isready
--health-interval 10s
--health-timeout 5s
--health-retries 5
steps:
- name: Check out the repository
uses: actions/checkout@v6
- name: Set up Python 3.14
uses: actions/setup-python@v6
with:
python-version: "3.14"
- name: Install dependencies
run: |
pip install -r requirements.txt
pip install -r requirements-dev.txt
- name: Install activerecord and testsuite
run: |
pip install git+https://github.com/rhosocial/python-activerecord.git@release/v1.0.0.dev29#egg=rhosocial-activerecord
pip install git+https://github.com/rhosocial/python-activerecord-testsuite.git@release/v1.0.0.dev16#egg=rhosocial-activerecord-testsuite
- name: Create postgres scenario config
run: |
cat > postgres_scenarios.yaml << EOF
scenarios:
postgres_default:
host: 127.0.0.1
port: 5432
database: test_db
username: root
password: password
EOF
echo "POSTGRES_SCENARIOS_CONFIG_PATH=$(pwd)/postgres_scenarios.yaml" >> $GITHUB_ENV
- name: Install postgres client for health check
run: |
sudo apt-get update
sudo apt-get install --yes postgresql-client
- name: Wait for postgres service
run: |
until pg_isready -h 127.0.0.1 -p 5432 -U root; do
echo "Waiting for postgres..."
sleep 2
done
echo "postgres is ready!"
- name: Run tests
run: |
export PYTHONPATH=src:tests
python -m pytest tests/ --tb=short --scenario-parallel -n 2 --dist=loadgroup