Skip to content

Add cmd:: unit tests and CI coverage job - #120

Merged
tonythethompson merged 7 commits into
masterfrom
coverage-cmd-tests
Aug 11, 2026
Merged

Add cmd:: unit tests and CI coverage job#120
tonythethompson merged 7 commits into
masterfrom
coverage-cmd-tests

Conversation

@tonythethompson

@tonythethompson tonythethompson commented Aug 10, 2026

Copy link
Copy Markdown
Collaborator

Summary

  • Adds #[cfg(test)] unit tests for previously-weak cmd:: entry points: cmd::list (0% -> 99%), cmd::nu_pin_offer (0% -> 71%), cmd::registry (34% -> 82%, add/remove/list, no network), cmd::snapshot (26% -> 73%, list/inspect/short_hash), install::download's local file-path copy branch (19% -> 42%)
  • Adds tests for config.rs (62% -> 90%), core/nu_version.rs (73% -> 89%), cmd::remove (66% -> 93%, including a full happy-path removal), cmd::search (70% -> 91%, execute() end-to-end via a fixture registry), cmd::nupm (61% -> 80%, argument-validation bails plus status/inspect --all happy paths)
  • util::stdio_redirect.rs's remaining gap is the Windows-only code path, not exercisable on Linux CI — left as-is
  • install/transaction.rs, cmd/setup.rs, cmd/update.rs, nu/bootstrap.rs remain below-average (see below) — their gaps sit inside large, monolithic functions that need the same heavy fixture machinery tests/install_test.rs already builds for install_package, not a quick unit-test addition. Flagged as a follow-up rather than attempted here.
  • Adds a coverage job to ci.yml using cargo-llvm-cov — informational only, reports to the job summary, no --fail-under-lines gate

Workspace line coverage: 81.3% -> 83.9%

Test plan

  • cargo test --lib — 757 tests, all green
  • cargo fmt --all -- --check — clean
  • cargo clippy -- -D warnings — clean

…er; add CI coverage job

Adds in-process #[cfg(test)] coverage for previously-0%/low-coverage cmd
entry points: cmd::list (0% -> 99%), cmd::nu_pin_offer (0% -> 71%),
cmd::registry (34% -> 82%, add/remove/list, no network), cmd::snapshot
(26% -> 73%, list/inspect/short_hash), and install::download's local
file-path copy branch (19% -> 42%).

Adds a coverage job to ci.yml using cargo-llvm-cov (informational only,
no fail-under-lines threshold), reporting to the job summary.

@sourcery-ai sourcery-ai Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Sorry @tonythethompson, you have reached your weekly rate limit of 500000 diff characters.

Please try again later or upgrade to continue using Sourcery

@coderabbitai

coderabbitai Bot commented Aug 10, 2026

Copy link
Copy Markdown
Contributor

Review Change Stack

Warning

Review limit reached

@tonythethompson, you've reached your PR review limit, so we couldn't start this review.

Next review available in: 3 minutes

You've used all free OSS reviews for now. Wait for the free limit to reset to keep reviewing this public repository.

How can I continue?

After more reviews become available, a review can be triggered using the @coderabbitai review command as a PR comment. Alternatively, push new commits to this PR.

To avoid repeated limits, reduce automatic review volume by pausing incremental auto-reviews earlier, using label-based review opt-in, excluding WIP or generated PR titles, or requesting reviews manually when the PR is ready. If your team needs uninterrupted high-volume reviews, an organization admin can enable usage-based reviews.

How do review limits work?

CodeRabbit enforces per-developer PR review limits for each organization. Most developers receive the normal plan review availability.

For paid Pro and Pro+ PR reviews, CodeRabbit uses adaptive limits for sustained high-volume activity. When a developer's recent PR review activity reaches the 95th percentile or higher among CodeRabbit users, additional reviews become available more gradually as earlier reviews age out of the rolling window.

Please refer docs for additional details.

Review details
⚙️ Run configuration

Configuration used: Organization UI

Review profile: ASSERTIVE

Plan: Pro Plus

Run ID: 4ad776e7-8ad4-4371-9269-aea206518986

📥 Commits

Reviewing files that changed from the base of the PR and between 39d55e5 and 0d442ce.

📒 Files selected for processing (4)
  • .github/workflows/ci.yml
  • src/cmd/nupm.rs
  • src/core/nu_version.rs
  • tests/doctor_test.rs
📝 Walkthrough

Walkthrough

The pull request adds Ubuntu workspace coverage reporting, injectable output handling for several commands, validation fixes for Nu versions and local downloads, test environment restoration, and expanded tests for command behavior and persisted state.

Changes

Command output and state flows

Layer / File(s) Summary
Injectable command output and state flows
src/cmd/list.rs, src/cmd/registry.rs, src/cmd/search.rs, src/cmd/snapshot.rs, src/cmd/remove.rs
Commands write output through injected writers. Tests cover listings, registry operations, searches, snapshots, and package removal.

Validation and test isolation

Layer / File(s) Summary
Configuration, version, and download validation
src/config.rs, src/core/nu_version.rs, src/install/download.rs, Cargo.toml
Tests cover configuration persistence, Nu version constraints, cached versions, and plain or file:// download sources.
Package-management command validation
src/cmd/nu_pin_offer.rs, src/cmd/nupm.rs
Tests cover pin confirmation outcomes, argument validation, status scans, and inspect-all reporting.
Environment restoration for tests
src/util/test_paths.rs, src/cmd/doctor.rs
NumanRootRestoreGuard restores NUMAN_ROOT, and doctor repair tests use the guard.

Coverage pipeline

Layer / File(s) Summary
Workspace coverage reporting
.github/workflows/ci.yml, .gitignore
CI runs cargo-llvm-cov and publishes the workspace report. .gitignore excludes *.profraw files.

Estimated code review effort: 4 (Complex) | ~60 minutes

Possibly related PRs

Suggested reviewers: greptile-apps

🚥 Pre-merge checks | ✅ 8
✅ Passed checks (8 passed)
Check name Status Explanation
Title check ✅ Passed The title clearly summarizes the main changes: added command unit tests and an informational CI coverage job.
Description check ✅ Passed The description directly explains the added tests, coverage improvements, deferred gaps, CI coverage job, and validation results.
Docstring Coverage ✅ Passed Docstring coverage is 70.00% which is sufficient. The required threshold is 60.00%.
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.
Pipeline Stage Enum Ordering ✅ Passed The repository contains no SessionWorkflowStage enum, member references, or related comparisons; this pipeline-order check is not applicable to the pull request.
Gpu/Cpu Runtime Boundary ✅ Passed The PR modifies Rust source, Cargo files, and CI only. No inference file or managed CPU/GPU requirements file is changed, so the runtime-boundary checks do not apply.
Managed Host Restart Safety ✅ Passed The PR changes only coverage/tests, configuration, download, and CI files; none of the named managed-host components or restart/readiness symbols are modified.
✨ Finishing Touches
📝 Generate docstrings
  • Create stacked PR
  • Commit on current branch
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch coverage-cmd-tests
✨ Simplify code
  • Create PR with simplified code
  • Commit simplified code in branch coverage-cmd-tests

Warning

