Files
xsl 9c1802130d chore(prep): shared groundwork for batch-3 (admin/golden/cache)
第三批(T12 后台/T13 黄金集/T14 检索缓存)协调提交:
- kb:KbAssetService(登记/审核,tryon_ready 只能随 approved 打开)+ Asset 模型与 repo
- retrieval:list_gaps 缺口看板查询 + invalidate_cache() 钩子(T14 背后实现真缓存)
- 配置:ADMIN_TOKEN(空=后台 404)+ 检索缓存三参数
- pytest golden marker(默认跳过,CI 强制跑)+ Makefile golden + CI 防线 5c
- 测试隔离修复:test_auth_sms 加 autouse 清 sms:* 键夹具(频控计数跨运行
  累积会毒化后续运行——随机 IP 空间仅 254 且部分用例固定 device_id)
2026-08-14 20:57:52 +08:00

127 lines
3.8 KiB
YAML
Executable File

# 架构文档 §16.2:这些防线是机器可执行的检查,任一失败即阻断合并。
name: CI
on:
push:
branches: [main]
pull_request:
workflow_dispatch:
concurrency:
group: ci-${{ github.ref }}
cancel-in-progress: true
env:
UV_CACHE_DIR: /tmp/.uv-cache
jobs:
quality-gate:
name: lint / typecheck / import-linter / tests / secrets
runs-on: ubuntu-latest
timeout-minutes: 20
services:
postgres:
image: pgvector/pgvector:pg16
env:
POSTGRES_USER: meida
POSTGRES_PASSWORD: meida
POSTGRES_DB: meida_test
ports: ["5432:5432"]
options: >-
--health-cmd "pg_isready -U meida"
--health-interval 5s
--health-timeout 5s
--health-retries 20
redis:
image: redis:7-alpine
ports: ["6379:6379"]
options: >-
--health-cmd "redis-cli ping"
--health-interval 5s
--health-timeout 5s
--health-retries 20
env:
APP_ENV: dev
JWT_SECRET: ci-only-not-a-real-secret-0123456789abcdef
DATABASE_URL: postgresql+asyncpg://meida:meida@localhost:5432/meida_test
REDIS_URL: redis://localhost:6379/0
CELERY_BROKER_URL: redis://localhost:6379/1
CELERY_RESULT_BACKEND: redis://localhost:6379/2
DEEPSEEK_API_KEY: ci-placeholder-no-network-calls-in-ci
steps:
- uses: actions/checkout@v4
with:
fetch-depth: 0
- name: Install uv
uses: astral-sh/setup-uv@v5
with:
enable-cache: true
- name: Set up Python 3.12
run: uv python install 3.12
- name: Install dependencies
run: uv sync --extra dev --frozen
# --- 防线 1: 静态检查 (ruff lint + format) ---
- name: Ruff lint
run: uv run ruff check --output-format=github .
- name: Ruff format check
run: uv run ruff format --check .
# --- 防线 2: mypy strict 覆盖 packages/domain 与 packages/llm ---
- name: Mypy (strict scope)
run: uv run mypy packages/domain packages/llm
- name: Mypy (remaining scope)
run: uv run mypy apps packages/shared packages/identity packages/billing packages/task packages/agent packages/compliance packages/analytics packages/storage
# --- 防线 3: 分层依赖检查 (架构文档 §4.2) ---
- name: Import contracts
run: uv run lint-imports --verbose
# --- 防线 4: 单元测试 + 覆盖率 ---
- name: Pytest (unit)
run: uv run pytest --cov-report=xml
# --- 防线 5: 数据库迁移必须可正向执行并可回滚 (T-P1-06) ---
- name: Alembic upgrade/downgrade round-trip
run: |
uv run alembic upgrade head
uv run alembic downgrade base
uv run alembic upgrade head
# --- 防线 5b: 集成切片。容器已经为迁移往返拉起来了,不跑等于白起 ---
- name: Pytest (integration)
env:
MEIDA_RUN_INTEGRATION: "1"
run: uv run pytest -m integration --no-cov
# --- 防线 5c: 黄金集回归。指标退化(通过率低于阈值)直接失败(T-P2-11) ---
- name: Golden set regression
env:
MEIDA_RUN_INTEGRATION: "1"
run: uv run pytest -m golden --no-cov
# --- 防线 6: 敏感信息扫描 ---
- name: Secrets scan (detect-secrets)
run: |
uv run detect-secrets scan --baseline .secrets.baseline
git diff --exit-code .secrets.baseline
- name: Gitleaks
uses: gitleaks/gitleaks-action@v2
env:
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
- name: Upload coverage
if: always()
uses: actions/upload-artifact@v4
with:
name: coverage
path: coverage.xml
if-no-files-found: ignore