zenops 0.19.0

Declarative system configuration management for shell config and dotfiles.
Documentation
//! Per-package-manager install hints. Mirrors
//! [`super::super::super::output::PkgInstallHints`] and the runtime side of
//! `pkg_manager::DetectedPackageManager` — extend in lockstep when adding a
//! new manager.

#[derive(serde::Deserialize, schemars::JsonSchema, Debug, Clone, PartialEq, Default)]
#[serde(deny_unknown_fields)]
pub struct InstallHint {
    pub brew: BrewHint,
    pub dnf5: Dnf5Hint,
    pub apt: AptHint,
    pub pacman: PacmanHint,
    pub cargo: CargoHint,
    // Future package managers should be added as additional REQUIRED fields here
    // (e.g. zypper, apk) and wired into
    // `pkg_manager::DetectedPackageManager::{packages_for, install_command}`.
    // Keeping them required guarantees cross-manager completeness at parse time —
    // a pkg with no install path under a given manager declares that intent
    // explicitly via `packages = []`, never by omission.
}

#[derive(serde::Deserialize, schemars::JsonSchema, Debug, Clone, PartialEq, Default)]
#[serde(deny_unknown_fields)]
pub struct BrewHint {
    pub packages: Vec<String>,
}

/// Install hint for DNF5 (Fedora 41+ default; new command grammar vs DNF4).
/// Labeled `dnf5` rather than `dnf` so the version pin travels with the
/// package list — if DNF6 lands with another grammar shift, it gets its
/// own field rather than silently inheriting this one's semantics. The
/// user-facing label in `zenops pkg` output is the friendlier `"dnf"`;
/// only the schema/field name carries the version pin.
#[derive(serde::Deserialize, schemars::JsonSchema, Debug, Clone, PartialEq, Default)]
#[serde(deny_unknown_fields)]
pub struct Dnf5Hint {
    pub packages: Vec<String>,
}

/// Install hint for apt (Debian / Ubuntu). Primary manager on those
/// hosts; the install command uses the friendly `apt` wrapper rather
/// than `apt-get` for consistency with how users actually type the
/// command on modern releases.
#[derive(serde::Deserialize, schemars::JsonSchema, Debug, Clone, PartialEq, Default)]
#[serde(deny_unknown_fields)]
pub struct AptHint {
    pub packages: Vec<String>,
}

/// Install hint for pacman (Arch Linux). Primary manager on Arch hosts.
/// Install command uses `pacman -S` (Sync) which is the standard install
/// invocation; the `-S` is non-optional since `pacman install` doesn't
/// exist as a separate subcommand.
#[derive(serde::Deserialize, schemars::JsonSchema, Debug, Clone, PartialEq, Default)]
#[serde(deny_unknown_fields)]
pub struct PacmanHint {
    pub packages: Vec<String>,
}

/// Install hint for `cargo install` — crates.io crate names. Cargo is a
/// supplementary manager: it doesn't replace the host's system package
/// manager (most pkgs aren't Rust crates), but it fills gaps for Rust
/// tools that aren't in the system repos (e.g. `skim` on Fedora).
#[derive(serde::Deserialize, schemars::JsonSchema, Debug, Clone, PartialEq, Default)]
#[serde(deny_unknown_fields)]
pub struct CargoHint {
    pub packages: Vec<String>,
}