Skip to content

Commit a1d302c

Browse files
committed
refactor: streamline CLI and code structure
- rename CLI flags for clarity (copy to copy_to_clipboard, print_table to check_env) - add JSON output format with enum-based detection in main.rs - simplify conditional checks using if-let patterns in repository and openai modules - fix copyright typo in message.rs - add serde_json and serde dependencies for JSON serialization Signed-off-by: mingcheng <[email protected]>
1 parent d0af28f commit a1d302c

File tree

7 files changed

+80
-31
lines changed

7 files changed

+80
-31
lines changed

Cargo.lock

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,8 @@ dependencies = [
2121
"git2",
2222
"log",
2323
"reqwest",
24+
"serde",
25+
"serde_json",
2426
"tabled",
2527
"tokio",
2628
"tracing",
@@ -1842,9 +1844,9 @@ dependencies = [
18421844

18431845
[[package]]
18441846
name = "rustls"
1845-
version = "0.23.32"
1847+
version = "0.23.33"
18461848
source = "registry+https://github.com/rust-lang/crates.io-index"
1847-
checksum = "cd3c25631629d034ce7cd9940adc9d45762d46de2b0f57193c4443b92c6d4d40"
1849+
checksum = "751e04a496ca00bb97a5e043158d23d66b5aabf2e1d5aa2a0aaebb1aafe6f82c"
18481850
dependencies = [
18491851
"once_cell",
18501852
"ring",

Cargo.toml

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -38,6 +38,8 @@ tracing = "0.1"
3838
tracing-subscriber = "0.3"
3939
arboard = "3.6"
4040
tabled = "0.20"
41+
serde_json = "1.0.145"
42+
serde = { version = "1.0.228", features = ["derive"] }
4143

4244
[[bin]]
4345
name = "aigitcommit"

src/cli.rs

Lines changed: 19 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -76,15 +76,31 @@ If not specified, the current directory will be used"#,
7676
default_value_t = false,
7777
required = false
7878
)]
79-
pub copy: bool,
79+
pub copy_to_clipboard: bool,
80+
81+
#[arg(
82+
long,
83+
help = "Print the commit message in JSON format",
84+
default_value_t = false,
85+
required = false
86+
)]
87+
pub json: bool,
8088

8189
#[arg(
8290
long,
8391
help = "Print the commit message in a table format",
84-
default_value_t = true,
92+
default_value_t = false,
93+
required = false
94+
)]
95+
pub no_table: bool,
96+
97+
#[arg(
98+
long,
99+
help = "Check current environment variables for OpenAI API key and model name",
100+
default_value_t = false,
85101
required = false
86102
)]
87-
pub print_table: bool,
103+
pub check_env: bool,
88104

89105
#[arg(
90106
long,

src/git/message.rs

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
/*!
2-
* Copyright (c) 2025 Hangzhou Guanwaii Technology Co,.Ltd.
2+
* Copyright (c) 2025 Hangzhou Guanwaii Technology Co., Ltd.
33
*
44
* This source code is licensed under the MIT License,
55
* which is located in the LICENSE file in the source tree's root directory.
@@ -9,7 +9,7 @@
99
* File Created: 2025-10-16 15:06:58
1010
*
1111
* Modified By: mingcheng <[email protected]>
12-
* Last Modified: 2025-10-16 17:03:29
12+
* Last Modified: 2025-10-17 18:22:55
1313
*/
1414