Review ran into problems

🔥 Problems

Linked repositories: Public OSS repositories can only analyze public repositories installed in this organization. Analyzed tonythethompson/QuickShell, tonythethompson/numan, tonythethompson/dependency-chain-substrate, skipped Trackdubllc/Trackdub.


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.

❤️ Share

Comment @coderabbitai help to get the list of available commands.

@qodo-code-review

Copy link
Copy Markdown
Contributor

PR Summary by Qodo

Add unit tests for cmd entrypoints and a CI coverage summary job

🧪 Tests ⚙️ Configuration changes 🕐 20-40 Minutes

Grey Divider

AI Description

• Add targeted unit tests for cmd::* entrypoints and local-file download paths.
• Improve coverage for previously low/untested branches without introducing network dependencies.
• Add an informational cargo-llvm-cov coverage job to CI and ignore raw coverage artifacts.
Diagram

graph TD
  A["GitHub Actions"] --> B["ci.yml"] --> C["Coverage job"] --> D["cargo llvm-cov"] --> E("Unit tests")
  E --> F("cmd::* tests")
  E --> G("install::download tests")
  F --> H[("Temp config/state")]
  subgraph Legend
    direction LR
    _svc["CI/Tooling"] ~~~ _mod("Test/module") ~~~ _db[("On-disk state")]
  end
Loading
High-Level Assessment

The following are alternative approaches to this PR:

1. Add a coverage gate (fail-under-lines)
  • ➕ Prevents coverage regressions over time
  • ➕ Creates an explicit quality bar for new code paths
  • ➖ Can introduce churn/noise when refactors move uncovered code
  • ➖ Requires choosing and maintaining a realistic threshold
2. Integration/CLI tests instead of unit tests
  • ➕ Validates real user-facing behavior (stdout/stderr, exit codes, arg parsing)
  • ➕ Catches wiring issues between cmd layer and underlying state/config
  • ➖ Slower and harder to keep hermetic (filesystem/process concerns)
  • ➖ More brittle output assertions unless snapshots/golden files are used
3. Upload coverage to an external service/artifact
  • ➕ Historical tracking and diff-based reporting per PR
  • ➕ Easier to spot coverage hotspots and trends
  • ➖ Adds external dependency/credentials management
  • ➖ More CI complexity than an informational summary

Recommendation: Current approach (hermetic unit tests + informational CI summary) is a good low-friction step: it raises confidence without adding flaky network dependencies or blocking merges. Consider introducing a soft/hard coverage threshold later once the baseline stabilizes, or adding a small set of CLI-level integration tests for critical end-to-end flows.

Files changed (7) +448 / -0

Tests (5) +420 / -0
list.rsAdd unit tests for list command output paths +93/-0

Add unit tests for list command output paths

• Adds '#[cfg(test)]' coverage for 'cmd::list::execute' across empty lockfiles, single package, and mixed active/inactive package scenarios. Tests build minimal lockfile entries and required Nu state fixtures in a temp directory.

src/cmd/list.rs

nu_pin_offer.rsAdd unit tests for managed Nu pin offer interactions +68/-0

Add unit tests for managed Nu pin offer interactions

• Adds tests covering accept/decline/invalid input behavior, plus a non-interactive short-circuit that must not read input. The accept-path test uses a malformed pin to fail before any network work, keeping the test deterministic.

src/cmd/nu_pin_offer.rs

registry.rsAdd unit tests for registry add/remove/list and package listing +133/-0

Add unit tests for registry add/remove/list and package listing

• Expands the existing test module to cover listing registries (empty and populated), adding registries (including trust key persistence and duplicate rejection), removing registries (including cached index cleanup), and listing packages from an on-disk index without network access.

src/cmd/registry.rs

snapshot.rsAdd unit tests for snapshot listing/inspect and hash shortening +96/-0

Add unit tests for snapshot listing/inspect and hash shortening

• Adds tests for 'short_hash', listing snapshots when empty and after creating a committed snapshot, and inspecting snapshot details including payload file presence. Tests create minimal state and lockfile/payload fixtures in a temp directory.

src/cmd/snapshot.rs

download.rsAdd unit tests for local path and file:// download copies +30/-0

Add unit tests for local path and file:// download copies

• Adds tests ensuring 'download_file' copies from a plain local path and from a 'file://' URL into the destination, including nested destination directory creation expectations.

src/install/download.rs

Other (2) +28 / -0
ci.ymlAdd informational cargo-llvm-cov coverage job +25/-0

Add informational cargo-llvm-cov coverage job

• Introduces a new 'coverage' CI job that installs 'cargo-llvm-cov' and 'llvm-tools-preview', then posts a workspace summary to the GitHub job summary. The job is explicitly non-blocking (no fail-under threshold).

.github/workflows/ci.yml

.gitignoreIgnore raw coverage output artifacts +3/-0

Ignore raw coverage output artifacts

• Adds '*.profraw' to '.gitignore' to prevent llvm coverage raw profiles from being committed.

.gitignore

@greptile-apps

greptile-apps Bot commented Aug 10, 2026

Copy link
Copy Markdown
Contributor

Greptile Summary

Adds unit-test coverage across command, configuration, version-resolution, download, and snapshot paths, plus an informational CI coverage job.

  • Refactors command output through injectable writers for deterministic testing.
  • Adds local-path and file:// download coverage using the url crate.
  • Serializes tests that mutate the process-global NUMAN_ROOT environment variable.
  • Makes malformed Nu-version comparator bounds fail closed and fixes exact zero-major version matching.

Confidence Score: 5/5

The PR appears safe to merge.

No blocking failure remains.

Important Files Changed

Filename Overview
.github/workflows/ci.yml Adds a non-gating cargo-llvm-cov job that publishes its summary to the GitHub Actions job summary.
src/cmd/list.rs Routes list output through an injectable writer and adds empty, installed, and activated package tests.
src/cmd/registry.rs Makes registry listing output injectable and adds coverage for listing, adding, removing, trust keys, and cached indexes.
src/cmd/search.rs Makes search output injectable and adds fixture-backed end-to-end coverage for empty, matching, and incompatible results.
src/cmd/snapshot.rs Routes snapshot list and inspect output through writers and adds snapshot creation, listing, inspection, and payload verification tests.
src/core/nu_version.rs Makes malformed comparator bounds fail closed and correctly distinguishes exact zero-major versions from minor wildcards.
src/install/download.rs Parses file URLs with the url crate and tests both plain local paths and platform-appropriate file URLs.
src/util/test_paths.rs Adds an RAII guard and mutex for restoring and serializing tests that mutate NUMAN_ROOT.

Reviews (7): Last reviewed commit: "Address remaining bot review findings" | Re-trigger Greptile

greptile-apps[bot]
greptile-apps Bot previously approved these changes Aug 10, 2026

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: 189e20c555

ℹ️ 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".

Comment thread .github/workflows/ci.yml Outdated
@qodo-code-review

qodo-code-review Bot commented Aug 10, 2026

Copy link
Copy Markdown
Contributor

Code Review by Qodo

🐞 Bugs (0) 📘 Rule violations (0) 📜 Skill insights (0)

Grey Divider


Remediation recommended

