SKILL.md
唯讀
名稱
code-simplifier
描述
審查 RTK Rust 程式碼,找出慣用簡化方式。偵測過度工程、不必要的記憶體配置、冗長模式。在不改變行為的前提下套用 Rust 慣用語法。
RTK 程式碼簡化器
審查並簡化 RTK 中的 Rust 程式碼,同時尊重專案的限制。
限制(絕不可簡化掉)
LazyLock正規表達式 — 即使「更簡單」也不能移到函式內- 每個
?上的.context()— 冗長但必須 - 回退到原始指令 — 即使看起來像死碼也絕不能移除
- 結束碼傳遞 — 絕不可簡化成
Ok(()) #[cfg(test)] mod tests— 絕不可移除測試模組
簡化模式
1. 疊代器鏈取代手動迴圈
// ❌ 冗長
let mut result = Vec::new();
for line in input.lines() {
let trimmed = line.trim();
if !trimmed.is_empty() && trimmed.starts_with("error") {
result.push(trimmed.to_string());
}
}
// ✅ 慣用
let result: Vec<String> = input.lines()
.map(|l| l.trim())
.filter(|l| !l.is_empty() && l.starts_with("error"))
.map(str::to_string)
.collect();
2. 字串建構
// ❌ 冗長的 push 迴圈
let mut out = String::new();
for (i, line) in lines.iter().enumerate() {
out.push_str(line);
if i < lines.len() - 1 {
out.push('\n');
}
}
// ✅ join
let out = lines.join("\n");
3. Option/Result 鏈式呼叫
// ❌ 巢狀 match
let result = match maybe_value {
Some(v) => match transform(v) {
Ok(r) => r,
Err(_) => default,
},
None => default,
};
// ✅ 鏈式
let result = maybe_value
.and_then(|v| transform(v).ok())
.unwrap_or(default);
4. 結構解構
// ❌ 重複欄位存取
fn process(args: &MyArgs) -> String {
format!("{} {}", args.command, args.subcommand)
}
// ✅ 解構
fn process(&MyArgs { ref command, ref subcommand, .. }: &MyArgs) -> String {
format!("{} {}", command, subcommand)
}
5. 提早回傳取代巢狀
// ❌ 深度巢狀
fn filter(input: &str) -> Option<String> {
if !input.is_empty() {
if let Some(line) = input.lines().next() {
if line.starts_with("error") {
return Some(line.to_string());
}
}
}
None
}
// ✅ 提早回傳
fn filter(input: &str) -> Option<String> {
if input.is_empty() { return None; }
let line = input.lines().next()?;
if !line.starts_with("error") { return None; }
Some(line.to_string())
}
6. 避免多餘的 clone
// ❌ 不必要的 clone
fn filter_output(input: &str) -> String {
let s = input.to_string(); // 無意義的 clone
s.lines().filter(|l| !l.is_empty()).collect::<Vec<_>>().join("\n")
}
// ✅ 直接使用 &str
fn filter_output(input: &str) -> String {
input.lines().filter(|l| !l.is_empty()).collect::<Vec<_>>().join("\n")
}
7. 單一變體的 match 使用 if let
// ❌ 只為一個變體寫完整 match
match output {
Ok(s) => process(&s),
Err(_) => {},
}
// ✅ if let(但在 RTK 中仍要處理錯誤 — 不要靜默丟棄)
if let Ok(s) = output {
process(&s);
}
// 注意:在 RTK 過濾器中,務必用 eprintln! 處理 Err 並加上回退
RTK 特定檢查
簡化後執行以下檢查:
# 確認沒有回歸
cargo fmt --all && cargo clippy --all-targets && cargo test
# 確認函式中沒有新增正規表達式
grep -n "Regex::new" src/<file>.rs
# 固定且重複使用的模式應放在 `LazyLock<Regex>` 靜態變數中
# 確認生產程式碼中沒有新增 unwrap
grep -n "\.unwrap()" src/<file>.rs
# 只應出現在 #[cfg(test)] 區塊內
不要簡化的項目
static RE: LazyLock<Regex> = LazyLock::new(|| Regex::new(...).unwrap());— 這裡的.unwrap()可接受,因為是初始化時.context("description")?鏈 — 冗長但必要- 回退的 match 分支
Err(e) => { eprintln!(...); raw_output }— 看似多餘但這是安全網 std::process::exit(code)在 run() 結尾 — 看似可以改成Ok(())但其實不行




