Repository navigation
Conversation
Avoids the per-file blob cap diverging from MAX_SBOM_BYTES. Previously hardcoded to 50 MB independently, so a change to the parser cap would silently leave the blob cap stale. Refs: IkarusAILabs#103
IkarusAILabs
left a comment
There was a problem hiding this comment.
Thanks for picking up #103, and for the clean, focused diff. Deriving the constant instead of duplicating the literal is a good instinct. Two things need to change before this can merge.
1. This PR does not fix #103, but Fixes #103 would close it
MAX_BLOB_BYTES was already 50 MB, the same value as MAX_SBOM_BYTES, so this PR doesn't change behaviour. The part of #103 that is still open (see this comment) is that the per-file cap equals the 50 MB total budget, so a single large file can use up the whole budget.
Reproduced on this branch, with _get_repo_tree stubbed to one 52,428,799-byte package-lock.json followed by five 100-byte requirements.txt files:
selected: ['big/package-lock.json']
reasons: ['svc0/requirements.txt: repository size cap (52428800 bytes) reached; remaining dependency files not inspected']
All five manifests go uninspected, which is exactly the scenario #103 describes. Merged as is, the issue would auto-close with that bug still there.
Either change the description to Refs #103, or finish #103:
- Set a per-file cap below the total budget (25 MB is #103's suggestion).
- Add #103's acceptance test: a tree with one oversized lockfile plus two small manifests. The two manifests are inspected, coverage is PARTIAL with one per-file reason, and the cumulative-cap path still reports its own reason.
test_truncated_tree_reports_partialintests/test_github_reader.pyis a good template; stub_get_repo_tree.
2. The existing cap test becomes a tautology
tests/test_bounded_io.py::test_blob_cap_matches_the_parser_cap asserts MAX_BLOB_BYTES == MAX_SBOM_BYTES. With MAX_BLOB_BYTES = MAX_SBOM_BYTES, that compares one object with itself and can never fail, yet the new comment says the relationship is "(enforced by tests)". Please replace it with assertions on the invariants that actually matter:
assert MAX_BLOB_BYTES <= MAX_SBOM_BYTES # never fetch what no reader will parse
assert MAX_BLOB_BYTES < MAX_DISCOVERED_BYTES # one file cannot use the whole budget (#103)
assert MAX_BLOB_BYTES <= 100 * 1024 * 1024 # GitHub blobs API limitA note for CI: this fork's workflows need a maintainer's approval before they run, so a push won't show checks right away.
Inline comments below have the details.
🤖 Review by Claude Code
| # only to be rejected. Over the cap is an explicit PARTIAL skip, never a silent | ||
| # "no dependencies" (F2). Derived from MAX_SBOM_BYTES so the two caps can never | ||
| # diverge (enforced by tests). | ||
| MAX_BLOB_BYTES = MAX_SBOM_BYTES |
There was a problem hiding this comment.
Binding the per-blob cap to the parser cap couples two different limits. If MAX_SBOM_BYTES is ever raised (multi-hundred-MB SBOMs exist), this rises with it, past GitHub's 100 MB blobs-API limit and past the 50 MB MAX_DISCOVERED_BYTES budget, and nothing notices. The pre-download 'exceeds inspection limit' skip would then turn into a fetch failure.
The cap is really the smallest of the three, so it reads more honestly as e.g.
_GITHUB_BLOB_API_LIMIT = 100 * 1024 * 1024
MAX_BLOB_BYTES = min(MAX_SBOM_BYTES, _GITHUB_BLOB_API_LIMIT, MAX_DISCOVERED_BYTES // 2)(// 2 gives the 25 MB that #103 suggests.)
🤖 Review by Claude Code
| # is skipped by its tree-declared size before download instead of being fetched | ||
| # only to be rejected. Over the cap is an explicit PARTIAL skip, never a silent | ||
| # "no dependencies" (F2). Derived from MAX_SBOM_BYTES so the two caps can never | ||
| # diverge (enforced by tests). |
There was a problem hiding this comment.
"(enforced by tests)" doesn't hold after this change: test_blob_cap_matches_the_parser_cap now compares the constant with itself (see the review summary). Please update the test to the real invariants, or drop the claim.
🤖 Review by Claude Code
| MAX_BLOB_BYTES = MAX_SBOM_BYTES | ||
| MAX_FILES = 200 # max dependency files to process | ||
| MAX_TREE_ENTRIES = 20_000 # bound recursive Git tree expansion before filtering | ||
| MAX_DISCOVERED_BYTES = 50 * 1024 * 1024 # 50MB total supported-file budget |
There was a problem hiding this comment.
The goal here is that the caps can't diverge, but this is still a separate copy of the same 50 MB literal, and nothing ties it to the per-file cap. Defining the per-file cap relative to this budget (and pinning MAX_BLOB_BYTES < MAX_DISCOVERED_BYTES in a test) would cover the #103 scenario for good.
🤖 Review by Claude Code
Fixes #103
Summary
Derive
MAX_BLOB_BYTESfromMAX_SBOM_BYTESinstead of a hardcodedduplicate so the two caps can never diverge.
Test plan
pytest tests/test_bounded_io.py tests/test_github_reader.py— 58 passedruff check core/github_reader.py— clean