dojo_cli/commands/
config.rs

1use crate::config::Config;
2use dialoguer::{Confirm, Input, Select};
3
4pub async fn handle_config_command(
5    _sub_matches: &clap::ArgMatches,
6) -> Result<(), Box<dyn std::error::Error>> {
7    println!("__________.__  __               .__         ________             __        ");
8    println!("\\______   \\__|/  |_  ____  ____ |__| ____   \\______ \\   ____    |__| ____  ");
9    println!(" |    |  _/  \\   __\\/ ___\\/  _ \\|  |/    \\   |    |  \\ /  _ \\   |  |/  _ \\ ");
10    println!(" |    |   \\  ||  | \\  \\__(  <_> )  |   |  \\  |    `   (  <_> )  |  (  <_> )");
11    println!(" |______  /__||__|  \\___  >____/|__|___|  / /_______  /\\____/\\__|  |\\____/ ");
12    println!("        \\/              \\/              \\/          \\/      \\______|       \n");
13    println!("āš™ļø  Bitcoin Dojo CLI Configuration");
14    println!("Update your configuration settings interactively.\n");
15
16    // Check if config exists
17    if !Config::exists() {
18        println!("āŒ No configuration file found!");
19        println!("Please run 'dojo-cli init' first to create your initial configuration.");
20        return Ok(());
21    }
22
23    // Load existing config
24    let mut config = Config::load()?;
25    println!(
26        "šŸ“ Current configuration loaded from: {}",
27        Config::get_config_path()?.display()
28    );
29
30    // Show current values
31    println!("\nšŸ“‹ Current Configuration:");
32    println!("   Workspace Directory: {}", config.workspace_directory);
33    println!("   API Token: {}", mask_token(&config.api_token));
34    println!(
35        "   Environment: {}",
36        config.get_environment().display_name()
37    );
38    println!("   Curriculum Version: {}", config.get_curriculum_version());
39
40    // Interactive configuration menu
41    loop {
42        let options = vec![
43            "Update workspace directory",
44            "Update API token",
45            "Save and exit",
46            "Exit without saving",
47        ];
48
49        let selection = Select::new()
50            .with_prompt("\nWhat would you like to update?")
51            .items(&options)
52            .default(0)
53            .interact()?;
54
55        match selection {
56            0 => {
57                let new_workspace: String = Input::new()
58                    .with_prompt("Enter new workspace directory")
59                    .default(config.workspace_directory.clone())
60                    .interact_text()?;
61                config.workspace_directory = new_workspace;
62                println!("āœ… Workspace directory updated!");
63            }
64            1 => {
65                let new_token: String = Input::new()
66                    .with_prompt("Enter new API token")
67                    .interact_text()?;
68                if !new_token.trim().is_empty() {
69                    config.api_token = new_token;
70                    println!("āœ… API token updated!");
71                } else {
72                    println!("āŒ API token cannot be empty. Update cancelled.");
73                }
74            }
75            2 => {
76                // Save configuration
77                config.save()?;
78                println!("\nāœ… Configuration saved successfully!");
79                println!("šŸ“ Config file: {}", Config::get_config_path()?.display());
80                break;
81            }
82            3 => {
83                let confirm = Confirm::new()
84                    .with_prompt("Are you sure you want to exit without saving changes?")
85                    .default(false)
86                    .interact()?;
87
88                if confirm {
89                    println!("āŒ Changes discarded.");
90                    break;
91                }
92            }
93            _ => unreachable!(),
94        }
95    }
96
97    Ok(())
98}
99
100fn mask_token(token: &str) -> String {
101    if token.len() <= 8 {
102        "*".repeat(token.len())
103    } else {
104        format!("{}...{}", &token[..4], &token[token.len() - 4..])
105    }
106}