1. Coverage job not locked ✓ Resolved 🐞 Bug ☼ Reliability
Description
The new Coverage workflow runs cargo llvm-cov without --locked, so dependency resolution can
diverge from the rest of CI (MSRV/package) and can introduce non-reproducible coverage results or
lockfile-related flakes. This inconsistency is introduced by the new job’s command line.
Code

.github/workflows/ci.yml[R79-82]

+            echo "### Coverage summary"
+            echo '```'
+            cargo llvm-cov --workspace --summary-only
+            echo '```'
Relevance

●●● Strong

Repo frequently uses/adjusts CI for reproducibility; adding --locked matches existing MSRV/package
patterns.

PR-#13

ⓘ Recommendations generated based on similar findings in past PRs

Evidence
The coverage job’s cargo llvm-cov invocation omits --locked, while other jobs in the same
workflow use --locked for reproducibility (MSRV check and cargo package).

.github/workflows/ci.yml[60-83]
.github/workflows/ci.yml[171-196]

Agent prompt
The issue below was found during a code review. Follow the provided context and guidance below and implement a solution

### Issue description
The Coverage job runs `cargo llvm-cov` without `--locked`, which can allow Cargo to resolve/update dependencies differently than the rest of CI.

### Issue Context
Other CI jobs in the same workflow explicitly use `--locked`, so Coverage should match to keep results consistent and reduce flakes.

### Fix Focus Areas
- .github/workflows/ci.yml[60-83]

ⓘ Copy this prompt and use it to remediate the issue with your preferred AI generation tools


2. File URL parsing untested ✓ Resolved 🐞 Bug ≡ Correctness
Description
The new download_file_copies_file_url test builds a file:// string via `format!("file://{}",
src.display()), but download_file implements file://` handling by stripping the prefix and
treating the remainder as a raw path, not a URL. As a result, a file:///C:/... input would be
stripped to /C:/... (leading slash preserved) and is not covered by tests, so Windows file-URL
compatibility is not actually validated.
Code

src/install/download.rs[R103-106]

+        let dest = dir.path().join("dest.txt");
+        let url = format!("file://{}", src.display());
+
+        download_file(&url, &dest).unwrap();
Relevance

●● Moderate

Windows file:// semantics are subtle; no clear repo precedent on file-URL parsing/tests, so
acceptance uncertain.

ⓘ Recommendations generated based on similar findings in past PRs

Evidence
The implementation handles file URLs by stripping the literal file:// prefix and converting the
remainder directly to a PathBuf, and the test constructs the URL using file://{src.display()};
together, this means the test only validates this specific formatting and does not validate
file:///... handling on Windows (which would keep a leading /).

src/install/download.rs[7-19]
src/install/download.rs[98-109]

Agent prompt
The issue below was found during a code review. Follow the provided context and guidance below and implement a solution

### Issue description
`download_file` treats `file://` inputs by `strip_prefix("file://")` and `PathBuf::from(...)`, which is not robust for standard file URL shapes (notably on Windows where `file:///C:/...` becomes `/C:/...`). The new unit test also constructs `file://` inputs via `Path::display()`, so it doesn’t cover the more standard forms that callers may pass.

### Issue Context
Because the PR’s goal is to add coverage for the local-copy branches, the test should reflect real-world `file://` inputs and the implementation should decode/convert file URLs reliably.

### Fix Focus Areas
- src/install/download.rs[7-19]
- src/install/download.rs[98-109]

ⓘ Copy this prompt and use it to remediate the issue with your preferred AI generation tools


Grey Divider

Context used
✅ Compliance rules (platform): 31 rules
✅ REVIEW.md
Review mode: ⚖️ Balanced: The PR spans multiple independent test modules plus a CI workflow, so it has meaningful correctness and configuration risk, but is not dense enough in production logic to justify extended review.

Grey Divider

Tip of the day
💡 Did you know, you can group findings by type and pick your Finding display, from Minimal to Full

More tips ↗ | Customize Qodo ↗ | Qodo docs ↗

Grey Divider

Qodo Logo

Comment thread .github/workflows/ci.yml
Comment thread src/install/download.rs
@qodo-code-review

Copy link
Copy Markdown
Contributor

Qodo Fixer

No findings are within the configured fix scope. To change which findings are fixed, adjust the setting on your Qodo configuration page.

- config.rs: load/save round trip, missing-file default, malformed TOML,
  serde defaults, NUMAN_ROOT env override
- core/nu_version.rs: parse() error branches, matches_constraint's >, <,
  and =exact-version operators, from_paths_or_detect cached-version path
- cmd::remove: full execute_with_tty happy path (lockfile entry removed,
  payload deleted) on top of the existing guard-path tests

util::stdio_redirect.rs's remaining gap is the Windows-only code path,
not exercisable on this platform — left as-is.
greptile-apps[bot]
greptile-apps Bot previously approved these changes Aug 10, 2026
- cmd::search: 70% -> 91% (execute() end-to-end via a fixture registry
  index, covering the no-match/found/--all paths)
- cmd::nupm: 61% -> 80% (diff/import/inspect argument-validation bails,
  status/inspect --all happy paths via the nupm-home-layout fixture)
greptile-apps[bot]
greptile-apps Bot previously approved these changes Aug 10, 2026

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 11

🤖 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 @.github/workflows/ci.yml:
- Line 64: Update the actions/checkout step in the coverage job to set
persist-credentials to false, while preserving the existing pinned action
reference and version comment.
- Line 75: Update the coverage-gating comment in the CI workflow to clarify that
although no line-coverage threshold is enforced, a nonzero exit from cargo
llvm-cov --workspace --summary-only still fails the Bash step and gates the
build.
- Line 81: Update the cargo llvm-cov coverage command in the CI workflow to
include the --locked flag, ensuring it uses the committed Cargo.lock dependency
graph without modifying it.

In `@src/cmd/list.rs`:
- Around line 86-135: The list command tests in src/cmd/list.rs lines 86-135
only check successful execution; capture stdout in execute_empty_lockfile,
execute_one_package, and execute_multiple_packages_with_one_active, then assert
the empty message, package IDs, and correct activated or installed status. In
src/cmd/snapshot.rs lines 337-387, capture stdout in the affected snapshot tests
and assert the empty-list message, snapshot metadata, payload provenance, and
hash formatting as applicable.

In `@src/cmd/nu_pin_offer.rs`:
- Around line 141-163: Strengthen the tests around
offer_managed_nu_pin_with_interaction by tracking whether input is read and
whether installation/refresh occurs. Add or use an injectable install/refresh
seam, or assert the temporary root remains unchanged, so
decline_returns_false_without_installing verifies no installation and
invalid_input_is_treated_as_decline verifies invalid input follows the same
rejection path.
- Around line 125-138: Strengthen
accept_proceeds_to_install_and_fails_hermetically_on_bad_pin by asserting the
error chain includes “Failed to normalize requested version 'not-a-version'”.
Preserve the existing outer install-failure assertion; alternatively, use the
injectable installer seam to verify installation is never invoked.

In `@src/cmd/nupm.rs`:
- Around line 483-498: Update inspect_all_without_nupm_home_bails to assert that
execute returns the expected failure result instead of discarding it. Remove the
narrative comment after adding the assertion, while preserving the existing
nonexistent nupm_home setup.

