view rust/rhg/src/commands/debugdata.rs @ 49913:c15b415d1bff

rust: use `logging_timer` instead of `micro_timer` I am the author of `micro_timer`. I built it at the time because I couldn't find a crate that was simple to use and flexible to do function timing with. Turns out I just couldn't find it because crates.io's search isn't all that great, or maybe I didn't look hard enough. `logging_timer` is better in every way: - supports changing the logging level - supports start and end logging - supports intermediary messages - supports inline macros - supports formatting the output - better IDE/tree-sitter integration thanks to a more robust proc macro I also changed all uses to one-liners, so it's easier to copy-paste.
author Raphaël Gomès <rgomes@octobus.net>
date Fri, 06 Jan 2023 18:52:04 +0100
parents 37bc3edef76f
children 532e74ad3ff6
line wrap: on
line source

use crate::error::CommandError;
use clap::Arg;
use clap::ArgGroup;
use hg::operations::{debug_data, DebugDataKind};

pub const HELP_TEXT: &str = "
Dump the contents of a data file revision
";

pub fn args() -> clap::Command {
    clap::command!("debugdata")
        .arg(
            Arg::new("changelog")
                .help("open changelog")
                .short('c')
                .action(clap::ArgAction::SetTrue),
        )
        .arg(
            Arg::new("manifest")
                .help("open manifest")
                .short('m')
                .action(clap::ArgAction::SetTrue),
        )
        .group(
            ArgGroup::new("revlog")
                .args(&["changelog", "manifest"])
                .required(true),
        )
        .arg(
            Arg::new("rev")
                .help("revision")
                .required(true)
                .value_name("REV"),
        )
        .about(HELP_TEXT)
}

#[logging_timer::time("trace")]
pub fn run(invocation: &crate::CliInvocation) -> Result<(), CommandError> {
    let args = invocation.subcommand_args;
    let rev = args
        .get_one::<String>("rev")
        .expect("rev should be a required argument");
    let kind = match (
        args.get_one::<bool>("changelog").unwrap(),
        args.get_one::<bool>("manifest").unwrap(),
    ) {
        (true, false) => DebugDataKind::Changelog,
        (false, true) => DebugDataKind::Manifest,
        (true, true) => {
            unreachable!("Should not happen since options are exclusive")
        }
        (false, false) => {
            unreachable!("Should not happen since options are required")
        }
    };

    let repo = invocation.repo?;
    if repo.has_narrow() {
        return Err(CommandError::unsupported(
            "support for ellipsis nodes is missing and repo has narrow enabled",
        ));
    }
    let data = debug_data(repo, rev, kind).map_err(|e| (e, rev.as_ref()))?;

    let mut stdout = invocation.ui.stdout_buffer();
    stdout.write_all(&data)?;
    stdout.flush()?;

    Ok(())
}