From e395878f925c10f5f51271b87170255f5913c2fc Mon Sep 17 00:00:00 2001 From: timmy Date: Sun, 16 Aug 2026 21:04:44 +0000 Subject: [PATCH] security: block vulnerable runtime dependencies (Closes #988) --- .gitea/workflows/ci.yml | 2 ++ requirements-audit.txt | 1 + requirements.txt | 2 +- tests/test_ci_workflow.py | 17 +++++++++++++++++ 4 files changed, 21 insertions(+), 1 deletion(-) create mode 100644 requirements-audit.txt diff --git a/.gitea/workflows/ci.yml b/.gitea/workflows/ci.yml index d8103a3..68d0c58 100644 --- a/.gitea/workflows/ci.yml +++ b/.gitea/workflows/ci.yml @@ -15,6 +15,8 @@ jobs: - uses: actions/setup-python@v5 with: { python-version: "3.11" } - run: pip install -r requirements.txt + - run: pip install -r requirements-audit.txt + - run: python3 -m pip_audit -r requirements.txt --strict - run: python3 -m pytest tests/ -q build-release: diff --git a/requirements-audit.txt b/requirements-audit.txt new file mode 100644 index 0000000..684087b --- /dev/null +++ b/requirements-audit.txt @@ -0,0 +1 @@ +pip-audit==2.10.1 diff --git a/requirements.txt b/requirements.txt index 3343e85..cd3011c 100644 --- a/requirements.txt +++ b/requirements.txt @@ -2,7 +2,7 @@ fastapi==0.133.1 httpx==0.28.1 pydantic==2.13.4 Pillow==12.3.0 -python-multipart==0.0.22 +python-multipart==0.0.32 pytest==9.1.1 pywebpush==2.1.2 rjsmin==1.2.5 diff --git a/tests/test_ci_workflow.py b/tests/test_ci_workflow.py index b7540ff..56bc7d8 100644 --- a/tests/test_ci_workflow.py +++ b/tests/test_ci_workflow.py @@ -17,6 +17,23 @@ def test_ci_installs_declared_requirements_before_tests(): assert install < tests +def test_ci_audits_pinned_runtime_dependencies_before_tests_and_release_build(): + text = WORKFLOW.read_text() + lint = text[text.index(" lint:") : text.index(" build-release:")] + build = text[text.index(" build-release:") : text.index(" browser-journey:")] + + audit_install = lint.index("pip install -r requirements-audit.txt") + audit = lint.index("python3 -m pip_audit -r requirements.txt --strict") + tests = lint.index("python3 -m pytest tests/ -q") + assert audit_install < audit < tests + assert "needs: lint" in build + + +def test_runtime_multipart_parser_uses_advisory_fixed_release(): + requirements = Path("requirements.txt").read_text().splitlines() + assert "python-multipart==0.0.32" in requirements + + def test_release_promotion_waits_for_tests_and_bundle(): text = WORKFLOW.read_text() release = text[text.index(" release-candidate:") :]