chore: OSS hygiene — SECURITY.md, NOTICE, pre-commit, CI (F24, F25, F28)#12
Merged
Conversation
Two OSS hygiene additions surfaced by an internal security review: * **SECURITY.md** — points reporters at GitHub Security Advisories (private disclosure), documents a 90-day coordinated disclosure window, names what's in scope vs. upstream, and records the small set of accepted trade-offs (IPv4-literal SSRF blocklist; chunked refused with 411; loopback-bind threat model) so reporters do not re-file them as vulnerabilities. GitHub surfaces the file as a banner on the public repo. * **NOTICE** — explicit Apache-2.0 attribution for the vLLM upstream the gateway proxies in front of. The README mentions vLLM in prose; the NOTICE file is the canonical legal-attribution location and makes clear that vLLM is not redistributed by this package and references are nominative. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Adds the same set of formatters / linters / secret-scanners that CI runs, so a contributor sees lint failures locally before pushing rather than waiting for a CI red. Hooks: - pre-commit-hooks @ v4.6.0 — trailing whitespace, EOF newline, YAML/TOML syntax, large-file gate (512 KB), merge-conflict markers, LF line-ending fixer (defends against Windows contributor CRLF noise mixing into the repo). - ruff @ v0.7.0 — same version pinned in pyproject.toml dev-deps. Auto-fix on commit; manual review of the diff before push. - black @ 26.3.1 — same version pinned in pyproject.toml dev-deps. - detect-secrets @ v1.5.0 — baseline file pattern is the standard ``.secrets.baseline``; first-run generates it via ``detect-secrets scan > .secrets.baseline``. Install per-checkout with ``pre-commit install``. Run ad-hoc with ``pre-commit run --all-files``. Versions are pinned to exact tags so behaviour is reproducible and bumps are deliberate. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
GitHub's default-setup CodeQL was the only automated check on PRs; broken format / lint / type / test regressions slipped past review because nothing stopped them at the seam between author and merge. Add ``ci.yml`` covering Python 3.11 + 3.12 matrix: - Poetry install with poetry.lock-keyed cache - ``ruff check`` (lint) - ``black --check`` (format gate, no auto-fix in CI) - ``pyright`` (type check on llm_gateway/) - ``pytest tests/unit/ -v`` (existing unit suite) Concurrency group cancels superseded runs on the same ref so a fast-following push does not waste runners. Pip-audit is deliberately not bundled into this workflow — it deserves its own scheduled cron to surface new CVEs decoupled from PR lifecycle, and is queued as a follow-up. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
The CI workflow added in this PR surfaced a pyright error on chat_completions.py:143 — `int(value or 0)` rejects when `value` is typed as `object` because object does not conform to ConvertibleToInt (str | Buffer | SupportsInt | SupportsIndex). `Any` is the honest type for this defensive helper since the function exists precisely to handle arbitrary upstream JSON; the `try/except (TypeError, ValueError)` already covers every runtime shape mismatch. No behaviour change — pyright type relaxation only. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Companion to PR #6 / commit f40049e which bumped the bearer-token rate-limit key truncation from `[:16]` (64 bits) to `[:32]` (128 bits). The existing test `test_middleware_passes_request_when_limiter_allows` still asserted the old 16-hex slice, so the production code drifted from the test silently — PR #6 had no CI gate at the time it merged (the CI workflow lands in this PR), and the gap surfaced once CI ran. The companion regression-guard test `test_middleware_key_hash_does_not_contain_plaintext_token` is agnostic to digest length and stays unchanged. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
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
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
Four OSS hygiene additions split into atomic commits. None touches
llm_gateway/source code.docs: add SECURITY.md and NOTICESECURITY.mddocs: add SECURITY.md and NOTICENOTICEchore: add .pre-commit-config.yaml mirroring CI gates.pre-commit-config.yamlchore: add CI workflow (ruff / black / pyright / pytest).github/workflows/ci.ymlWhy bundled
All four are first-time OSS scaffolding that share one mental model ("how do contributors and CI know what passes"). Splitting them across PRs leaves the repo in awkward intermediate states (e.g. CI but no pre-commit, or vice versa).
What's deliberately NOT in this PR
pip-auditschedule — deserves its own cron-driven workflow that surfaces new CVEs decoupled from PR lifecycle. Queued as a follow-up.Test plan
ci.ymlruns against this PR itself; matrix output is the verificationRelated
Findings F24 (SECURITY.md), F25 (pre-commit), F28 (NOTICE for vLLM Apache-2.0) from internal security review punch list.
🤖 Generated with Claude Code