In `@src/cmd/registry.rs`:
- Around line 270-290: Update the command tests to capture user-visible output
at the command boundary or through an injectable writer, then assert the
expected results: in src/cmd/registry.rs lines 270-290, verify the
empty-registry message and configured registry name, URL, and enabled state; in
src/cmd/registry.rs lines 341-391, verify package ID, version, type, and
description; in src/cmd/search.rs lines 445-476, verify the no-match message,
matching package row, and incompatible --all result; and in src/cmd/nupm.rs
lines 610-637, verify the configured scan summary and inspection candidates.
Keep the existing command return checks while adding assertions for relevant
failure and behavior paths.

In `@src/config.rs`:
- Around line 220-227: Update the resolve_root test around
resolve_root_prefers_numan_root_env_var to acquire the shared test-only
environment lock before changing NUMAN_ROOT, and use the established RAII
restore guard to reinstate its prior value on every exit path. Ensure all tests
that mutate NUMAN_ROOT use the same lock and guard so environment changes cannot
overlap.

In `@src/core/nu_version.rs`:
- Around line 237-256: Update NuVersion::matches_constraint to parse inclusive
upper bounds by removing the <= prefix directly, and return false whenever a
constraint bound cannot be parsed instead of silently ignoring it. Revise
matches_constraint_ignores_unparseable_bound to assert failure and add coverage
that <=0.113.0 does not match 0.113.1.

In `@src/install/download.rs`:
- Around line 98-109: Update download_file to convert file URIs using
platform-aware URI-to-path handling rather than manually stripping the file://
prefix, ensuring standard Windows URIs such as file:///C:/... resolve correctly.
Extend download_file_copies_file_url with a Windows-specific test covering the
file:///C:/... form while preserving existing file-copy behavior.
🪄 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: 4818a503-279f-457a-86db-51f5c8d6689f

📥 Commits

Reviewing files that changed from the base of the PR and between ea0b785 and 0bafa4c.

📒 Files selected for processing (12)
  • .github/workflows/ci.yml
  • .gitignore
  • src/cmd/list.rs
  • src/cmd/nu_pin_offer.rs
  • src/cmd/nupm.rs
  • src/cmd/registry.rs
  • src/cmd/remove.rs
  • src/cmd/search.rs
  • src/cmd/snapshot.rs
  • src/config.rs
  • src/core/nu_version.rs
  • src/install/download.rs
🔗 Linked repositories identified

CodeRabbit considers these linked repositories for cross-repo context during reviews:

  • tonythethompson/QuickShell (manual)
  • tonythethompson/numan (manual)
  • tonythethompson/dependency-chain-substrate (manual)
📜 Review details
⏰ Context from checks skipped due to timeout. (1)
  • GitHub Check: Greptile Review
🧰 Additional context used
📓 Path-based instructions (12)
!**/.env,!**/credentials.json,!**/*.pem

📄 CodeRabbit inference engine (CLAUDE.md)

Do not commit files that appear to contain secrets, including .env, credentials.json, and PEM files; warn before doing so even if explicitly requested.

Files:

  • .gitignore
  • src/cmd/remove.rs
  • src/config.rs
  • src/cmd/search.rs
  • src/cmd/registry.rs
  • .github/workflows/ci.yml
  • src/core/nu_version.rs
  • src/cmd/nu_pin_offer.rs
  • src/install/download.rs
  • src/cmd/nupm.rs
  • src/cmd/snapshot.rs
  • src/cmd/list.rs
**/*

📄 CodeRabbit inference engine (CLAUDE.md)

**/*: Use Serena's semantic, symbol-aware tools as the primary tools for reading and editing code; use built-in Read, Glob, Grep, and Edit only under the stated exceptions.
Before editing a code file, inspect its symbol overview, read the specific symbols being changed, and edit them with Serena's symbol-aware tools.
Understand the existing code before changing it and make the smallest change that satisfies the request; avoid unrelated cleanup, premature abstractions, unnecessary error handling, feature flags, and compatibility shims.
Prefer editing existing files over creating new ones, and never create Markdown or README files unless explicitly requested.
For exploratory questions, provide a 2–3 sentence recommendation with the main tradeoff and do not implement 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.
Address 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, force-pushing, modifying CI/CD, posting externally, or uploading content.
When blocked, investigate the root cause instead of bypassing it with --no-verify, --force, or deletion; investigate unfamiliar files, branches, and configuration before deleting them.
Only commit when explicitly asked; do not proactively update git configuration or push changes.
Do not skip Git hooks unless explicitly asked; if a pre-commit hook fails, fix the issue, re-stage, and create a new commit rather than amending.
Stage files by name rather than using git add -A or git add ., to avoid accidentally including secrets or large binaries.
Use a HEREDOC for commit messages, and add co-author attribution only when the user explicitly requests the exact trailer.
Do not force-pus...

Files:

  • src/cmd/remove.rs
  • src/config.rs
  • src/cmd/search.rs
  • src/cmd/registry.rs
  • src/core/nu_version.rs
  • src/cmd/nu_pin_offer.rs
  • src/install/download.rs
  • src/cmd/nupm.rs
  • src/cmd/snapshot.rs
  • src/cmd/list.rs
**/*.{js,jsx,ts,tsx,py,java,go,rs,rb,php,c,cpp,h,hpp,cs,swift,kt,kts}

📄 CodeRabbit inference engine (CLAUDE.md)

Add comments only when the WHY is non-obvious; do not narrate what the code does, reference the current task, or reference the PR in comments.

Files:

  • src/cmd/remove.rs
  • src/config.rs
  • src/cmd/search.rs
  • src/cmd/registry.rs
  • src/core/nu_version.rs
  • src/cmd/nu_pin_offer.rs
  • src/install/download.rs
  • src/cmd/nupm.rs
  • src/cmd/snapshot.rs
  • src/cmd/list.rs
**/*.rs

📄 CodeRabbit inference engine (CONTRIBUTING.md)

**/*.rs: Use the Rust 2021 edition.
Use anyhow::Result with .context(...) in application code; use thiserror for library error types that callers match on.
Use clap derive macros for CLI definitions.
Use serde with serde_json or toml for serialization.
Function parameters must use &Path, not &PathBuf.
Library code must not panic; error paths should return anyhow::Result with context where appropriate.
Add or update tests for behavior changes, including relevant failure paths.
New mutating code paths must acquire the mutation lock via acquire_mutation_lock(root) and snapshot the lockfile before writes.
Lockfile, journal, and state-file JSON writes must use write_json_atomic.
numan install must write only to $NUMAN_ROOT; it must not invoke Nu or register plugins/autoloads.
Only activate and deactivate may modify Nu integration state.
Treat the lockfile as the authoritative source of truth; derived projections such as autoload state must not be authoritative.
Install payloads under versioned, content-addressed paths and never overwrite them in place.
Never overwrite foreign autoload files; respect OWNERSHIP_MARKER.
Pass plugin paths through environment variables only; do not use runtime interpolation in Nu program strings.

