From 3aa9a46fbaafb51276f7c54397a43f02564aaff8 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E5=BC=A0=E5=AE=B6=E8=AE=AD?= Date: Tue, 28 Jul 2026 10:45:57 +0800 Subject: [PATCH] =?UTF-8?q?=E4=BB=A3=E7=A0=81=E4=BC=98=E5=8C=96=E6=8F=90?= =?UTF-8?q?=E4=BA=A4?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../biz/gitreview/GitReviewService.java | 41 ++++++++++++++++++- 1 file changed, 40 insertions(+), 1 deletion(-) diff --git a/src/main/java/com/example/workutils/biz/gitreview/GitReviewService.java b/src/main/java/com/example/workutils/biz/gitreview/GitReviewService.java index 4cd2b19..4dc87ad 100644 --- a/src/main/java/com/example/workutils/biz/gitreview/GitReviewService.java +++ b/src/main/java/com/example/workutils/biz/gitreview/GitReviewService.java @@ -154,12 +154,51 @@ public class GitReviewService { } } + /** + * 工作区检查时忽略的路径模式。 + * 支持精确匹配文件名(如 ".gitignore")和目录前缀匹配(如 ".codefree/")。 + */ + private static final List STATUS_IGNORE_PATTERNS = Collections.unmodifiableList( + Arrays.asList(".gitignore", ".codefree/")); + private boolean hasLocalChanges(Path projectPath) { CmdResult status = run(projectPath, "git", "status", "--porcelain"); if (!status.ok) { throw new IllegalStateException("检查工作区状态失败: " + status.error); } - return !status.output.trim().isEmpty(); + // status.output 已在 run() 中 trim 过,不要再 trim,否则会删除首行前导空格导致解析错位 + String output = status.output; + if (output == null || output.isEmpty()) { + return false; + } + // 过滤掉忽略的路径,只检查实际关心的改动 + for (String line : output.split("\\R")) { + if (line.isEmpty()) { + continue; + } + // git status --porcelain 每行:前2字符是状态码(XY),第3字符是空格,之后是路径 + // 用正则 "^\S\S\s" 跳过状态码前缀,直接取路径 + String filePath = line.replaceFirst("^.{2}\\s+", ""); + // 处理重命名 "orig -> new",取 newpath + int arrowIdx = filePath.indexOf(" -> "); + if (arrowIdx > 0) { + filePath = filePath.substring(arrowIdx + 4); + } + log.debug("git status 行: [{}], 提取路径: [{}], 是否忽略: {}", line, filePath, isIgnoredPath(filePath)); + if (!isIgnoredPath(filePath)) { + return true; // 存在非忽略的改动,返回 true + } + } + return false; // 所有改动都是被忽略的 + } + + private boolean isIgnoredPath(String path) { + for (String pattern : STATUS_IGNORE_PATTERNS) { + if (path.equals(pattern) || path.startsWith(pattern)) { + return true; + } + } + return false; } private void fetchBranch(Path projectPath, String branch, LogSink logs) {