不要在存储库中克隆较新的标签

Don't clone newer tags in a repository

我克隆了很多存储库,所以我制作了一个脚本来检查预期标签是否与我拥有的标签相同。如果没有,它将 git pull origin newtag。但有时预期标签比远程中的最后一个标签更旧,即使两个标签之间没有任何变化(但新标签是因为其他回购收到变化而创建的)。但是随着 git 的拉动,我得到了最新的标签,而不是预期的标签。所以脚本将再次 git pull origin newtag,即使我已经有了它。要检查我所在的当前标签,我使用 git describe --tags --exact-match

TL;DR: 只是不要再获取了

如果你避免获取,你将避免为现有提交选择新名称。如果那不合适,您只需要自己将标签名称保存在某个地方。如果找到新标签,可以使用 git rev-parse:

检测到它指向同一个提交
git rev-parse android-8.0.0_r4^{commit}
git rev-parse android-8.0.0_r12^{commit}

会在这里产生相同的散列。

详细说明

标签不一定有年龄——Git的"annotated tags"确实有时间戳,但轻量级标签只是为现有提交添加一个新名称并且没有自己的时间戳——并且即使他们这样做了,在处理分支时,单一的线性度量也很少足够。

git clone -b android-8.0.0_r4 https://android.googlesource.com/platform/build/blueprint

在您的特定示例中,如果我们查看 https://android.googlesource.com/platform/build/blueprint,我们会发现标签 8.0.0_r48.0.0_r12 是带注释的标签,但实际上指向同一个提交,4fcacd3d193f1e1dfb0f5a9e818dd895eca45427.

标签 8.0.0_r11 也指向同一个提交(点击 https://android.googlesource.com/platform/build/blueprint/+/android-8.0.0_r11 查看;将 r11 更改为 r4r8 查看每个他们选择的网页显示格式中的注释标签)。

换句话说,您签出这些标签中的哪一个都无关紧要:您获得的所有三个标签都具有相同的源代码。如果您想记住您使用哪个标签执行 git checkout 操作(示例中 git clone 的最后一步),您必须自己将其保存在某个地方。相反,Git 保存了这个检出提交 4fcacd3d193f1e1dfb0f5a9e818dd895eca45427 的事实,并且 git describe --tags 查找导致 4fcacd3d193f1e1dfb0f5a9e818dd895eca45427 的标记。它找到很多,然后选择一个。在这里,如果它正在查看带注释的标签,它确实会使用带注释的标签日期。

每当你运行git fetchgit pull的前半部分),Git获得新对象;可能包含新标签。避免获取新标签(任何类型,轻量级或带注释的)的主要方法是避免获取。

如果为时已晚而无法避免选择新标签,请注意您可以使用 git for-each-ref refs/tags 查看 所有 标签(或所有带注释的标签)和将每个标记解析为其目标对象(通常是提交),或具体到提交(如果标记指向其他对象类型,可能会在之前的标记之后)。