**/*.rs: Use &Path rather than &PathBuf in Rust function parameters.
Use anyhow::Result for application code, thiserror for library errors, and add context with .context(...) or ?.
Never panic in library code; return errors instead.
Test-first development is expected: write a failing test, implement the change, then verify it passes.
Format and lint Rust code with cargo fmt --check and cargo clippy -- -D warnings; no warnings are permitted.

**/*.rs: All CI gates must pass: cargo test, cargo clippy -- -D warnings, cargo fmt --check, MSRV cargo +1.88 check --locked --all-targets, cargo package --locked, cargo deny, and ignored real-Nu acceptance tests.
numan install must not invoke...

Files:

  • src/cmd/remove.rs
  • src/config.rs
  • src/cmd/search.rs
  • src/cmd/registry.rs
  • src/core/nu_version.rs
  • src/cmd/nu_pin_offer.rs
  • src/install/download.rs
  • src/cmd/nupm.rs
  • src/cmd/snapshot.rs
  • src/cmd/list.rs
**/*.{rs,toml}

📄 CodeRabbit inference engine (CONTRIBUTING.md)

Run and keep cargo fmt/rustfmt clean, and ensure cargo clippy -- -D warnings passes.

Files:

  • src/cmd/remove.rs
  • src/config.rs
  • src/cmd/search.rs
  • src/cmd/registry.rs
  • src/core/nu_version.rs
  • src/cmd/nu_pin_offer.rs
  • src/install/download.rs
  • src/cmd/nupm.rs
  • src/cmd/snapshot.rs
  • src/cmd/list.rs
**/*.{rs,nu}

📄 CodeRabbit inference engine (CONTRIBUTING.md)

**/*.{rs,nu}: Real-Nu acceptance tests must be marked #[ignore] and should be run when changes affect activation or nupm import; unit tests must not spawn real nu and should use injectable seams such as FakeCandidateRunner or registrars.
The nupm integration must be read-only toward NUPM_HOME, must not execute build.nu, and must not perform bidirectional synchronization.

Files:

  • src/cmd/remove.rs
  • src/config.rs
  • src/cmd/search.rs
  • src/cmd/registry.rs
  • src/core/nu_version.rs
  • src/cmd/nu_pin_offer.rs
  • src/install/download.rs
  • src/cmd/nupm.rs
  • src/cmd/snapshot.rs
  • src/cmd/list.rs
**/*.{rs,md}

📄 CodeRabbit inference engine (CONTRIBUTING.md)

Match existing naming, module layout, and documentation level in the file being edited; update AGENTS.md, docs/, or command help when structure, conventions, or user-visible behavior changes.

Files:

  • src/cmd/remove.rs
  • src/config.rs
  • src/cmd/search.rs
  • src/cmd/registry.rs
  • src/core/nu_version.rs
  • src/cmd/nu_pin_offer.rs
  • src/install/download.rs
  • src/cmd/nupm.rs
  • src/cmd/snapshot.rs
  • src/cmd/list.rs
**/*.{rs,md,toml}

📄 CodeRabbit inference engine (CONTRIBUTING.md)

Use the repository's established serialization and module conventions rather than introducing unrelated refactors.

Files:

  • src/cmd/remove.rs
  • src/config.rs
  • src/cmd/search.rs
  • src/cmd/registry.rs
  • src/core/nu_version.rs
  • src/cmd/nu_pin_offer.rs
  • src/install/download.rs
  • src/cmd/nupm.rs
  • src/cmd/snapshot.rs
  • src/cmd/list.rs
src/**/*.rs

📄 CodeRabbit inference engine (AGENTS.md)

Use compile-time #[cfg(target_env)] platform detection rather than std::env::consts.

Files:

  • src/cmd/remove.rs
  • src/config.rs
  • src/cmd/search.rs
  • src/cmd/registry.rs
  • src/core/nu_version.rs
  • src/cmd/nu_pin_offer.rs
  • src/install/download.rs
  • src/cmd/nupm.rs
  • src/cmd/snapshot.rs
  • src/cmd/list.rs
src/cmd/*.rs

📄 CodeRabbit inference engine (AGENTS.md)

Create a snapshot before mutations performed by install, update, remove, activate, deactivate, nupm import, and init --refresh.

Files:

  • src/cmd/remove.rs
  • src/cmd/search.rs
  • src/cmd/registry.rs
  • src/cmd/nu_pin_offer.rs
  • src/cmd/nupm.rs
  • src/cmd/snapshot.rs
  • src/cmd/list.rs
src/cmd/{activate,deactivate,update,remove,nupm,init}.rs

📄 CodeRabbit inference engine (AGENTS.md)

Acquire the root mutation lock before mutating managed state; the lock must serialize concurrent mutations and fail immediately on a second acquisition.

Files:

  • src/cmd/remove.rs
  • src/cmd/nupm.rs
src/install/**/*.rs

📄 CodeRabbit inference engine (AGENTS.md)

src/install/**/*.rs: Install operations must remain inert: they may write only to $NUMAN_ROOT and must not perform Nu integration.
Plugin binary artifacts must include a SHA256 value; the install transaction must bail when it is missing.
Never overwrite installed payloads; use the immutable path shape <root>/packages/<type>/<owner>/<name>/<version>-<sha8prefix>/.

Files:

  • src/install/download.rs
🪛 zizmor (1.29.0)
.github/workflows/ci.yml

[warning] 64-64: credential persistence through GitHub Actions artifacts (artipacked): does not set persist-credentials: false

(artipacked)


[error] 69-69: runtime artifacts potentially vulnerable to a cache poisoning attack (cache-poisoning): enables caching by default

(cache-poisoning)


[info] 65-65: action functionality is already included by the runner (superfluous-actions): use rustup and/or cargo in a script step

(superfluous-actions)

🔍 Remote MCP GitHub Copilot

Additional review context

  • PR #120 adds only tests, CI coverage reporting, and .gitignore changes; it does not alter production behavior. The PR reports +859 lines across 12 files.
  • CI coverage passed, along with Ubuntu/macOS tests, Clippy, formatting, MSRV, packaging, and acceptance checks. Windows tests and some analysis checks were still in progress; CodeRabbit status remained pending.
  • The coverage command uses cargo llvm-cov --workspace --summary-only without --locked, despite Cargo.lock being committed and other reproducibility-sensitive jobs using --locked. Automated review flagged this.
  • The job is described as informational, but a failing cargo llvm-cov command can still fail the job; omitting --fail-under-lines only disables the coverage threshold.
  • download_file handles file:// by stripping the prefix into a raw PathBuf; the added test covers the Unix-style construction but not standard Windows file:///C:/... URLs.
  • Several new command tests call functions and assert only success/non-panicking behavior without checking stdout contents, notably list, registry, search, and snapshot tests.
  • The new configuration test mutates the process-global NUMAN_ROOT; existing repository tests also modify that variable, so parallel-test isolation is worth checking.
🔇 Additional comments (9)
src/config.rs (1)

164-218: LGTM!

src/core/nu_version.rs (2)

217-235: LGTM!


258-281: LGTM!

src/install/download.rs (1)

86-96: LGTM!

src/cmd/list.rs (1)

45-84: LGTM!

src/cmd/remove.rs (1)

372-398: LGTM!

