如何在不丢失标记消息的情况下更改带注释Git标记的日期?

如何在不丢失标记消息的情况下更改带注释Git标记的日期?,git,git-tag,Git,Git Tag,我正在为我的Git项目创建发行版,方法是向我的master分支添加标记 由于我没有按时间顺序添加标记,Git GUI以非时间顺序显示我的标记,v0.1.0是最近的标记,前面是v0.1.2和v0.1.1 对一个类似问题的公认答案表明。不幸的是,我发现这个方法没有保存标签描述,导致我丢失了每个标签的发行说明。(谢天谢地,我能够从备份中恢复我的历史记录) 如何编辑带注释的标记,使其与标记的提交日期相同?(不删除我的标签信息) 只需创建一个新的带注释的标记,指向现有的提交。(另见) 正如您所观察到的,提

我正在为我的Git项目创建发行版,方法是向我的
master
分支添加标记

由于我没有按时间顺序添加标记,Git GUI以非时间顺序显示我的标记,
v0.1.0
是最近的标记,前面是
v0.1.2
v0.1.1

对一个类似问题的公认答案表明。不幸的是,我发现这个方法没有保存标签描述,导致我丢失了每个标签的发行说明。(谢天谢地,我能够从备份中恢复我的历史记录)

如何编辑带注释的标记,使其与标记的提交日期相同?(不删除我的标签信息)

只需创建一个新的带注释的标记,指向现有的提交。(另见)

正如您所观察到的,提供的答案中的缺陷在于它没有保留标记的消息。1一个真正健壮的脚本会尝试重新创建消息,同时对PGP签名进行一些处理。PGP签名的问题在于,您唯一可以自动执行的操作就是删除它们

不幸的是,它有47行shell脚本(并且依赖于额外的shell脚本帮助程序)。您可能希望重写它,以确保标记存在并且是带注释的标记,并保持相同的提交ID和标记名称。2

如果您有一个带注释的标记,甚至是PGP签名的标记,那么您可以创建一个新的带注释的PGP签名标记。也就是说,您可以直接使用
git-tag
而不是使用
git-filter-brach
使用的管道
git-hash-object-t-tag-w--stdin
命令,甚至
git-mktag
。使用链接到的答案中概述的技术在新标记对象内设置日期

要保存标记的消息,请使用
git cat file-p$tag
(或
git cat file tag$tag
)并去掉第一个空行的内容:

$ git cat-file tag v2.9.4 | sed '1,/^$/d'
Git 2.9.4
-----BEGIN PGP SIGNATURE-----
Version: GnuPG v1

iQIcBAABAgAGBQJZC/1WAAoJELC16IaWr+bLreYP/0HhgbODcdFE9tFtxHUMwqVz
kw6E2HtKRugb1hJulo+WNk40CL3Fg/YvP2CWaqsOA6woBOofLMGv1VzT8kkavyiM
UCL4Gjcm4rHaUrln7Gr+gIfEdlCT3cbJ7cNoEYRegbxd0vG/M/AyS4kOLfLQc7LQ
TMO5yqq1wJRJO5WhwqbW6XDwhsjWnQhKuobWpVr+AB1SPNQfWlWVnpBAdhseV2Ui
Q79GXhxSYT+es72CuhFbQc/Crn0iS0sFo5ljA9baDUzj7SOqfcDhNJFEF+xthIcN
DOFgHyUAoTKSIreMX5JO5tFCYDiAfNtkTd+8BLbfvsc2/zC+Qv0UxXh8aH3DzHIV
qsyZILXCjtkaxtqZfDIgE+4u8nPAuO/9ubJH9eunz1bbK2rJAMPeIo0Kmp6yRHIb
gvgG6gCR29TdqdgZN22UjsV94Bq/PqWKb2dN6NAVIRDi/TOhK8woLxfVdNKyT68s
3edTe/XzKVo18PediSt6KgzXJpUuIHJlE5IWq1cKysElw4fv5jOiHBWvH9LFRAXS
JTLXv6sS5Bk+KB2sgbTvoLwh0qC7g+cxyeBInqbIVP1spGLAsAJADHMmPJxx3yt3
PfsiARSRgoDh5J45smZPgJj/kMUg78SKXyBc3GgfH48tY5rAwVDe3TMMjEFVxa7n
zAbtKPw4yovxWW4/3WTj
=8LG8
-----END PGP SIGNATURE-----
例如,您可以将其转储到一个临时文件中,并使用
git tag-F
。但是,正如您在本例中看到的,这个特定的标记是PGP签名的。虽然Git将为新标记使用相同的数据,但签名将无效


1同样,它使用了一个相当笨拙的构造来查找标记所指向的提交。使用
git rev parse${tag}^{commit}
将是一种方法,这可以让您验证标记是否也指向commit


2请记住,
git filter分支
有一个
--tag name filter
参数,因此它在重写标记名时会更改标记名。它还进行提交复制,因此它必须将旧的提交哈希映射到适当的新提交哈希。这两种情况在您的情况下都不正确:您希望标记名保持不变,目标提交对象保持不变。您只需要创建一个新的标记对象,然后更新标记的引用部分以使用新对象。

您的标记消息是多行的吗?对于单行消息,我可以修改以保留消息(实际上,提取并重新应用它们)。但对于多行,这是一个问题,至少对我来说是这样,因为我的标记是有签名的,并且我无法提取没有签名的多行消息。我的标记用于列出版本之间的更改。