diff --git a/.gitea/ai-review/exclusions.json b/.gitea/ai-review/exclusions.json index d5d5caf..b8c4d13 100644 --- a/.gitea/ai-review/exclusions.json +++ b/.gitea/ai-review/exclusions.json @@ -28,5 +28,29 @@ "role": "Rogue", "original_finding": "run 函式 maxBuffer 設為 64MB,git diff 內容極大時易引發 OOM,建議改用 stream。", "reason": "run() 採同步 spawnSync 為刻意設計(所有呼叫端皆同步取用 result.stdout);maxBuffer 為上限保護而非預先配置,僅在輸出達該量時才佔用;傳給 opencode 的 diff 已於 index.js 以 maxDiffChars 截斷。改為 stream 屬大規模架構重構,牽涉設計取捨。" + }, + { + "location": "app/lib/git.js:39, 52", + "role": "Mage", + "original_finding": "多次使用 `git config --global` 修改全域設定,可能導致 ~/.gitconfig 無限膨脹、污染環境;safe.directory 使用萬用字元 `*` 過於寬鬆,建議改用 --local。", + "reason": "action 於每次執行皆在全新且即拋的 Docker 容器內運行,~/.gitconfig 不跨執行保留,無「無限膨脹」問題。safe.directory 基於安全考量 git 刻意忽略 repo-local 設定,必須寫在 global/system,無法改用 `--local`;在 owner 不可預期的 CI checkout 工作區使用 `*` 是 runner 的標準做法(如 actions/checkout 亦同)。user.name/email 已使用 --local。" + }, + { + "location": "app/index.js:183", + "role": "Assassin", + "original_finding": "錯誤處理中的 maskSecrets 基於字串取代,可能無法處理所有 Token 變體導致敏感資訊洩漏;建議禁止輸出原始錯誤物件。", + "reason": "maskSecrets 以子字串比對取代,能涵蓋 token 出現於錯誤訊息的各處(含 URL 內嵌 `oauth2:@`),實際洩漏向量(http.extraheader 帶入的原始 token)已被遮蔽。URL 編碼/base64 變體不會出現在本專案的錯誤路徑;完全禁止輸出 err.stack 會嚴重損及 CI 除錯能力,取捨上以遮蔽 token 為宜。" + }, + { + "location": "app/index.js:7", + "role": "Leo", + "original_finding": "函式 main() 承擔過多責任,違反單一職責原則,建議抽離 ConflictManager 並封裝 Gitea API 互動。", + "reason": "屬主觀重構偏好而非缺陷;程式已分層為 Git/GiteaClient/OpenCode 三個職責清楚的類別,main() 僅負責編排流程,長度與複雜度可控,無立即重構必要。" + }, + { + "location": "app/index.js:37", + "role": "Rogue", + "original_finding": "在 ahead 為 0 時,仍執行昂貴的 diff 採集與分析;建議先執行 countAheadCommits,若 ahead === 0 則直接終止。", + "reason": "現有程式已於 `countAheadCommits` 後立即檢查,`if (ahead === 0) { ...; return; }`(index.js:28-32)早於 diff 採集(index.js:36 起)就終止,與建議行為一致,屬誤報。" } ] diff --git a/.gitea/ai-review/findings.json b/.gitea/ai-review/findings.json index ecdeca3..3722013 100644 --- a/.gitea/ai-review/findings.json +++ b/.gitea/ai-review/findings.json @@ -20,48 +20,6 @@ "problem": "detectConflict 函式在執行 git 合併失敗後的 abort 嘗試若失敗,會導致工作區殘留錯誤狀態,且未經測試驗證。", "suggestion": "增加測試案例來模擬 git 合併失敗與 abort 失敗的場景,確保狀態正確復原。" }, - { - "level": "warning", - "role": "Mage", - "location": "app/lib/git.js:39, 52", - "problem": "多次使用 `git config --global` 修改全域設定,可能導致 `~/.gitconfig` 無限膨脹、污染環境或導致並行 Git 作業行為異常。", - "suggestion": "改用 `--local` 設定,或在執行 Git 指令時透過 `-c` 傳入設定,避免修改全域組態。同時限制 `safe.directory` 只針對特定的工作目錄,而非萬用字元 `*`。" - }, - { - "level": "warning", - "role": "Mage", - "location": "app/lib/opencode.js:106, 111", - "problem": "將 `HOME` 環境變數硬編碼為 `/root`;`opencode run` 設定了 5 分鐘 timeout 但未處理發生時的清理。", - "suggestion": "動態獲取當前使用者的家目錄;增加對 timeout 的特殊處理,並確保 finally 區塊正確清理所有狀態。" - }, - { - "level": "warning", - "role": "Leo", - "location": "app/lib/opencode.js:34, 46, 143", - "problem": "暫存目錄與設定檔未清理造成空間堆積;頻繁 I/O;且複雜的 JSON 解析邏輯不僅脆弱且維護成本高。", - "suggestion": "在 finally 區塊中統一實作檔案系統清理;將設定檔產生邏輯快取;優化 Prompt 嚴格要求 LLM 僅輸出標準 JSON,並使用原生 `JSON.parse`。" - }, - { - "level": "warning", - "role": "Mage", - "location": "app/index.js:84, 176", - "problem": "分支名稱長度可能超出 Git 限制,或字元替換後導致名稱無效。", - "suggestion": "確保 resolveBranch 長度不超過 Git 建議限制,並對最終產生的分支名稱進行正規化。" - }, - { - "level": "warning", - "role": "Assassin", - "location": "app/index.js:183", - "problem": "錯誤處理中的 `maskSecrets` 基於字串取代,可能無法處理所有 Token 變體導致敏感資訊洩漏。", - "suggestion": "確保 `maskSecrets` 處理所有可能的變體,並在生產環境中禁止輸出原始錯誤物件。" - }, - { - "level": "warning", - "role": "Leo", - "location": "app/index.js:7", - "problem": "函式 `main()` 承擔過多責任,違反單一職責原則。", - "suggestion": "將職責拆解,抽離衝突處理邏輯為 `ConflictManager`,並封裝 Gitea API 互動。" - }, { "level": "warning", "role": "Maya", @@ -89,12 +47,5 @@ "location": "app/lib/opencode.js:77", "problem": "呼叫外部指令時傳遞整個 `process.env`,導致敏感環境變數暴露。", "suggestion": "應明確篩選並只傳遞必要環境變數。" - }, - { - "level": "info", - "role": "Rogue", - "location": "app/index.js:37", - "problem": "在 `ahead` 為 0 時,仍執行昂貴的 diff 採集與分析。", - "suggestion": "先執行 `countAheadCommits`,若 `ahead === 0` 則直接終止。" } ]