src/cmd/snapshot.rs (1)

290-335: LGTM!

src/cmd/nu_pin_offer.rs (1)

110-123: LGTM!

Also applies to: 165-175

.gitignore (1)

47-49: LGTM!

Comment thread .github/workflows/ci.yml
Comment thread .github/workflows/ci.yml Outdated
Comment thread .github/workflows/ci.yml Outdated
Comment thread src/cmd/list.rs
Comment thread src/cmd/nu_pin_offer.rs
Comment thread src/cmd/nupm.rs
Comment thread src/cmd/registry.rs Outdated
Comment thread src/config.rs
Comment thread src/core/nu_version.rs
Comment thread src/install/download.rs
resolve_root_prefers_numan_root_env_var (new in this PR) and doctor.rs's
two tests both mutate the process-global NUMAN_ROOT env var without
synchronization, in the same parallel cargo-test binary. Since
Config::resolve_root reads NUMAN_ROOT, a concurrently-running doctor.rs
test could overwrite it mid-test and make the new assertion read the
wrong tempdir — an intermittent, hard-to-reproduce CI failure.

Adds NumanRootRestoreGuard to util/test_paths.rs, mirroring the existing
PathRestoreGuard/HomeRestoreGuard pattern (a shared Mutex serializes
snapshot/restore across threads), and uses it at all three call sites.
As a side effect, doctor.rs's two tests now restore NUMAN_ROOT on drop
instead of leaking it into the rest of the test binary's process state.
greptile-apps[bot]
greptile-apps Bot previously approved these changes Aug 11, 2026
…ssertions

Real bug fix:
- NuVersion::matches_constraint's "<=" branch double-stripped the "="
  prefix (strip_prefix("<=") then strip_prefix('=') again), so any real
  "<=X.Y.Z" constraint silently matched everything — pre-existing on
  master, predates this PR. Also changed all operators to fail closed
  (return false) on an unparseable bound instead of silently ignoring
  it, matching the safety expectation for compatibility gating.

CI hardening:
- coverage job: add persist-credentials: false to checkout (matches
  the one other job in this file that handles a token), add --locked
  to cargo llvm-cov so it uses the committed Cargo.lock, and clarify
  the "informational only" comment (a nonzero cargo llvm-cov exit still
  fails the step; only the coverage threshold is not enforced).

download_file: replace manual file:// prefix stripping (which produced
an invalid path like "/C:/..." for Windows file:///C:/... URLs) with
url::Url::to_file_path(), which is platform-aware. url was already a
transitive dependency (via reqwest) — added directly, zero resolver
changes. Added a #[cfg(windows)] test for the file:///C:/... form.

