我想在我的存储库中列出所有轻量级标签;我能想到的最好的方法是将git for-each-ref
,grep
和cut
结合起来,但看起来好像很有点......
(虽然我们在这里,但我们不妨谈论注释标签的相同内容:有人肯定会在某处对此感到疑惑。)
修改
通过lightweight
标记,我的意思是那些不引用标记对象的标记引用。 (换句话说,未注释的标签。)
答案 0 :(得分:20)
所有轻量级标记都在refs/tags/
命名空间中,可以枚举,例如:
git for-each-ref --format '%(refname:short)' refs/tags/
或:
git show-ref --tags
对于带注释的标签,嗯,这里的技巧 - 它也会影响“轻量级”标签部分 - 带注释的标签实际上是git存储库中的一个对象,但是,这是一个轻量级的指向该对象的标记,它允许您通过其标记名称获取带注释的标记。 1 所以它实际上是对:一个轻量级标签,加上in-repo带注释的标签对象,使它“不是一个轻量级标签”,除了那个顽固的事实,它同时是一个轻量级标签!
因此,它归结为:找到所有轻量级标记,然后可选择只选择指向提交的标记或指向标记对象的标记,具体取决于您想要的行为,然后继续发出标签名称。
在git-for-each-ref
文档中有一个很长的例子,即在--format
字符串中编写完整的脚本并使用eval
来执行它(或者你可以管道sh
到git for-each-ref
执行,以一个额外的过程为代价)。我通常发现将while read ...
的输出传递到git for-each-ref refs/tags/ --format '%(objecttype) %(refname:short)' |
while read ty name; do [ $ty = commit ] && echo $name; done
循环更简单:
git for-each-ref refs/tags/ --format '%(objecttype) %(refname:short)' |
while read ty name; do [ $ty = tag ] && echo $name; done
可打印所有仅限轻量级标记。
与:比较:
tree
打印所有带注释的标签(或者更准确地说,是“带注释的轻量级”标签)。
请注意,标记可以(可以想象 - 现在没有实际的用例,据我所知)指向除了提交或标记之外的其他内容;您是否要使用直接指向blob
或annotag
的标记执行某些操作。
1 如果没有轻量级标记,您将无法使用名称annotag
引用带注释的标记git fsck
- 而不是经过{{1}}的所有搜索工作{1}}用于查找悬空物体,至少。此外,如果删除轻量级标记,则带注释的标记对象可能会被垃圾收集。只要第一个标记对象具有外部名称,您就可以使一个标记对象指向另一个标记对象以将其保留在repo中(即,禁止gc)而不使用第二个标记对象的外部名称。尽管如此,这绝对是一件奇怪的事。
有趣的是,带注释的标签的内部格式包含外部名称,因此可以使用此技术来保护“旧的”带注释的标签,通过删除它们的轻量级标签来隐藏它们,然后再恢复原始的轻量级标签。是否有人可以为此提出使用,但是......: - )
答案 1 :(得分:0)
总结其他答案及其注释(如果您使用的是bash)
function git-lightweight-tags() {
git for-each-ref refs/tags/ --format '%(objecttype) %(refname:short)' | awk '$1 == "commit" {print $2}' ;
}
答案 2 :(得分:0)
仅列出轻量级标签:
git for-each-ref refs/tags | grep commit
要仅列出带注释的标签:
git for-each-ref refs/tags | grep -v commit
说明:
git for-each-ref
列出所有引用:heads、remotes、stash 和 tags
git for-each-ref refs/tags
仅列出 标签 引用。
| grep commit
只列出那些包含单词 commit 的行。这些是指向提交的标签,因此是轻量级标签。
| grep -v commit
仅列出那些不包含 commit 一词的行。这些是指向标签的标签,因此是带注释的标签。