Skip to content

feat(cargo): Cargo trait + LiveCargo + MockCargo + install-list parser#11

Merged
UnbreakableMJ merged 1 commit into
mainfrom
feat/cargo-adapter
Apr 27, 2026
Merged

feat(cargo): Cargo trait + LiveCargo + MockCargo + install-list parser#11
UnbreakableMJ merged 1 commit into
mainfrom
feat/cargo-adapter

Conversation

@UnbreakableMJ

Copy link
Copy Markdown
Contributor

Plan §6.7 — second M1 Week 2 adapter probe path. Inventory only at M1; install/uninstall arrive in M2 with the apply-engine adapters per Plan §7.3.

Public surface

  • trait Cargo { fn inventory(&self) -> Result<CargoInventory, CargoError>; }
  • struct LiveCargo — production, default cargo from PATH, with_binary() for test injection.
  • struct MockCargo — feature-gated behind test-mocks, in-memory canned inventory.
  • fn parse_install_list(&str) -> CargoInventory — exposed pub for probe code that already has captured stdout.
  • enum CargoErrorNotInPath (hint: paru -S rustup), Io, InvocationFailed { code, stderr }, NotUtf8.

Parser coverage

  • standard crate-name vX.Y.Z: header
  • (registry+...) source spec after the version
  • (https://...#sha) git source spec
  • version without v prefix (defensive)
  • indented binary listings — skipped; Pearlite tracks crates, not bins

Tests (10 passing)

  • inventory: parse_known_output, empty_output, registry_source, git_source, ignores_binary_lines, version_without_v_prefix
  • live: cargo_not_in_path_error_class, live_cargo_inventory_succeeds_in_a_rust_environment
  • mock: empty_mock, with_inventory_round_trips

Verification

  • cargo test -p pearlite-cargo — 10 passed; 0 failed
  • cargo clippy --workspace --all-targets -- -D warnings
  • cargo fmt --all --check
  • scripts/ci/check-spdx.sh
  • pearlite-audit check . — 1 check, 0 violations

🤖 Generated with Claude Code

Plan §6.7 — second M1 Week 2 adapter probe path. Inventory only at M1;
install/uninstall arrive in M2 with the rest of the apply-engine
adapters per Plan §7.3.

Public surface:

- pub trait Cargo { fn inventory(&self) -> Result<CargoInventory, CargoError>; }
- pub struct LiveCargo with new() / with_binary() / binary().
- pub struct MockCargo (test-mocks feature) with new() / with_inventory().
- pub fn parse_install_list(&str) -> CargoInventory — exposed because
  parsing is purely textual and useful from tests / probes.
- pub enum CargoError — NotInPath (hint: paru -S rustup), Io,
  InvocationFailed { code, stderr }, NotUtf8.

Parser handles:
- standard `crate-name vX.Y.Z:` header
- registry source spec `(registry+...)` after the version
- git source spec `(https://...#sha)` after the version
- version without `v` prefix (defensive against future cargo releases)
- indented binary listings (skipped — Pearlite tracks crates, not bins)

Tests (10 passing):
- inventory: parse_known_output, empty_output_yields_empty_inventory,
  parses_registry_source_spec, parses_git_source_spec, ignores_binary_lines,
  version_without_v_prefix_still_parses.
- live: cargo_not_in_path_error_class,
  live_cargo_inventory_succeeds_in_a_rust_environment.
- mock: empty_mock_yields_empty_inventory, with_inventory_round_trips.

Cargo dep on pearlite-schema pinned to "0.1" per the cargo-deny
wildcard rule.

Verification:
- cargo test -p pearlite-cargo  (10 passed; 0 failed)
- cargo clippy --workspace --all-targets -- -D warnings  (zero warnings)
- cargo fmt --all --check
- scripts/ci/check-spdx.sh
- pearlite-audit check .  (1 check, 0 violations)

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
@UnbreakableMJ
UnbreakableMJ merged commit e1333fa into main Apr 27, 2026
3 checks passed
@UnbreakableMJ
UnbreakableMJ deleted the feat/cargo-adapter branch April 27, 2026 17:00
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