Strengthened weak assertions (mostly "call it, assert it doesn't
panic" -> real content checks). Where the target function only wrote
to real stdout, added an internal `execute_to`/`out: &mut dyn Write`
seam mirroring the pattern nupm.rs already used, so tests can capture
output without touching the public API:
- cmd::list, cmd::snapshot (list/inspect), cmd::registry
  (list_registries/list_packages), cmd::search: capture stdout, assert
  package/snapshot/registry content instead of just Result::is_ok.
- cmd::nu_pin_offer: decline/invalid-input tests now assert nothing
  was written under root (proving install was never reached); the
  accept-with-bad-pin test now asserts the underlying normalization
  error is in the chain, not just the outer wrapper message.
- cmd::nupm: inspect_all_without_nupm_home_bails now asserts the
  actual validation error instead of discarding the result; the
  status/inspect-all fixture tests assert the real scan summary and
  candidate listing instead of non-empty/not-contains checks.

Skipped as stale (already fixed in a prior review pass on this PR):
config.rs's resolve_root_prefers_numan_root_env_var already uses
NumanRootRestoreGuard.
greptile-apps[bot]
greptile-apps Bot previously approved these changes Aug 11, 2026

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

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 `@src/core/nu_version.rs`:
- Around line 108-118: Update the exact-version handling in
NuVersion::matches_constraint so the legacy minor-only branch runs only when the
value has the “.x” suffix; route exact 0.x.y values such as “=0.113.1” through
parse_version and version_eq. Add assertions covering matches_constraint for
“=0.113.1” and rejecting “=0.113.2”.

In `@src/util/test_paths.rs`:
- Around line 134-146: Update the test around the NUMAN_ROOT mutation in
doctor_test to hold a NumanRootRestoreGuard for the entire test scope, ensuring
the environment snapshot, lock, and restoration cover all related operations;
alternatively remove the mutation if the test does not require it.
🪄 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: 0bcc61a4-7ebd-4875-a6e6-19e9274cfe98

📥 Commits

Reviewing files that changed from the base of the PR and between 0bafa4c and 39d55e5.

⛔ Files ignored due to path filters (1)
  • Cargo.lock is excluded by !**/*.lock
📒 Files selected for processing (13)
  • .github/workflows/ci.yml
  • Cargo.toml
  • src/cmd/doctor.rs
  • src/cmd/list.rs
  • src/cmd/nu_pin_offer.rs
  • src/cmd/nupm.rs
  • src/cmd/registry.rs
  • src/cmd/search.rs
  • src/cmd/snapshot.rs
  • src/config.rs
  • src/core/nu_version.rs
  • src/install/download.rs
  • src/util/test_paths.rs
🔗 Linked repositories identified

CodeRabbit considers these linked repositories for cross-repo context during reviews:

  • tonythethompson/QuickShell (manual)
  • tonythethompson/numan (manual)
  • tonythethompson/dependency-chain-substrate (manual)
📜 Review details
⏰ Context from checks skipped due to timeout. (5)
  • GitHub Check: Greptile Review
  • GitHub Check: Real-Nu acceptance (windows-latest)
  • GitHub Check: Test (windows-latest)
  • GitHub Check: Coverage
  • GitHub Check: Analyze (rust)
🧰 Additional context used
📓 Path-based instructions (12)
**/*

📄 CodeRabbit inference engine (CLAUDE.md)

**/*: Use Serena's semantic, symbol-aware tools as the primary tools for reading and editing code; use built-in Read, Glob, Grep, and Edit only under the stated exceptions.
Before editing a code file, inspect its symbol overview, read the specific symbols being changed, and edit them with Serena's symbol-aware tools.
Understand the existing code before changing it and make the smallest change that satisfies the request; avoid unrelated cleanup, premature abstractions, unnecessary error handling, feature flags, and compatibility shims.
Prefer editing existing files over creating new ones, and never create Markdown or README files unless explicitly requested.
For exploratory questions, provide a 2–3 sentence recommendation with the main tradeoff and do not implement 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.
Address 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, force-pushing, modifying CI/CD, posting externally, or uploading content.
When blocked, investigate the root cause instead of bypassing it with --no-verify, --force, or deletion; investigate unfamiliar files, branches, and configuration before deleting them.
Only commit when explicitly asked; do not proactively update git configuration or push changes.
Do not skip Git hooks unless explicitly asked; if a pre-commit hook fails, fix the issue, re-stage, and create a new commit rather than amending.
Stage files by name rather than using git add -A or git add ., to avoid accidentally including secrets or large binaries.
Use a HEREDOC for commit messages, and add co-author attribution only when the user explicitly requests the exact trailer.
Do not force-pus...

Files:

  • Cargo.toml
  • src/util/test_paths.rs
  • src/cmd/doctor.rs
  • src/config.rs
  • src/cmd/nu_pin_offer.rs
  • src/core/nu_version.rs
  • src/cmd/nupm.rs
  • src/cmd/snapshot.rs
  • src/cmd/list.rs
  • src/cmd/search.rs
  • src/cmd/registry.rs
  • src/install/download.rs
!**/.env,!**/credentials.json,!**/*.pem

📄 CodeRabbit inference engine (CLAUDE.md)

Do not commit files that appear to contain secrets, including .env, credentials.json, and PEM files; warn before doing so even if explicitly requested.

Files:

  • Cargo.toml
  • src/util/test_paths.rs
  • .github/workflows/ci.yml
  • src/cmd/doctor.rs
  • src/config.rs
  • src/cmd/nu_pin_offer.rs
  • src/core/nu_version.rs
  • src/cmd/nupm.rs
  • src/cmd/snapshot.rs
  • src/cmd/list.rs
  • src/cmd/search.rs
  • src/cmd/registry.rs
  • src/install/download.rs
**/*.{rs,toml}

📄 CodeRabbit inference engine (CONTRIBUTING.md)

Run and keep cargo fmt/rustfmt clean, and ensure cargo clippy -- -D warnings passes.

Files:

  • Cargo.toml
  • src/util/test_paths.rs
  • src/cmd/doctor.rs
  • src/config.rs
  • src/cmd/nu_pin_offer.rs
  • src/core/nu_version.rs
  • src/cmd/nupm.rs
  • src/cmd/snapshot.rs
  • src/cmd/list.rs
  • src/cmd/search.rs
  • src/cmd/registry.rs
  • src/install/download.rs
**/*.{rs,md,toml}

📄 CodeRabbit inference engine (CONTRIBUTING.md)

Use the repository's established serialization and module conventions rather than introducing unrelated refactors.

Files:

  • Cargo.toml
  • src/util/test_paths.rs
  • src/cmd/doctor.rs
  • src/config.rs
  • src/cmd/nu_pin_offer.rs
  • src/core/nu_version.rs
  • src/cmd/nupm.rs
  • src/cmd/snapshot.rs
  • src/cmd/list.rs
  • src/cmd/search.rs
  • src/cmd/registry.rs
  • src/install/download.rs
**/*.{js,jsx,ts,tsx,py,java,go,rs,rb,php,c,cpp,h,hpp,cs,swift,kt,kts}

📄 CodeRabbit inference engine (CLAUDE.md)

Add comments only when the WHY is non-obvious; do not narrate what the code does, reference the current task, or reference the PR in comments.

Files:

  • src/util/test_paths.rs
  • src/cmd/doctor.rs
  • src/config.rs
  • src/cmd/nu_pin_offer.rs
  • src/core/nu_version.rs
  • src/cmd/nupm.rs
  • src/cmd/snapshot.rs
  • src/cmd/list.rs
  • src/cmd/search.rs
  • src/cmd/registry.rs
  • src/install/download.rs
**/*.rs

📄 CodeRabbit inference engine (CONTRIBUTING.md)

**/*.rs: Use the Rust 2021 edition.
Use anyhow::Result with .context(...) in application code; use thiserror for library error types that callers match on.
Use clap derive macros for CLI definitions.
Use serde with serde_json or toml for serialization.
Function parameters must use &Path, not &PathBuf.
Library code must not panic; error paths should return anyhow::Result with context where appropriate.
Add or update tests for behavior changes, including relevant failure paths.
New mutating code paths must acquire the mutation lock via acquire_mutation_lock(root) and snapshot the lockfile before writes.
Lockfile, journal, and state-file JSON writes must use write_json_atomic.
numan install must write only to $NUMAN_ROOT; it must not invoke Nu or register plugins/autoloads.
Only activate and deactivate may modify Nu integration state.
Treat the lockfile as the authoritative source of truth; derived projections such as autoload state must not be authoritative.
Install payloads under versioned, content-addressed paths and never overwrite them in place.
Never overwrite foreign autoload files; respect OWNERSHIP_MARKER.
Pass plugin paths through environment variables only; do not use runtime interpolation in Nu program strings.

**/*.rs: Use &Path rather than &PathBuf in Rust function parameters.
Use anyhow::Result for application code, thiserror for library errors, and add context with .context(...) or ?.
Never panic in library code; return errors instead.
Test-first development is expected: write a failing test, implement the change, then verify it passes.
Format and lint Rust code with cargo fmt --check and cargo clippy -- -D warnings; no warnings are permitted.

**/*.rs: All CI gates must pass: cargo test, cargo clippy -- -D warnings, cargo fmt --check, MSRV cargo +1.88 check --locked --all-targets, cargo package --locked, cargo deny, and ignored real-Nu acceptance tests.
numan install must not invoke...

Files:

  • src/util/test_paths.rs
  • src/cmd/doctor.rs
  • src/config.rs
  • src/cmd/nu_pin_offer.rs
  • src/core/nu_version.rs
  • src/cmd/nupm.rs
  • src/cmd/snapshot.rs
  • src/cmd/list.rs
  • src/cmd/search.rs
  • src/cmd/registry.rs
  • src/install/download.rs
**/*.{rs,nu}

📄 CodeRabbit inference engine (CONTRIBUTING.md)

**/*.{rs,nu}: Real-Nu acceptance tests must be marked #[ignore] and should be run when changes affect activation or nupm import; unit tests must not spawn real nu and should use injectable seams such as FakeCandidateRunner or registrars.
The nupm integration must be read-only toward NUPM_HOME, must not execute build.nu, and must not perform bidirectional synchronization.

Files:

  • src/util/test_paths.rs
  • src/cmd/doctor.rs
  • src/config.rs
  • src/cmd/nu_pin_offer.rs
  • src/core/nu_version.rs
  • src/cmd/nupm.rs
  • src/cmd/snapshot.rs
  • src/cmd/list.rs
  • src/cmd/search.rs
  • src/cmd/registry.rs
  • src/install/download.rs
**/*.{rs,md}

📄 CodeRabbit inference engine (CONTRIBUTING.md)

Match existing naming, module layout, and documentation level in the file being edited; update AGENTS.md, docs/, or command help when structure, conventions, or user-visible behavior changes.

Files:

  • src/util/test_paths.rs
  • src/cmd/doctor.rs
  • src/config.rs
  • src/cmd/nu_pin_offer.rs
  • src/core/nu_version.rs
  • src/cmd/nupm.rs
  • src/cmd/snapshot.rs
  • src/cmd/list.rs
  • src/cmd/search.rs
  • src/cmd/registry.rs
  • src/install/download.rs
src/**/*.rs

📄 CodeRabbit inference engine (AGENTS.md)

Use compile-time #[cfg(target_env)] platform detection rather than std::env::consts.

Files:

  • src/util/test_paths.rs
  • src/cmd/doctor.rs
  • src/config.rs
  • src/cmd/nu_pin_offer.rs
  • src/core/nu_version.rs
  • src/cmd/nupm.rs
  • src/cmd/snapshot.rs
  • src/cmd/list.rs
  • src/cmd/search.rs
  • src/cmd/registry.rs
  • src/install/download.rs
src/cmd/*.rs

📄 CodeRabbit inference engine (AGENTS.md)

Create a snapshot before mutations performed by install, update, remove, activate, deactivate, nupm import, and init --refresh.

Files:

  • src/cmd/doctor.rs
  • src/cmd/nu_pin_offer.rs
  • src/cmd/nupm.rs
  • src/cmd/snapshot.rs
  • src/cmd/list.rs
  • src/cmd/search.rs
  • src/cmd/registry.rs
src/cmd/{activate,deactivate,update,remove,nupm,init}.rs

📄 CodeRabbit inference engine (AGENTS.md)

Acquire the root mutation lock before mutating managed state; the lock must serialize concurrent mutations and fail immediately on a second acquisition.

Files:

  • src/cmd/nupm.rs
src/install/**/*.rs

📄 CodeRabbit inference engine (AGENTS.md)

src/install/**/*.rs: Install operations must remain inert: they may write only to $NUMAN_ROOT and must not perform Nu integration.
Plugin binary artifacts must include a SHA256 value; the install transaction must bail when it is missing.
Never overwrite installed payloads; use the immutable path shape <root>/packages/<type>/<owner>/<name>/<version>-<sha8prefix>/.

Files:

  • src/install/download.rs
🔍 Remote MCP DeepWiki, GitHub Copilot

Additional review context

  • The PR’s coverage job uses cargo llvm-cov --workspace --locked --summary-only; the committed lockfile also includes the new url dependency. The job can still fail if tests or coverage execution fail, but it does not enforce a coverage threshold.

  • Command output refactors preserve normal CLI behavior by passing stdout from each public execute function into private writer-based helpers. Tests generally validate captured output, though many assertions use contains rather than exact output comparisons.

  • Config::resolve_root is an early, shared entry point for determining Numan’s managed state directory, and the new NUMAN_ROOT guard serializes only tests that explicitly construct it. Any other tests mutating NUMAN_ROOT without the guard could still race.

  • The NuVersion::matches_constraint change now fails closed for malformed parsed bounds, but the =0.* branch still treats every version beginning with 0. as the special minor-version form. Consequently, a constraint such as =0.113.1 attempts to parse 113.1 as a minor number and will not perform full-version equality. The added equality test covers only =1.2.3, so this case remains untested.

  • Download handling now uses url::Url::to_file_path(), while the Windows-specific test covers a drive-form URL only under #[cfg(windows)]; no test covers invalid file URLs or file URLs with a host component.

  • Numan’s install transaction downloads artifacts into partial files, verifies SHA-256, and atomically renames them; the PR only adds direct download_file tests and does not exercise that broader transaction path.

  • Current checks show Format, Clippy, MSRV, Ubuntu tests, macOS acceptance, Ubuntu acceptance, packaging, and roadmap checks succeeded. Coverage, Windows tests, macOS tests, Rust analysis, and Windows acceptance were still in progress when queried.

🔇 Additional comments (14)
src/cmd/list.rs (1)

5-22: LGTM!

Also applies to: 42-46, 57-153

src/cmd/registry.rs (1)

7-7: LGTM!

Also applies to: 35-59, 175-213, 267-415

src/cmd/search.rs (1)

22-31: LGTM!

Also applies to: 43-54, 117-150, 253-253, 433-518

src/cmd/snapshot.rs (1)

3-3: LGTM!

Also applies to: 43-253, 321-435

src/install/download.rs (1)

98-109: Generate the test URL from the source path.

Line 104 creates file://C:\... on Windows. This is not a portable file URL. Use url::Url::from_file_path(&src) so this cross-platform test validates a URL that to_file_path() can round trip. Keep the explicit Windows drive-form test. Url::to_file_path() has platform-specific file-host handling. (docs.rs)

Proposed fix
-        let url = format!("file://{}", src.display());
+        let url = url::Url::from_file_path(&src).unwrap().to_string();
src/config.rs (1)

222-227: LGTM!

Cargo.toml (1)

41-41: LGTM!

src/cmd/nu_pin_offer.rs (2)

150-180: Prove that the interactive input path runs.

The new filesystem assertions prove that no root artifact remains, but both tests still pass if offer_managed_nu_pin_with_interaction skips read_line and returns false. Track callback invocation in both closures, then assert that the callback was called. Keep the no-artifact assertion for the installation side effect.


139-147: LGTM!

Also applies to: 182-192

src/cmd/nupm.rs (2)

483-498: Assert the explicit-path failure.

Line 497 discards execute's result, so the test passes if inspect --all succeeds. The test also supplies Some("/nonexistent/nupm-home"); resolve_nupm_home validates an explicit path instead of using the NotConfigured branch (src/nupm_compat/discovery.rs:18-29). Capture unwrap_err() and assert the path-validation error, or set nupm_home to None and control NUPM_HOME if the test is intended to cover the not-configured branch. Remove the control-flow comment after adding the assertion.

As per coding guidelines, “Add comments only when the WHY is non-obvious; do not narrate what the code does.”

Source: Coding guidelines


456-480: LGTM!

Also applies to: 501-604, 606-608, 611-648

.github/workflows/ci.yml (1)

65-66: LGTM!

Also applies to: 77-85

src/util/test_paths.rs (1)

148-174: LGTM!

src/cmd/doctor.rs (1)

1860-1860: LGTM!

Also applies to: 1893-1893

Comment thread src/core/nu_version.rs
Comment thread src/util/test_paths.rs
- ci.yml: add continue-on-error: true to the coverage job's "Run
  coverage" step. Without it, cargo llvm-cov exiting nonzero (e.g. a
  test failing during the instrumented run) would still fail the
  build despite the "informational only" framing — the test job
  already gates on real test failures, this job only publishes the
  summary.
