feat(ci): 週次 schedule と workflow_dispatch を追加し外界の変化を検知する (v1.8.169) #938
Workflow file for this run
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| name: CI | |
| on: | |
| push: | |
| branches: [main] | |
| pull_request: | |
| branches: [main] | |
| # 週次で main をフル実行する(push とは独立に)。 | |
| # | |
| # 検知したいのは「コードの変化」ではなく **外界の変化** — 上流の advisory データである。 | |
| # 2026-05-30 から 2026-08-12 までの 74 日間、このリポジトリには 1 コミットも無く、 | |
| # CI も一度も走らなかった。その間にコードは 1 行も変わっていないのに `pip-audit` の | |
| # 検出数は 0 → 22 件(pyjwt / cryptography / starlette を含む=認証と TLS の面)へ増えていた。 | |
| # advisory は我々のコミットではなく、それ自身の時計で公開されるためである。 | |
| # | |
| # ここでの検知器は `pip-audit`。`uv.lock` をコミットしていて `uv sync` がそれを尊重するので、 | |
| # 週次実行は「いま固定している版に対する既知脆弱性」を正確に測る。 | |
| # | |
| # 毎時 00 分は GitHub Actions の高負荷帯で schedule が遅延しやすいと公式に明記されているため、 | |
| # 意図的に 30 分にずらしている。月曜 00:30 UTC = 09:30 JST(週明けの始業時刻)。 | |
| # | |
| # 🔴 既知の限界: public リポジトリの scheduled workflow は、リポジトリの活動が 60 日間 | |
| # 無いと GitHub により **自動的に無効化される**。上記の空白は 74 日で、しきい値を 14 日 | |
| # 超えている。つまりこの装置は、それが検知しようとしている状態そのものによって止められうる。 | |
| # 「週次が動いている」ことを外側から確かめる仕組みは、この workflow では解決できない | |
| # (docs/review/2026-08-12.md の後続タスク)。 | |
| schedule: | |
| - cron: '30 0 * * 1' | |
| # schedule の初回発火を待たずに動作確認・再実行するための手動トリガー。 | |
| workflow_dispatch: | |
| # 同一 ref への連続 push で古い実行を打ち切り、CI 時間を無駄にしない。 | |
| # 🔴 `github.event_name` を必ず group に含めること。含めないと schedule / workflow_dispatch の | |
| # 実行が push の実行に cancel され、「設定したのに走らない」状態になる。設定ファイルは | |
| # 正しく見えるのに動かないため気づきにくい(nene-origin で実測された罠)。 | |
| concurrency: | |
| group: ci-${{ github.workflow }}-${{ github.ref }}-${{ github.event_name }} | |
| cancel-in-progress: true | |
| jobs: | |
| check: | |
| runs-on: ubuntu-latest | |
| strategy: | |
| matrix: | |
| python-version: ["3.12", "3.14"] | |
| steps: | |
| - uses: actions/checkout@v4 | |
| - name: Install uv | |
| uses: astral-sh/setup-uv@v5 | |
| with: | |
| version: "latest" | |
| enable-cache: true | |
| - name: Set up Python ${{ matrix.python-version }} | |
| run: uv python install ${{ matrix.python-version }} | |
| - name: Install dependencies | |
| run: uv sync --all-extras | |
| - name: pytest (with coverage) | |
| run: uv run pytest | |
| - name: coverage gate — domain/use_case layers (90%) | |
| run: | | |
| uv run coverage report \ | |
| --include="src/example/*/use_case.py,src/example/*/async_use_case.py,src/example/*/entity.py" \ | |
| --fail-under=90 | |
| - name: mypy | |
| run: uv run mypy src/ | |
| - name: ruff check | |
| run: uv run ruff check src/ tests/ | |
| - name: ruff format | |
| run: uv run ruff format --check src/ tests/ | |
| - name: pip-audit | |
| # PYSEC-2025-183: pyjwt weak-key-length — disputed by supplier, no fix version available. | |
| # Transitive via mcp>=1.0. Re-evaluate when pyjwt releases a fix. (#280) | |
| run: uv run pip-audit --ignore-vuln PYSEC-2025-183 | |
| integration-db: | |
| name: Real-DB integration tests | |
| runs-on: ubuntu-latest | |
| # 実 PostgreSQL / MySQL に対してリポジトリ層を検証する(#747)。 | |
| # SQLite だけでは露見しなかった lastrowid 由来の採番バグを CI で恒常的に防ぐ。 | |
| services: | |
| postgres: | |
| image: postgres:16-alpine | |
| env: | |
| POSTGRES_PASSWORD: nene2 | |
| POSTGRES_DB: nene2_test | |
| ports: | |
| - 5432:5432 | |
| options: >- | |
| --health-cmd "pg_isready -U postgres" | |
| --health-interval 5s --health-timeout 5s --health-retries 10 | |
| mysql: | |
| image: mysql:8 | |
| env: | |
| MYSQL_ROOT_PASSWORD: nene2 | |
| MYSQL_DATABASE: nene2_test | |
| ports: | |
| - 3306:3306 | |
| options: >- | |
| --health-cmd "mysqladmin ping -uroot -pnene2" | |
| --health-interval 5s --health-timeout 5s --health-retries 20 | |
| steps: | |
| - uses: actions/checkout@v4 | |
| - name: Install uv | |
| uses: astral-sh/setup-uv@v5 | |
| with: | |
| version: "latest" | |
| enable-cache: true | |
| - name: Set up Python | |
| run: uv python install 3.14 | |
| - name: Install dependencies | |
| run: uv sync --all-extras | |
| - name: integration tests (PostgreSQL + MySQL) | |
| env: | |
| NENE2_TEST_POSTGRES_URL: postgresql+psycopg2://postgres:nene2@127.0.0.1:5432/nene2_test | |
| NENE2_TEST_MYSQL_URL: mysql+pymysql://root:nene2@127.0.0.1:3306/nene2_test | |
| run: uv run pytest tests/integration/ -v --no-cov | |
| package-build: | |
| name: Package build verification | |
| runs-on: ubuntu-latest | |
| steps: | |
| - uses: actions/checkout@v4 | |
| - name: Install uv | |
| uses: astral-sh/setup-uv@v5 | |
| with: | |
| version: "latest" | |
| # publish.yml と同じ uv build を PR ごとに走らせ、配布物の壊れを早期検出する(#541)。 | |
| - name: Build sdist + wheel | |
| run: uv build | |
| - name: Validate distribution metadata (twine check) | |
| run: uvx twine check dist/* | |
| - name: Verify clean install + import (no example/tests leakage) | |
| run: | | |
| uv venv /tmp/verify | |
| uv pip install --python /tmp/verify/bin/python dist/*.whl | |
| /tmp/verify/bin/python -c "import nene2; from nene2.http import PaginationResponse; print('import OK')" | |
| # フレームワーク以外(example/tests)が配布物に混入していないことを保証 | |
| if /tmp/verify/bin/python -c "import example" 2>/dev/null; then | |
| echo "ERROR: example package leaked into wheel"; exit 1 | |
| fi |