aboutsummaryrefslogtreecommitdiffhomepage
path: root/crates/mozart/src/commands/depends.rs
diff options
context:
space:
mode:
authornsfisis <nsfisis@gmail.com>2026-02-21 14:11:18 +0900
committernsfisis <nsfisis@gmail.com>2026-02-21 14:11:18 +0900
commit294bd3dd425a374eda13a52b925a2cd0c4db7f0a (patch)
treef63a008b88113ac2548affbd0a662879f14b1ed7 /crates/mozart/src/commands/depends.rs
parent48e88e9e204a38d1e31483412003f1492fa8fdcf (diff)
downloadphp-mozart-294bd3dd425a374eda13a52b925a2cd0c4db7f0a.tar.gz
php-mozart-294bd3dd425a374eda13a52b925a2cd0c4db7f0a.tar.zst
php-mozart-294bd3dd425a374eda13a52b925a2cd0c4db7f0a.zip
feat(depends): implement depends and prohibits commands with shared dependency logic
Add the `depends` (why) and `prohibits` (why-not) commands that query the dependency graph to answer "which packages require X?" and "which packages prevent version Y of X from being installed?" respectively. Introduces the shared `dependency` module with package loading from lock file or installed.json, forward/inverted dependency graph walking, recursive traversal with cycle detection, and table/tree output formatters. Adds `conflict` field to LockedPackage for conflict-based prohibition detection, updating all struct literals across install, remove, require, and update test helpers. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Diffstat (limited to 'crates/mozart/src/commands/depends.rs')
-rw-r--r--crates/mozart/src/commands/depends.rs41
1 files changed, 39 insertions, 2 deletions
diff --git a/crates/mozart/src/commands/depends.rs b/crates/mozart/src/commands/depends.rs
index ecdbb24..fa84f7d 100644
--- a/crates/mozart/src/commands/depends.rs
+++ b/crates/mozart/src/commands/depends.rs
@@ -1,4 +1,5 @@
use clap::Args;
+use std::path::PathBuf;
#[derive(Args)]
pub struct DependsArgs {
@@ -18,6 +19,42 @@ pub struct DependsArgs {
pub locked: bool,
}
-pub fn execute(_args: &DependsArgs, _cli: &super::Cli) -> anyhow::Result<()> {
- todo!()
+pub fn execute(args: &DependsArgs, cli: &super::Cli) -> anyhow::Result<()> {
+ let working_dir = match &cli.working_dir {
+ Some(dir) => PathBuf::from(dir),
+ None => std::env::current_dir()?,
+ };
+
+ let packages = super::dependency::load_packages(&working_dir, args.locked)?;
+
+ if packages.is_empty() {
+ println!(
+ "{}",
+ crate::console::info("No packages found. Run `mozart install` first.")
+ );
+ return Ok(());
+ }
+
+ let target = args.package.to_lowercase();
+
+ // Verify the target package is known
+ let target_known = packages.iter().any(|p| p.name.to_lowercase() == target);
+ if !target_known {
+ anyhow::bail!(
+ "Package '{}' not found in the dependency graph.",
+ args.package
+ );
+ }
+
+ let recursive = args.tree || args.recursive;
+ let needles = vec![target];
+ let results = super::dependency::get_dependents(&packages, &needles, None, false, recursive)?;
+
+ if args.tree {
+ super::dependency::print_tree(&results, 0);
+ } else {
+ super::dependency::print_table(&results);
+ }
+
+ Ok(())
}