commit_wizard/engine/capabilities/config/
show.rs1use std::path::{Path, PathBuf};
2
3use crate::engine::{
4 config::{ProjectConfig, StandardConfig},
5 constants::{CONFIG_FILE_NAME, PROJECT_CONFIG_FILE_NAME, paths::app_config_dir},
6 error::{ErrorCode, Result},
7};
8
9#[derive(Debug, Clone, Copy)]
10pub enum ConfigTarget {
11 Project,
12 Global,
13}
14
15#[derive(Debug, Clone, Copy, PartialEq, Eq)]
16pub enum ConfigShowFormat {
17 Human,
18 Json,
19 Toml,
20}
21
22pub struct ConfigPathInput<'a> {
23 pub cwd: &'a Path,
24 pub target: ConfigTarget,
25}
26
27pub struct ConfigPathOutput {
28 pub path: PathBuf,
29}
30
31pub struct ConfigShowInput<'a> {
32 pub cwd: &'a Path,
33 pub target: ConfigTarget,
34 pub explicit_path: Option<&'a Path>,
35 pub format: ConfigShowFormat,
36}
37
38pub struct ConfigShowOutput {
39 pub path: PathBuf,
40 pub exists: bool,
41 pub content: String,
42}
43
44pub fn resolve_config_path(target: ConfigTarget, cwd: &Path) -> Result<PathBuf> {
45 match target {
46 ConfigTarget::Project => Ok(cwd.join(PROJECT_CONFIG_FILE_NAME)),
47 ConfigTarget::Global => Ok(app_config_dir()?.join(CONFIG_FILE_NAME)),
48 }
49}
50
51pub fn config_path(input: &ConfigPathInput<'_>) -> Result<ConfigPathOutput> {
52 Ok(ConfigPathOutput {
53 path: resolve_config_path(input.target, input.cwd)?,
54 })
55}
56
57pub fn config_show(input: &ConfigShowInput<'_>) -> Result<ConfigShowOutput> {
58 let path = resolve_config_path(input.target, input.cwd)?;
59
60 if !path.exists() {
61 return Err(ErrorCode::ConfigUnreadable
62 .error()
63 .with_context("path", path.display().to_string())
64 .with_context("reason", "config file does not exist"));
65 }
66
67 let raw = std::fs::read_to_string(&path)?;
68
69 let content = match input.target {
70 ConfigTarget::Project => {
71 let parsed = ProjectConfig::from_toml_str(&raw)?;
72 match input.format {
73 ConfigShowFormat::Human | ConfigShowFormat::Toml => raw,
74 ConfigShowFormat::Json => serde_json::to_string_pretty(&parsed).map_err(|err| {
75 ErrorCode::SerializationFailure
76 .error()
77 .with_context("error", err.to_string())
78 })?,
79 }
80 }
81 ConfigTarget::Global => {
82 let parsed = StandardConfig::from_toml_str(&raw)?;
83 match input.format {
84 ConfigShowFormat::Human | ConfigShowFormat::Toml => raw,
85 ConfigShowFormat::Json => serde_json::to_string_pretty(&parsed).map_err(|err| {
86 ErrorCode::SerializationFailure
87 .error()
88 .with_context("error", err.to_string())
89 })?,
90 }
91 }
92 };
93
94 Ok(ConfigShowOutput {
95 path,
96 exists: true,
97 content,
98 })
99}