Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
34 changes: 9 additions & 25 deletions src/cli/bootupctl.rs
Original file line number Diff line number Diff line change
Expand Up @@ -49,10 +49,6 @@ impl CtlCommand {
/// CLI sub-commands.
#[derive(Debug, Parser)]
pub enum CtlVerb {
// FIXME(lucab): drop this after refreshing
// https://github.com/coreos/fedora-coreos-config/pull/595
#[clap(name = "backend", hide = true, subcommand)]
Backend(CtlBackend),
#[clap(name = "status", about = "Show components status")]
Status(StatusOpts),
#[clap(name = "update", about = "Update all components")]
Expand All @@ -61,6 +57,14 @@ pub enum CtlVerb {
AdoptAndUpdate(AdoptAndUpdateOpts),
#[clap(name = "validate", about = "Validate system state")]
Validate,
/// Low-level commands for building and installing OS images
///
/// These act on an OS tree or target root rather than on the running
/// system, and are intended for image build and installation tooling
/// (e.g. `bootc install` or disk image builders). To update the
/// bootloader of a booted system, use `update` or `adopt-and-update`.
#[clap(name = "backend", subcommand)]
Backend(super::bootupd::DVerb),
#[clap(
name = "migrate-static-grub-config",
hide = true,
Expand All @@ -69,17 +73,6 @@ pub enum CtlVerb {
MigrateStaticGrubConfig,
}

#[derive(Debug, Parser)]
pub enum CtlBackend {
#[clap(name = "generate-update-metadata", hide = true)]
Generate(super::bootupd::GenerateOpts),
#[clap(name = "install", hide = true)]
Install(super::bootupd::InstallOpts),
#[clap(hide = true)]
#[cfg(efi_arch)]
SetDefaultBootloader(super::bootupd::DefaultBootloaderOpts),
}

#[derive(Debug, Parser)]
pub struct StatusOpts {
/// If there are updates available, output `Updates available: ` to standard output;
Expand Down Expand Up @@ -123,16 +116,7 @@ impl CtlCommand {
CtlVerb::Update(opts) => Self::run_update(opts),
CtlVerb::AdoptAndUpdate(opts) => Self::run_adopt_and_update(opts),
CtlVerb::Validate => Self::run_validate(),
CtlVerb::Backend(CtlBackend::Generate(opts)) => {
super::bootupd::DCommand::run_generate_meta(opts)
}
CtlVerb::Backend(CtlBackend::Install(opts)) => {
super::bootupd::DCommand::run_install(opts)
}
#[cfg(efi_arch)]
CtlVerb::Backend(CtlBackend::SetDefaultBootloader(opts)) => {
super::bootupd::DCommand::set_default_bootloader(opts)
}
CtlVerb::Backend(verb) => verb.run(),
CtlVerb::MigrateStaticGrubConfig => Self::run_migrate_static_grub_config(),
}
}
Expand Down
36 changes: 27 additions & 9 deletions src/cli/bootupd.rs
Original file line number Diff line number Diff line change
Expand Up @@ -36,10 +36,21 @@ impl DCommand {
/// CLI sub-commands.
#[derive(Debug, Parser)]
pub enum DVerb {
#[clap(name = "generate-update-metadata", about = "Generate metadata")]
/// Generate update metadata from the bootloader files in an OS tree
///
/// Run this at image build time. It records the bootloader component
/// versions (e.g. from the RPM database) under /usr/lib/bootupd/updates,
/// which `install` and `update` later use as their source.
#[clap(name = "generate-update-metadata")]
GenerateUpdateMetadata(GenerateOpts),
#[clap(name = "install", about = "Install components")]
/// Install bootloader components to a target root
///
/// Used when creating a disk image or installing a system: copies the
/// update payload from the source root into the target's ESP and/or
/// boot partition, and installs to the target block device(s) as needed.
#[clap(name = "install")]
Install(InstallOpts),
/// Set the default bootloader on EFI systems
#[cfg(efi_arch)]
SetDefaultBootloader(DefaultBootloaderOpts),
}
Expand Down Expand Up @@ -94,7 +105,7 @@ pub(crate) struct InstallOpts {

#[derive(Debug, Parser)]
pub struct GenerateOpts {
/// Physical root mountpoint
/// Root of the OS tree (only `/` is currently supported)
#[clap(value_parser)]
sysroot: Option<String>,
}
Expand All @@ -108,15 +119,22 @@ pub struct DefaultBootloaderOpts {
pub(crate) bootloader: Bootloader,
}

impl DVerb {
/// Run this verb; shared by `bootupd` and `bootupctl backend`.
pub(crate) fn run(self) -> Result<()> {
match self {
DVerb::Install(opts) => DCommand::run_install(opts),
DVerb::GenerateUpdateMetadata(opts) => DCommand::run_generate_meta(opts),
#[cfg(efi_arch)]
DVerb::SetDefaultBootloader(opts) => DCommand::set_default_bootloader(opts),
}
}
}

impl DCommand {
/// Run CLI application.
pub fn run(self) -> Result<()> {
match self.cmd {
DVerb::Install(opts) => Self::run_install(opts),
DVerb::GenerateUpdateMetadata(opts) => Self::run_generate_meta(opts),
#[cfg(efi_arch)]
DVerb::SetDefaultBootloader(opts) => Self::set_default_bootloader(opts),
}
self.cmd.run()
}

/// Runner for `generate-install-metadata` verb.
Expand Down
17 changes: 17 additions & 0 deletions src/cli/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -58,6 +58,23 @@ mod tests {
bootupd::DCommand::command().debug_assert();
}

#[test]
fn backend_is_documented() {
use clap::CommandFactory;
let ctl = bootupctl::CtlCommand::command();
let backend = ctl.find_subcommand("backend").unwrap();
assert!(!backend.is_hide_set());
assert!(backend.get_about().is_some());
for verb in backend.get_subcommands() {
assert!(!verb.is_hide_set(), "{} is hidden", verb.get_name());
assert!(
verb.get_about().is_some(),
"{} has no help",
verb.get_name()
);
}
}

#[test]
fn test_multicall_dispatch() {
{
Expand Down