git for-each-ref 是查看最近活跃分支的最佳方案,因其原生支持按提交时间排序和格式化输出,性能优于遍历分支执行 git log;需用 shell 函数封装别名实现日期筛选,注意时区与字符串比较精度问题。

git branch 列表里怎么只看最近活跃的分支
默认 git branch 不带时间信息,没法直接筛“某天起有提交的分支”。得靠 git for-each-ref 或组合 git log 查每个分支最新提交时间,再过滤。
别名本质是命令缩写,但这里要的是「动态计算+筛选」,不能只用静态 git branch。推荐用 git for-each-ref ——它原生支持按提交时间排序和格式化输出,比遍历每个分支跑 git log -1 快得多。
-
git for-each-ref直接读 .git/refs/,不触发工作区检出,性能好 - 用
--sort=-committerdate倒序排(最新在前),--format控制输出字段 - 时间过滤必须用
%(committerdate:iso8601)这类格式化字段,不能依赖 shell 的 date 命令做字符串比较(时区、格式易错)
定义一个带日期参数的 git 别名
Git 别名不支持位置参数(如 git recent 2024-05-01),所以得用 shell 函数封装。在 ~/.gitconfig 里加:
[alias]
recent = "!f() { git for-each-ref --sort=-committerdate --format='%(refname:short) %(committerdate:iso8601)' refs/heads/ | while read branch datetime; do [[ \"$datetime\" >= \"$1\" ]] && echo \"$branch $datetime\"; done; }; f"
注意:>= 比较依赖 ISO8601 字符串字典序(如 2024-05-01T10:30:00+08:00 >= 2024-05-01 成立),但严格来说只比到日,小时分钟会被忽略。如果真要精确到小时,得用 %(committerdate:format:%Y-%m-%d %H) 并手动解析。
- 别名名必须以
!开头才能调用 shell -
$1是传入的第一个参数,调用时写git recent "2024-05-01"(引号防空格截断) -
refs/heads/是必须限定的 refspace,否则会混入 remotes 或 tags
为什么不用 git log --all --since=... --pretty=format:"%D"?
这个命令看起来能“反向查分支”,但实际不可靠:
-
%D输出的是 ref 名(如origin/main, tag:v1.0),不是当前本地分支名;合并过多次的提交可能关联多个分支,结果重复或遗漏 -
--all扫所有 ref,包括远程分支,--since只过滤提交时间,无法区分“该提交是否属于某个本地分支的 tip” - 没提交的空分支(比如刚
git checkout -b但没 commit)完全不会出现
所以它适合查「哪些提交在某时间段内」,不适合查「哪些本地分支在某时间段内有活跃」。
容易被忽略的时区和边界问题
committerdate:iso8601 输出带时区偏移(如 +08:00),而你传入的 "2024-05-01" 被 shell 当作本地时区字符串处理。如果 Git 配置了 core.autocrlf 或用户时区与提交者不一致,比较可能失效。
- 最稳妥做法:统一用 UTC 时间,把参数写成
"2024-05-01T00:00:00+00:00",并用committerdate:format:%Y-%m-%dT%H:%M:%S%z格式对齐 - 空分支永远不显示——这是设计使然,因为没提交就没 committerdate,
for-each-ref根本不输出它 - 已删但未 prune 的远程跟踪分支(如
origin/dead-branch)不会出现在refs/heads/下,不影响结果
真要包含空分支,只能先 git branch --format='%(refname:short)' 全列出来,再逐个 git log -1 --format=%cd 2>/dev/null || echo "never" 补时间,代价高且没必要。