1515
use crate::git::repository::Repository;
@@ -21,6 +21,7 @@ use tracing::trace;
2121
/// A commit message consists of:
2222
/// - `title`: The first line (subject line), typically 50-72 characters
2323
/// - `content`: The body of the commit message with detailed description
24+
#[derive(Debug, serde::Serialize)]
2425
pub struct GitMessage {
2526
pub title: String,
2627
pub content: String,

src/git/repository.rs

Lines changed: 7 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,7 @@
99
* File Created: 2025-10-16 15:07:05
1010
*
1111
* Modified By: mingcheng <[email protected]>
12-
* Last Modified: 2025-10-16 22:55:18
12+
* Last Modified: 2025-10-17 18:27:34
1313
*/
1414

1515
use git2::{Repository as _Repo, RepositoryOpenFlags, Signature};
@@ -199,13 +199,12 @@ impl Repository {
199199
let mut result = Vec::new();
200200
diff.print(git2::DiffFormat::Patch, |delta, _hunk, line| {
201201
// Check if the file should be excluded
202-
if let Some(path) = delta.new_file().path() {
203-
if let Some(filename) = path.file_name() {
204-
if excluded_files.contains(&filename.to_string_lossy().as_ref()) {
205-
warn!("skipping excluded file: {}", filename.to_string_lossy());
206-
return true; // Skip this file
207-
}
208-
}
202+
if let Some(path) = delta.new_file().path()
203+
&& let Some(filename) = path.file_name()
204+
&& excluded_files.contains(&filename.to_string_lossy().as_ref())
205+
{
206+
warn!("skipping excluded file: {}", filename.to_string_lossy());
207+
return true; // Skip this file
209208
}
210209

211210
// Add non-empty lines to result

src/main.rs

Lines changed: 39 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -12,7 +12,7 @@
1212
* Last Modified: 2025-09-26 15:45:37
1313
*/
1414

15-
use aigitcommit::cli::{print_table, Cli};
15+
use aigitcommit::cli::{Cli, print_table};
1616
use aigitcommit::git::message::GitMessage;
1717
use aigitcommit::git::repository::Repository;
1818
use aigitcommit::openai;
@@ -28,7 +28,26 @@ use std::error::Error;
2828
use std::fs::File;
2929
use std::io::Write;
3030
use std::{env, fs};
31-
use tracing::{debug, trace, Level};
31+
use tracing::{Level, debug, trace};
32+
33+
/// The output format for the commit message
34+
#[derive(Debug)]
35+
enum OutPutFormat {
36+
Stdout,
37+
Table,
38+
Json,
39+
}
40+
41+
/// Detect the output format based on the command line arguments
42+
fn detect_output_format(cli: &Cli) -> OutPutFormat {
43+
if cli.json {
44+
return OutPutFormat::Json;
45+
} else if cli.no_table {
46+
return OutPutFormat::Stdout;
47+
}
48+
49+
OutPutFormat::Table
50+
}
3251

3352
#[tokio::main]
3453
async fn main() -> std::result::Result<(), Box<dyn Error>> {
@@ -146,16 +165,26 @@ async fn main() -> std::result::Result<(), Box<dyn Error>> {
146165

147166
let message: GitMessage = GitMessage::new(&repository, title, content, need_signoff)?;
148167

149-
// Write the commit message to stdout
150-
trace!("write to stdout, and finish the process");
151-
if cli.print_table {
152-
print_table(&message.title, &message.content);
153-
} else {
154-
writeln!(std::io::stdout(), "{}", message)?;
155-
}
168+
// Decide the output format based on the command line arguments
169+
match detect_output_format(&cli) {
170+
OutPutFormat::Stdout => {
171+
// Write the commit message to stdout
172+
trace!("write to stdout, and finish the process");
173+
writeln!(std::io::stdout(), "{}", message)?;
174+
}
175+
OutPutFormat::Json => {
176+
// Print the commit message in JSON format
177+
let json = serde_json::to_string_pretty(&message)?;
178+
writeln!(std::io::stdout(), "{}", json)?;
179+
}
180+
OutPutFormat::Table => {
181+
// Default print message in table
182+
print_table(&message.title, &message.content);
183+
}
184+
};
156185

157186
// Copy the commit message to clipboard if the --copy option is enabled
158-
if cli.copy {
187+
if cli.copy_to_clipboard {
159188
let mut clipboard = Clipboard::new()?;
160189
clipboard.set_text(format!("{}", &message))?;
161190
writeln!(

src/openai.rs

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -21,9 +21,9 @@ use askama::Template;
2121
use async_openai::config::OPENAI_API_BASE;
2222
use async_openai::error::OpenAIError;
2323
use async_openai::{
24+
Client,
2425
config::OpenAIConfig,
2526
types::{ChatCompletionRequestMessage, CreateChatCompletionRequestArgs},
26-
Client,
2727
};
2828
use log::trace;
2929
use reqwest::header::{HeaderMap, HeaderValue};
@@ -88,11 +88,11 @@ impl OpenAI {
8888

8989
let request_timeout =
9090
env::var("OPENAI_REQUEST_TIMEOUT").unwrap_or_else(|_| String::from(""));
91-
if !request_timeout.is_empty() {
92-
if let Ok(timeout) = request_timeout.parse::<u64>() {
93-
trace!("Setting request timeout to: {request_timeout}ms");
94-
http_client_builder = http_client_builder.timeout(Duration::from_millis(timeout));
95-
}
91+
if !request_timeout.is_empty()
92+
&& let Ok(timeout) = request_timeout.parse::<u64>()
93+
{
94+
trace!("Setting request timeout to: {request_timeout}ms");
95+
http_client_builder = http_client_builder.timeout(Duration::from_millis(timeout));
9696
}
9797

9898
// Set up timeout and build the HTTP client

0 commit comments

Comments
 (0)