- nu_version.rs: matches_constraint's "=0.x.y" handling used
  ver.strip_prefix("0.") to detect the legacy "=0.113.x" minor-only
  format, which also matches full exact versions like "=0.113.1" —
  "113.1" then fails to parse as a minor number and (after the earlier
  fail-closed fix) always returns false, so an exact 0.x.y match was
  reported incompatible. Only take the legacy path when the value ends
  in ".x".
- nupm.rs: inspect_all_without_nupm_home_bails still discarded the
  execute() result (`let _ = ...`) — an earlier commit's message
  claimed this was fixed but the edit was never actually applied.
  Fixed for real this time and verified by running the test.
- tests/doctor_test.rs: doctor_fix_auto_creates_layout_without_network
  mutates the process-global NUMAN_ROOT env var without the
  NumanRootRestoreGuard added earlier in this PR, so it could race a
  passing test in the future if more of this integration binary's
  tests start reading NUMAN_ROOT concurrently. Applied the same guard.
@tonythethompson
tonythethompson merged commit 0a1f0a5 into master Aug 11, 2026
24 checks passed
@tonythethompson
tonythethompson deleted the coverage-cmd-tests branch August 11, 2026 05:17
@linear-code

linear-code Bot commented Aug 11, 2026

Copy link
Copy Markdown

QUI-17

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant