12

--abbrev-commit标志可以与提交对象结合使用git loggit rev-list以显示部分前缀而不是完整的 40 个字符的 SHA-1 哈希。根据Pro Git 书

它默认使用七个字符,但如果需要使它们更长,以保持 SHA-1 明确 [...]

此外,短 SHA 至少有 4 个字符长。仍然根据 Pro Git 书,

通常,八到十个字符足以在一个项目中保持唯一性。

例如,Linux 内核是一个相当大的项目,有超过 450k 的提交和 360 万个对象,没有两个对象的 SHA-1 重叠超过前 11 个字符。

由于防止提交对象的所有前缀哈希之间的任何重叠所需的最长前缀的长度(在 Linux 内核的情况下为 11)是 repo 大小的粗略指标,我想以编程方式确定相应的数量我自己的本地存储库。我怎样才能做到这一点?

4

2 回答 2

19

以下 shell 脚本在本地存储库中运行时,会打印所需的最长前缀长度,以防止该存储库的提交对象的所有前缀哈希之间出现任何重叠。

MAX_LENGTH=4;

git rev-list --abbrev=4 --abbrev-commit --all | \
  ( while read -r line; do
      if [ ${#line} -gt $MAX_LENGTH ]; then
        MAX_LENGTH=${#line};
      fi
    done && printf %s\\n "$MAX_LENGTH"
  )

上次我编辑这个答案时,脚本打印了

于 2015-09-04T20:28:41.050 回答
13

Jubob 的剧本很棒,点赞。

如果你想了解 minimum-commit-hash-length 的分布,你可以运行这个单行:

git rev-list --abbrev=4 --abbrev-commit --all | ( while read -r line; do echo ${#line}; done; ) | sort -n | uniq -c

对于今天的git 项目本身(git-on-git),这会产生如下内容:

 1788 4
35086 5
 7881 6
  533 7
   39 8
    4 9

...产生1788个提交,可以用4 -char 哈希(或更低,这是 Git 的最小缩写)唯一表示,以及4 个提交,需要40 个哈希字符中的9个才能唯一选择它们。

相比之下,一个更大的项目,比如Linux 内核,今天有这个发行版:

6179   5
446463 6
139247 7
10018  8
655    9
41    10
3     11

因此,对于一个包含近 500 万个对象和 60 万次提交的数据库,目前有3 个提交需要 40 个十六进制数字中的 11 个才能将它们与所有其他提交区分开来。

于 2016-05-24T01:49:28.537 回答