es_fluent_cli/commands/
generate.rs

1//! Generate command implementation.
2
3use crate::commands::{
4    WorkspaceArgs, WorkspaceCrates, parallel_generate, render_generation_results,
5};
6use crate::core::{CliError, FluentParseMode, GenerationAction};
7use crate::utils::ui;
8use clap::Parser;
9use colored::Colorize as _;
10
11/// Arguments for the generate command.
12#[derive(Parser)]
13pub struct GenerateArgs {
14    #[command(flatten)]
15    pub workspace: WorkspaceArgs,
16
17    /// Parse mode for FTL generation
18    #[arg(short, long, value_enum, default_value_t = FluentParseMode::default())]
19    pub mode: FluentParseMode,
20
21    /// Dry run - show what would be generated without making changes.
22    #[arg(long)]
23    pub dry_run: bool,
24
25    /// Force rebuild of the runner, ignoring the staleness cache.
26    #[arg(long)]
27    pub force_run: bool,
28}
29
30/// Run the generate command.
31pub fn run_generate(args: GenerateArgs) -> Result<(), CliError> {
32    let workspace = WorkspaceCrates::discover(args.workspace)?;
33
34    if !workspace.print_discovery(ui::print_header) {
35        return Ok(());
36    }
37
38    let results = parallel_generate(
39        &workspace.workspace_info,
40        &workspace.valid,
41        &GenerationAction::Generate {
42            mode: args.mode,
43            dry_run: args.dry_run,
44        },
45        args.force_run,
46    );
47    let has_errors = render_generation_results(
48        &results,
49        |result| {
50            if args.dry_run {
51                if let Some(output) = &result.output {
52                    print!("{}", output);
53                } else if result.changed {
54                    // Fallback if no output captured but marked as changed
55                    println!(
56                        "{} {} ({} resources)",
57                        format!("{} would be generated in", result.name).yellow(),
58                        humantime::format_duration(result.duration)
59                            .to_string()
60                            .green(),
61                        result.resource_count.to_string().cyan()
62                    );
63                } else {
64                    println!("{} {}", "Unchanged:".dimmed(), result.name.bold());
65                }
66            } else if result.changed {
67                ui::print_generated(&result.name, result.duration, result.resource_count);
68            } else {
69                println!("{} {}", "Unchanged:".dimmed(), result.name.bold());
70            }
71        },
72        |result| ui::print_generation_error(&result.name, result.error.as_ref().unwrap()),
73    );
74
75    if has_errors {
76        std::process::exit(1);
77    }
78
79    Ok(())
80}