签名你的Git提交

目录

  1. 什么是签名Git的提交?

  2. Git提交为什么需要签名?

  3. 如何签名?

  4. 原理解析

  5. 引用

  6. 什么是签名Git的提交?

1. 什么是签名Git的提交?

下图是一张被签名过后的提交(Commit),在Github上的展示:

Verified Commit样例

与普通Commit的区别在于其多了一个Verified标识。这个标识能够被所有有权查看Commit的人看到,从而让大家更加信任这个Commit确实是作者本人提交的。而签名Git的提交正是显示Verified标识的最核心的一步。

2. Git提交为什么需要签名?

简单来说就是避免自己或者他人的Commit被伪造。

如今Git已然成为源码管理领域的重要成员,无数程序员使用Git作为其源码管理工具。那些以Git为核心的各种商业软件,如Github,Gitlab,Bitbucket等,每天接收大量的Git Commits。毫无疑问,这些Commit就是企业最重要的财产。即便如此,对于Commit本身的安全性,却没有得到太多的重视。当然Commit本身只是Git软件下的一个重要概念,保护Git软件的安全一定程度也能够保障Commit的安全,但这绝不是一个好的将Commit的安全放任不管的理由。要知道如果你什么都不做,Repository中的Commit是可以轻易被伪造的。而签名Git的提交正是为了解决这个问题而来。

3. 如何签名?

签名本身是一个简单的动作,尤其是在Git 2.34版本后,支持了SSH签名,对于那些本就使用SSH验证身份的用户就更加容易了。Github也支持使用GPG或者S/MIME进行签名,不过GPG相比于SSH更加复杂,S/MIME则主要用于企业。这里的例子以相对简单的Github上的SSH签名来演示。

生成密钥对

使用以下命令生成Key-Pair[1]

$ ssh-keygen -t ed25519 -C "your_email@example.com"

建议使用ed25519,相比于rsa 4096bit更快的速度,同时安全性也没有损失太多。

配置Github

打开“setting”页面的“SSH and GPG keys”:

Github配置Key截图1
Github配置Key截图2

将上一步生成的公钥xxx.pub中的内容作为Signing Key上传到Github:

Github配置Key截图3

签名部分的配置就完成了,为了在Github上显示Verified标识,还需要打开“SSH and GPG keys”页面里的“Vigilant mode”[2]:

Github严格模式

配置git[3]

配置Git使用SSH来签名Commit

$ git config --global gpg.format ssh

配置Git使用指定路径的公钥作为SSH的Signing Key

$ git config --global user.signingkey ~/.ssh/ed25519.pub

配置IDE(IntelliJ为例)

在commit页面上,点击设置,并勾选“Sign-off commit”,如下图所示:

IntelliJ配置sign-off截图

签名并提交

$ git commit -S -m "this is a signed commit"

Push commit之后就能够在Commit页面中看到Verified标识了:

Commit Verified截图

5. 原理解析

Sign Commit原理解析示意图

  1. 提交者通过准备好的Private Key对Commit的内容摘要(Hash)进行签名,得到一个加密后的摘要值A,并将其存储在Commit信息中。
  2. Github收到提交者上传的Commit后,使用对应的Public Key对Commit中的摘要加密信息A进行解密,得到Hash值
  3. 将这个Hash值与Commit中已存在的hash值进行比较,如果相等,则能够确定该Commit是由私钥所有者提交,也就验证了该Commit。

5. 引用

  1. https://docs.github.com/en/authentication/connecting-to-github-with-ssh/generating-a-new-ssh-key-and-adding-it-to-the-ssh-agenthttps://gnupg.org/
  2. https://docs.github.com/en/authentication/managing-commit-signature-verification/displaying-verification-statuses-for-all-of-your-commits
  3. https://docs.github.com/en/authentication/managing-commit-signature-verification/telling-git-about-your-signing-key