feat(manifest): add fork-identity fields for Phase C / P4 (no forks yet) - #82
Conversation
Tooling-only groundwork for the selective fork policy. Does not fork
anything -- see docs/adr/0001 for the full Lane 3 eligibility and
stewardship checklist that gates any real fork, which this PR doesn't
attempt.
- validate_manifest.py: optional upstream_repo field ('owner/name' of
the original upstream). Requires owner == 'numan-maintained' on any
entry that sets it, so a fork manifest entry can't claim the
original author's identity.
- gen_spec.py: when upstream_repo is present, emits source.upstream
in the generated spec (consumed by numan-registry's add-package.py,
which now requires it for owner 'numan-maintained') and appends a
fork-attribution note to the description.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
📝 WalkthroughWalkthroughThe manifest now documents and validates optional ChangesUpstream repository provenance
Estimated code review effort: 3 (Moderate) | ~20 minutes 🚥 Pre-merge checks | ✅ 8✅ Passed checks (8 passed)
✨ Finishing Touches📝 Generate docstrings
🧪 Generate unit tests (beta)
✨ Simplify code
Warning Review ran into problems🔥 ProblemsLinked repositories: Public OSS repositories can only analyze public repositories installed in this organization. Analyzed Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. Comment |
There was a problem hiding this comment.
Sorry @tonythethompson, you have reached your weekly rate limit of 500000 diff characters.
Please try again later or upgrade to continue using Sourcery
PR Summary by QodoAdd fork identity support via optional upstream_repo in manifest + spec output
AI Description
Diagram
High-Level Assessment
Files changed (5)
|
Greptile SummaryThe PR adds fork-identity validation and generated-spec provenance for future
Confidence Score: 4/5The PR is not yet safe to merge because malformed repository identities can still pass validation and produce incorrect upstream URLs. The new slug regex excludes slashes and whitespace inside each segment but still accepts URL delimiter characters; Files Needing Attention: scripts/validate_manifest.py
|
| Filename | Overview |
|---|---|
| scripts/validate_manifest.py | Adds centralized validation for maintained-fork ownership, required upstream identity, slug shape, and self-reference. |
| scripts/gen_spec.py | Reuses manifest validation and emits upstream provenance plus a fork-attribution description for maintained forks. |
| scripts/test_validate_manifest.py | Covers ownership, presence, blank values, common malformed forms, and self-referential upstream identities. |
| scripts/test_gen_spec_source.py | Covers generated provenance, attribution text, validation failures, and unchanged non-fork output. |
| manifest.json | Documents the optional fork-identity field and its intended stewardship constraints. |
Reviews (7): Last reviewed commit: "Potential fix for pull request finding" | Re-trigger Greptile
There was a problem hiding this comment.
💡 Codex Review
Here are some automated review suggestions for this pull request.
Reviewed commit: 3de7acfd42
ℹ️ About Codex in GitHub
Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you
- Open a pull request for review
- Mark a draft as ready
- Comment "@codex review".
If Codex has suggestions, it will comment; otherwise it will react with 👍.
Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".
Code Review by Qodo
1.
|
Qodo FixerNo findings are within the configured fix scope. To change which findings are fixed, adjust the setting on your Qodo configuration page. |
Require upstream_repo when owner is numan-maintained and reject values outside the documented owner/name form so gen_spec cannot emit broken upstream provenance. Co-authored-by: Cursor <cursoragent@cursor.com>
|
Fixed in ee44791: numan-maintained entries now require upstream_repo, and upstream_repo must match the documented owner/name form (rejects whitespace, URLs, and extra path segments). Added regression tests. |
Reduce validate_manifest complexity for CodeFactor while keeping the fork upstream_repo contract checks unchanged. Co-authored-by: Cursor <cursoragent@cursor.com>
Require numan-maintained owner when emitting upstream_repo in gen_spec and point manifest schema notes at the numan ADR on GitHub. Co-authored-by: Cursor <cursoragent@cursor.com>
There was a problem hiding this comment.
Actionable comments posted: 2
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
Inline comments:
In `@scripts/validate_manifest.py`:
- Line 73: Remove the behavior-only docstring from the manifest validation
function associated with optional fork upstream_repo metadata. Do not replace it
with another comment unless it documents a non-obvious rationale or invariant.
- Around line 72-89: Reject self-referential upstream provenance by updating
validate_upstream_repo in scripts/validate_manifest.py to compare upstream_repo
with entry["repo"] case-insensitively and raise a validation error when they
identify the same GitHub repository. In scripts/gen_spec.py lines 151-167, call
the shared validation helper before emitting source.upstream so direct
build_spec callers enforce the same invariant. Add matching rejection coverage
in scripts/test_validate_manifest.py lines 123-135 and
scripts/test_gen_spec_source.py lines 67-99, including case-only repository
variations.
🪄 Autofix
Fix all unresolved CodeRabbit comments on this PR:
- Push a commit to this branch (recommended)
- Create a new PR with the fixes
ℹ️ Review info
⚙️ Run configuration
Configuration used: Organization UI
Review profile: ASSERTIVE
Plan: Pro Plus
Run ID: 944e6c09-4ede-43f5-a062-f6042a18f2c7
📒 Files selected for processing (5)
manifest.jsonscripts/gen_spec.pyscripts/test_gen_spec_source.pyscripts/test_validate_manifest.pyscripts/validate_manifest.py
🔗 Linked repositories identified
CodeRabbit considers these linked repositories for cross-repo context during reviews:
tonythethompson/QuickShell(manual)tonythethompson/numan(manual) → reviewed against open PR#116feat/p4-fork-identity-toolinginstead of the default branchtonythethompson/dependency-chain-substrate(manual)
📜 Review details
⏰ Context from checks skipped due to timeout. (1)
- GitHub Check: Greptile Review
🧰 Additional context used
📓 Path-based instructions (7)
**/*.{cs,py}
📄 CodeRabbit inference engine (Custom checks)
**/*.{cs,py}: Ensure managed host restarts are safe: modifications involvingManagedVenvHostManager,ContainerizedServiceProbe,ContainerizedInferenceClient, orContainerizedProviderReadinessmust not callStopTrackedHost,RestartAsync, or equivalent host-kill methods unless active request leases are zero. Hosts reportingbusy_reasonoractive_requests > 0must not be restarted, and readiness probing must not downgrade a known-available host merely because a background refresh is in flight.
MaintainSessionWorkflowStageordering asFoundation < MediaLoaded < Transcribed < Diarized < Translated < TtsGenerated. Comparisons must use enum members rather than raw integer literals. New or renumbered members require a legacy-compatible JSON converter for old numeric values, and reordered enums require checking every inequality comparison across the solution for preserved semantic meaning.
Files:
scripts/test_gen_spec_source.pyscripts/gen_spec.pyscripts/validate_manifest.pyscripts/test_validate_manifest.py
**/*
📄 CodeRabbit inference engine (CLAUDE.md)
**/*: Use Serena's semantic, symbol-aware tools as the primary tools for code work; use built-in Read, Glob, Grep, and Edit only when Serena cannot perform the task or an explicitly listed exception applies.
Use the appropriate Serena symbol tool for code operations: get_symbols_overview for structure, find_symbol for symbol bodies, find_referencing_symbols for callers, find_declaration or implementations for declarations, replace_symbol_body for edits, insertion tools for nearby additions, replace_content for pattern replacement, and rename, move, safe-delete, or inline tools for refactoring.
Before editing code, obtain a symbol overview of the target file, inspect the specific symbols with bodies included, and edit using Serena's symbol-aware tools.
Understand existing code before changing it and make the smallest change that satisfies the request; avoid unrelated cleanup, premature abstractions, speculative error handling, feature flags, and compatibility shims unless requested.
Prefer editing existing files over creating new ones, and never create Markdown or README files unless explicitly requested.
For exploratory questions, provide a recommendation and the main tradeoff in two or three sentences without implementing changes until the user agrees.
For UI or frontend changes that cannot be tested in a browser, explicitly state that browser testing was not performed rather than claiming success.
Identify and fix security issues when discovered, including injection, XSS, SQL injection, path traversal, and secret leaks.
Pause and obtain confirmation before destructive, hard-to-reverse, externally visible, or third-party-upload actions, including deleting files or branches, dropping tables, killing processes, force-pushing, changing CI/CD, posting externally, or uploading content.
When encountering an obstacle, investigate the root cause instead of bypassing it with --no-verify, --force, or deletion; investigate unfamiliar files, branches, and configuration befor...
Files:
scripts/test_gen_spec_source.pyscripts/gen_spec.pymanifest.jsonscripts/validate_manifest.pyscripts/test_validate_manifest.py
**/*.{js,jsx,ts,tsx,py,java,go,rs,rb,php,c,cpp,h,hpp,cs,swift,kt,kts}
📄 CodeRabbit inference engine (CLAUDE.md)
Do not add comments unless the rationale is non-obvious, such as a hidden constraint, workaround, subtle invariant, or other necessary explanation; do not narrate behavior or reference the current task in comments.
Files:
scripts/test_gen_spec_source.pyscripts/gen_spec.pyscripts/validate_manifest.pyscripts/test_validate_manifest.py
scripts/**/*.py
📄 CodeRabbit inference engine (REVIEW.md)
scripts/**/*.py: The CI gates must pass:python3 -m compileall -q scriptsandpython3 -m unittest discover -s scripts -p "test_*.py" -v.
Packaging and release scripts must preserve draft ownership, refuse to overwrite existing release tags or assets, and fail closed when the complete asset set is unavailable.
Generated specifications must omit authoredsha256hashes; hashes are downloaded and generated bynuman-registryduring intake.
Files:
scripts/test_gen_spec_source.pyscripts/gen_spec.pyscripts/validate_manifest.pyscripts/test_validate_manifest.py
scripts/**/*.{py,json}
📄 CodeRabbit inference engine (REVIEW.md)
Packaging and release helpers must have tests covering failure modes, including incomplete asset sets, overwrite attempts, and release transaction errors.
Files:
scripts/test_gen_spec_source.pyscripts/gen_spec.pyscripts/validate_manifest.pyscripts/test_validate_manifest.py
manifest.json
📄 CodeRabbit inference engine (REVIEW.md)
manifest.json: Eachactive[]manifest entry must pin a human-facing upstream tag and immutablesource_commit; workflows must verify that the tag resolves to the pinned commit.
Changes to the active publish set must match the pull request scope; backlog-only edits must not silently modifyactive[].
Files:
manifest.json
scripts/validate_manifest.py
📄 CodeRabbit inference engine (REVIEW.md)
Manifest validation with
python3 scripts/validate_manifest.py --verify-upstreammust pass.
Files:
scripts/validate_manifest.py
🪛 Ruff (0.16.1)
scripts/gen_spec.py
[warning] 163-165: Avoid specifying long messages outside the exception class
(TRY003)
scripts/validate_manifest.py
[warning] 78-78: Avoid specifying long messages outside the exception class
(TRY003)
[warning] 80-82: Avoid specifying long messages outside the exception class
(TRY003)
[warning] 84-87: Avoid specifying long messages outside the exception class
(TRY003)
[warning] 89-89: Avoid specifying long messages outside the exception class
(TRY003)
scripts/test_validate_manifest.py
[warning] 105-105: Use pytest.raises instead of unittest-style assertRaisesRegex
Replace assertRaisesRegex with pytest.raises
(PT027)
[warning] 115-115: Use pytest.raises instead of unittest-style assertRaisesRegex
Replace assertRaisesRegex with pytest.raises
(PT027)
[warning] 120-120: Use pytest.raises instead of unittest-style assertRaisesRegex
Replace assertRaisesRegex with pytest.raises
(PT027)
[warning] 134-134: Use pytest.raises instead of unittest-style assertRaisesRegex
Replace assertRaisesRegex with pytest.raises
(PT027)
🔍 Remote MCP GitHub Copilot
Relevant review context
- The current PR is
#82intonythethompson/numan-plugins; its checks include successful manifest/packaging validation, while the AI reviewer check is neutral. - The companion registry PR numan-cli/numan-registry#66 adds the consumer-side
source.upstreamsupport. It additionally requires an HTTP(S) URL, rejectssource.upstreamon non-numan-maintainedpackages, and rejects an upstream URL identifying the same repository assource.git. - PR
#82’s manifest validation only checks a looseowner/nameslug.gen_spec.pyalso only checks thenuman-maintainedowner, so malformed or self-referential upstream values are not rejected until the registry intake step. - The base manifest already contains two entries tagged
"fork"but owned bytonythethompson(nu_plugin_qr_makerandnu_plugin_explore); noupstream_repofields are present on those entries. This is worth reconciling with the PR’s stated “no forks yet” scope and fork-identification policy. - The related
numan-plugins#80also changesvalidate_manifest.pyandgen_spec.pyfor commit-snapshot intake, so review should account for possible stacked-PR interactions rather than treating these files as isolated.
🔇 Additional comments (1)
manifest.json (1)
4-6: LGTM!
A numan-maintained entry could set upstream_repo equal to its own repo (case-insensitively), which the registry intake in numan-registry rejects since source.upstream would equal source.git. Validate this in both validate_manifest.py and gen_spec.py's build_spec() so direct callers get the same guarantee. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
|
Addressed in 6b43fcb (pushed): a numan-maintained entry can no longer set The two codex comments were already stale against current code: the reverse check ( Removed the restating docstring flagged by CodeRabbit and replaced it with one stating the actual invariants (fork can't claim original owner's identity, can't omit upstream_repo, can't self-reference) since this repo's docstring-coverage test requires every function to have one. |
There was a problem hiding this comment.
Caution
Some comments are outside the diff and can’t be posted inline due to platform limitations.
⚠️ Outside diff range comments (1)
scripts/gen_spec.py (1)
151-169: 🗄️ Data Integrity & Integration | 🟠 Major | ⚡ Quick winRun the full upstream validator in
build_spec.When
upstream_repois absent or"",if upstream_repo:skips validation. A directbuild_spec()call can emit anuman-maintainedspecification withoutsource.upstream, although manifest validation and registry intake require it. A malformed truthy slug also reaches the output ashttps://github.com/<value>.Call
validate_upstream_repo(entry)before this branch. Then useif upstream_repo is not Noneand remove the duplicate ownership and self-reference checks. Add directbuild_spec()coverage for absent, blank, and malformed values.🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the rest with a brief reason, keep changes minimal, and validate. In `@scripts/gen_spec.py` around lines 151 - 169, The build_spec flow must always validate upstream_repo before branching, including absent, blank, and malformed values. Call validate_upstream_repo(entry) before the upstream handling, change the condition to distinguish None from an empty string, and remove the duplicate owner and self-reference checks while preserving source.upstream generation only for valid configured values; add direct build_spec coverage for these cases.Source: MCP tools
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
Outside diff comments:
In `@scripts/gen_spec.py`:
- Around line 151-169: The build_spec flow must always validate upstream_repo
before branching, including absent, blank, and malformed values. Call
validate_upstream_repo(entry) before the upstream handling, change the condition
to distinguish None from an empty string, and remove the duplicate owner and
self-reference checks while preserving source.upstream generation only for valid
configured values; add direct build_spec coverage for these cases.
ℹ️ Review info
⚙️ Run configuration
Configuration used: Organization UI
Review profile: ASSERTIVE
Plan: Pro Plus
Run ID: 4a888067-dc71-48e2-ad01-fdbffd5e9af2
📒 Files selected for processing (4)
scripts/gen_spec.pyscripts/test_gen_spec_source.pyscripts/test_validate_manifest.pyscripts/validate_manifest.py
🔗 Linked repositories identified
CodeRabbit considers these linked repositories for cross-repo context during reviews:
tonythethompson/QuickShell(manual)tonythethompson/numan(manual) → reviewed against open PR#116feat/p4-fork-identity-toolinginstead of the default branchtonythethompson/dependency-chain-substrate(manual)
📜 Review details
⏰ Context from checks skipped due to timeout. (1)
- GitHub Check: Greptile Review
🧰 Additional context used
📓 Path-based instructions (6)
**/*.{cs,py}
📄 CodeRabbit inference engine (Custom checks)
**/*.{cs,py}: Ensure managed host restarts are safe: modifications involvingManagedVenvHostManager,ContainerizedServiceProbe,ContainerizedInferenceClient, orContainerizedProviderReadinessmust not callStopTrackedHost,RestartAsync, or equivalent host-kill methods unless active request leases are zero. Hosts reportingbusy_reasonoractive_requests > 0must not be restarted, and readiness probing must not downgrade a known-available host merely because a background refresh is in flight.
MaintainSessionWorkflowStageordering asFoundation < MediaLoaded < Transcribed < Diarized < Translated < TtsGenerated. Comparisons must use enum members rather than raw integer literals. New or renumbered members require a legacy-compatible JSON converter for old numeric values, and reordered enums require checking every inequality comparison across the solution for preserved semantic meaning.
Files:
scripts/gen_spec.pyscripts/test_validate_manifest.pyscripts/test_gen_spec_source.pyscripts/validate_manifest.py
**/*
📄 CodeRabbit inference engine (CLAUDE.md)
**/*: Use Serena's semantic, symbol-aware tools as the primary tools for code work; use built-in Read, Glob, Grep, and Edit only when Serena cannot perform the task or an explicitly listed exception applies.
Use the appropriate Serena symbol tool for code operations: get_symbols_overview for structure, find_symbol for symbol bodies, find_referencing_symbols for callers, find_declaration or implementations for declarations, replace_symbol_body for edits, insertion tools for nearby additions, replace_content for pattern replacement, and rename, move, safe-delete, or inline tools for refactoring.
Before editing code, obtain a symbol overview of the target file, inspect the specific symbols with bodies included, and edit using Serena's symbol-aware tools.
Understand existing code before changing it and make the smallest change that satisfies the request; avoid unrelated cleanup, premature abstractions, speculative error handling, feature flags, and compatibility shims unless requested.
Prefer editing existing files over creating new ones, and never create Markdown or README files unless explicitly requested.
For exploratory questions, provide a recommendation and the main tradeoff in two or three sentences without implementing changes until the user agrees.
For UI or frontend changes that cannot be tested in a browser, explicitly state that browser testing was not performed rather than claiming success.
Identify and fix security issues when discovered, including injection, XSS, SQL injection, path traversal, and secret leaks.
Pause and obtain confirmation before destructive, hard-to-reverse, externally visible, or third-party-upload actions, including deleting files or branches, dropping tables, killing processes, force-pushing, changing CI/CD, posting externally, or uploading content.
When encountering an obstacle, investigate the root cause instead of bypassing it with --no-verify, --force, or deletion; investigate unfamiliar files, branches, and configuration befor...
Files:
scripts/gen_spec.pyscripts/test_validate_manifest.pyscripts/test_gen_spec_source.pyscripts/validate_manifest.py
**/*.{js,jsx,ts,tsx,py,java,go,rs,rb,php,c,cpp,h,hpp,cs,swift,kt,kts}
📄 CodeRabbit inference engine (CLAUDE.md)
Do not add comments unless the rationale is non-obvious, such as a hidden constraint, workaround, subtle invariant, or other necessary explanation; do not narrate behavior or reference the current task in comments.
Files:
scripts/gen_spec.pyscripts/test_validate_manifest.pyscripts/test_gen_spec_source.pyscripts/validate_manifest.py
scripts/**/*.py
📄 CodeRabbit inference engine (REVIEW.md)
scripts/**/*.py: The CI gates must pass:python3 -m compileall -q scriptsandpython3 -m unittest discover -s scripts -p "test_*.py" -v.
Packaging and release scripts must preserve draft ownership, refuse to overwrite existing release tags or assets, and fail closed when the complete asset set is unavailable.
Generated specifications must omit authoredsha256hashes; hashes are downloaded and generated bynuman-registryduring intake.
Files:
scripts/gen_spec.pyscripts/test_validate_manifest.pyscripts/test_gen_spec_source.pyscripts/validate_manifest.py
scripts/**/*.{py,json}
📄 CodeRabbit inference engine (REVIEW.md)
Packaging and release helpers must have tests covering failure modes, including incomplete asset sets, overwrite attempts, and release transaction errors.
Files:
scripts/gen_spec.pyscripts/test_validate_manifest.pyscripts/test_gen_spec_source.pyscripts/validate_manifest.py
scripts/validate_manifest.py
📄 CodeRabbit inference engine (REVIEW.md)
Manifest validation with
python3 scripts/validate_manifest.py --verify-upstreammust pass.
Files:
scripts/validate_manifest.py
🪛 Ruff (0.16.1)
scripts/gen_spec.py
[warning] 167-167: Avoid specifying long messages outside the exception class
(TRY003)
scripts/test_validate_manifest.py
[warning] 125-125: Use pytest.raises instead of unittest-style assertRaisesRegex
Replace assertRaisesRegex with pytest.raises
(PT027)
scripts/test_gen_spec_source.py
[warning] 124-124: Use pytest.raises instead of unittest-style assertRaisesRegex
Replace assertRaisesRegex with pytest.raises
(PT027)
scripts/validate_manifest.py
[warning] 91-91: Avoid specifying long messages outside the exception class
(TRY003)
🔍 Remote MCP GitHub Copilot
Relevant review context
- PR
#82adds fork metadata only to the plugin build feeder; it does not add an active fork entry.validate_manifest()enforces the new invariants for manifest-driven flows. - The companion registry PR
#66independently enforces thatnuman-maintainedspecs contain a valid HTTP(S)source.upstream, rejects upstream values identifying the same repository assource.git, and rejectssource.upstreamfor non-numan-maintainedpackages. build_spec()only enters fork validation whenupstream_repois truthy. Therefore, a directbuild_spec()call withowner: "numan-maintained"and a missing or blankupstream_repodoes not fail locally, although manifest validation and registry intake reject it.build_spec()also does not validate theowner/nameformat or URL safety itself; those checks exist only invalidate_manifest(). This is weaker than the PR’s stated defense-in-depth behavior for direct callers.- PR
#80also modifiesvalidate_manifest.pyandgen_spec.py, so stacked-PR ordering or merge conflict resolution should be checked before approving.
🔇 Additional comments (4)
scripts/validate_manifest.py (1)
14-14: LGTM!Also applies to: 72-95, 132-132
scripts/test_validate_manifest.py (1)
103-141: LGTM!scripts/gen_spec.py (1)
171-181: LGTM!scripts/test_gen_spec_source.py (1)
67-100: LGTM!Also applies to: 101-130, 132-159
Call the shared validate_upstream_repo helper before emitting fork provenance, distinguish None from blank values, and drop duplicate owner/self-ref checks. Cover blank, malformed, absent, and wrong-owner cases directly through build_spec. Co-authored-by: Cursor <cursoragent@cursor.com>
There was a problem hiding this comment.
Pull request overview
Adds manifest + spec “fork identity” metadata (upstream_repo → emitted as source.upstream) as groundwork for the P4 selective fork policy, along with validation and tests so downstream intake (numan-registry) can reliably attribute forks without actually introducing any forked entries yet.
Changes:
scripts/validate_manifest.py: addsupstream_repovalidation, including “onlynuman-maintainedmay set it” and “numan-maintainedrequires it”.scripts/gen_spec.py: whenupstream_repois present, emitssource.upstreamand appends a fork attribution note to the spec description.- Updates manifest schema notes and adds unit tests covering the new validation/spec behavior.
Reviewed changes
Copilot reviewed 5 out of 5 changed files in this pull request and generated 2 comments.
Show a summary per file
| File | Description |
|---|---|
| scripts/validate_manifest.py | Adds upstream_repo invariants and integrates them into manifest validation. |
| scripts/test_validate_manifest.py | Adds unit tests for upstream_repo validation rules and malformed cases. |
| scripts/gen_spec.py | Emits source.upstream + fork attribution note when generating specs for fork entries. |
| scripts/test_gen_spec_source.py | Adds tests for fork spec emission and self-referential upstream rejection. |
| manifest.json | Documents upstream_repo in schema_notes and links to ADR 0001 for policy context. |
💡 Configure MCP servers for context-aware, tailored reviews. Learn more in the docs.
Co-authored-by: Copilot Autofix powered by AI <175728472+Copilot@users.noreply.github.com>
Resolves conflicts between the commit-snapshot intake mode (PR #80) and the fork-identity fields added in #82: manifest.json schema_notes keeps both new keys, gen_spec.py's build_spec combines intake_mode-derived versioning with upstream_repo fork attribution, validate_manifest.py's validate_active_entry now calls both validate_intake_fields and validate_upstream_repo, and the test files keep both new test suites. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Summary
Tooling-only groundwork for the selective fork policy (P4). Does not fork anything — see numan-registry PR (companion to this one) and
docs/adr/0001-...innumanfor why real forks are explicitly out of scope here.validate_manifest.py: optionalupstream_repofield (owner/nameof the original upstream). Requiresowner == "numan-maintained"on any entry that sets it — a fork manifest entry can't claim the original author's identity.gen_spec.py: whenupstream_repois present, emitssource.upstreamin the generated spec (consumed bynuman-registry'sadd-package.py, which now requires it forowner: "numan-maintained") and appends a fork-attribution note to the description.manifest.json:schema_notes.upstream_repodocuments the field and points at ADR 0001 for the eligibility/stewardship requirements this field doesn't itself enforce.Test plan
python -m pytest scripts/— 47 passedpython scripts/validate_manifest.py --manifest manifest.json— OK, 22 active plugins, unaffectedupstream_reporequiresnuman-maintainedowner / accepted with it / rejects blank,gen_spec.pyemitssource.upstream+ description note for fork entries, omits both for normal entriesRef:
numan/docs/plans/2026-08-09-intake-process-reform.md(P4), numan PR #113.🤖 Generated with Claude Code
Summary by cubic
Adds fork identity support for P4 selective forks and hardens manifest/spec validation, including
source.upstreamand a fork note for validnuman-maintainedforks. Tooling-only; no forks created.New Features
upstream_repofor ownernuman-maintained; enforce non-emptyowner/name; reject values equal torepo.source.upstreamand append a fork-attribution note; omit both for non-forks (needed bynuman-registry).schema_notes.upstream_repowith ADR link.Bug Fixes
build_specvalidatesupstream_repovia the shared helper, rejecting blank, malformed, wrong-owner, or self-referential values before emitting provenance.Written for commit dcafab1. Summary will update on new commits.