-
Notifications
You must be signed in to change notification settings - Fork 356
/
signing.asc
205 lines (156 loc) · 6.48 KB
/
signing.asc
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
[[_signing]]
=== 签署工作
Git 虽然是密码级安全的,但它不是万无一失的。
如果你从因特网上的其他人那里拿取工作,并且想要验证提交是不是真正地来自于可信来源,
Git 提供了几种通过 GPG 来签署和验证工作的方式。
==== GPG 介绍
首先,在开始签名之前你需要先配置 GPG 并安装个人密钥。
[source,console]
----
$ gpg --list-keys
/Users/schacon/.gnupg/pubring.gpg
---------------------------------
pub 2048R/0A46826A 2014-06-04
uid Scott Chacon (Git signing key) <[email protected]>
sub 2048R/874529A9 2014-06-04
----
如果你还没有安装一个密钥,可以使用 `gpg --gen-key` 生成一个。
[source,console]
----
$ gpg --gen-key
----
一旦你有一个可以签署的私钥,可以通过设置 Git 的 `user.signingkey` 选项来签署。
[source,console]
----
$ git config --global user.signingkey 0A46826A
----
现在 Git 默认使用你的密钥来签署标签与提交。
==== 签署标签
如果已经设置好一个 GPG 私钥,可以使用它来签署新的标签。
所有需要做的只是使用 `-s` 代替 `-a` 即可:
[source,console]
----
$ git tag -s v1.5 -m 'my signed 1.5 tag'
You need a passphrase to unlock the secret key for
user: "Ben Straub <[email protected]>"
2048-bit RSA key, ID 800430EB, created 2014-05-04
----
如果在那个标签上运行 `git show`,会看到你的 GPG 签名附属在后面:
[source,console]
--------
$ git show v1.5
tag v1.5
Tagger: Ben Straub <[email protected]>
Date: Sat May 3 20:29:41 2014 -0700
my signed 1.5 tag
-----BEGIN PGP SIGNATURE-----
Version: GnuPG v1
iQEcBAABAgAGBQJTZbQlAAoJEF0+sviABDDrZbQH/09PfE51KPVPlanr6q1v4/Ut
LQxfojUWiLQdg2ESJItkcuweYg+kc3HCyFejeDIBw9dpXt00rY26p05qrpnG+85b
hM1/PswpPLuBSr+oCIDj5GMC2r2iEKsfv2fJbNW8iWAXVLoWZRF8B0MfqX/YTMbm
ecorc4iXzQu7tupRihslbNkfvfciMnSDeSvzCpWAHl7h8Wj6hhqePmLm9lAYqnKp
8S5B/1SSQuEAjRZgI4IexpZoeKGVDptPHxLLS38fozsyi0QyDyzEgJxcJQVMXxVi
RUysgqjcpT8+iQM1PblGfHR4XAhuOqN5Fx06PSaFZhqvWFezJ28/CLyX5q+oIVk=
=EFTF
-----END PGP SIGNATURE-----
commit ca82a6dff817ec66f44342007202690a93763949
Author: Scott Chacon <[email protected]>
Date: Mon Mar 17 21:52:11 2008 -0700
changed the version number
--------
==== 验证标签
要验证一个签署的标签,可以运行 `git tag -v <tag-name>`。
这个命令使用 GPG 来验证签名。
为了验证能正常工作,签署者的公钥需要在你的钥匙链中。
[source,console]
----
$ git tag -v v1.4.2.1
object 883653babd8ee7ea23e6a5c392bb739348b1eb61
type commit
tag v1.4.2.1
tagger Junio C Hamano <[email protected]> 1158138501 -0700
GIT 1.4.2.1
Minor fixes since 1.4.2, including git-mv and git-http with alternates.
gpg: Signature made Wed Sep 13 02:08:25 2006 PDT using DSA key ID F3119B9A
gpg: Good signature from "Junio C Hamano <[email protected]>"
gpg: aka "[jpeg image of size 1513]"
Primary key fingerprint: 3565 2A26 2040 E066 C9A7 4A7D C0C6 D9A4 F311 9B9A
----
如果没有签署者的公钥,那么你将会得到类似下面的东西:
[source,console]
----
gpg: Signature made Wed Sep 13 02:08:25 2006 PDT using DSA key ID F3119B9A
gpg: Can't check signature: public key not found
error: could not verify the tag 'v1.4.2.1'
----
[[_signing_commits]]
==== 签署提交
在最新版本的 Git 中(v1.7.9 及以上),也可以签署个人提交。
如果相对于标签而言你对直接签署到提交更感兴趣的话,所有要做的只是增加一个 `-S` 到 `git commit` 命令。
[source,console]
----
$ git commit -a -S -m 'signed commit'
You need a passphrase to unlock the secret key for
user: "Scott Chacon (Git signing key) <[email protected]>"
2048-bit RSA key, ID 0A46826A, created 2014-06-04
[master 5c3386c] signed commit
4 files changed, 4 insertions(+), 24 deletions(-)
rewrite Rakefile (100%)
create mode 100644 lib/git.rb
----
`git log` 也有一个 `--show-signature` 选项来查看及验证这些签名。
[source,console]
----
$ git log --show-signature -1
commit 5c3386cf54bba0a33a32da706aa52bc0155503c2
gpg: Signature made Wed Jun 4 19:49:17 2014 PDT using RSA key ID 0A46826A
gpg: Good signature from "Scott Chacon (Git signing key) <[email protected]>"
Author: Scott Chacon <[email protected]>
Date: Wed Jun 4 19:49:17 2014 -0700
signed commit
----
另外,也可以配置 `git log` 来验证任何找到的签名并将它们以 `%G?` 格式列在输出中。
[source,console]
----
$ git log --pretty="format:%h %G? %aN %s"
5c3386c G Scott Chacon signed commit
ca82a6d N Scott Chacon changed the version number
085bb3b N Scott Chacon removed unnecessary test code
a11bef0 N Scott Chacon first commit
----
这里我们可以看到只有最后一次提交是签署并有效的,而之前的提交都不是。
在 Git 1.8.3 及以后的版本中,`git merge` 与 `git pull` 可以使用
`--verify-signatures` 选项来检查并拒绝没有携带可信 GPG 签名的提交。
如果使用这个选项来合并一个包含未签名或有效的提交的分支时,合并不会生效。
[source,console]
----
$ git merge --verify-signatures non-verify
fatal: Commit ab06180 does not have a GPG signature.
----
如果合并包含的只有有效的签名的提交,合并命令会提示所有的签名它已经检查过了然后会继续向前。
[source,console]
----
$ git merge --verify-signatures signed-branch
Commit 13ad65e has a good GPG signature by Scott Chacon (Git signing key) <[email protected]>
Updating 5c3386c..13ad65e
Fast-forward
README | 2 ++
1 file changed, 2 insertions(+)
----
也可以给 `git merge` 命令附加 `-S` 选项来签署自己生成的合并提交。
下面的例子演示了验证将要合并的分支的每一个提交都是签名的并且签署最后生成的合并提交。
[source,console]
----
$ git merge --verify-signatures -S signed-branch
Commit 13ad65e has a good GPG signature by Scott Chacon (Git signing key) <[email protected]>
You need a passphrase to unlock the secret key for
user: "Scott Chacon (Git signing key) <[email protected]>"
2048-bit RSA key, ID 0A46826A, created 2014-06-04
Merge made by the 'recursive' strategy.
README | 2 ++
1 file changed, 2 insertions(+)
----
==== 每个人必须签署
签署标签与提交很棒,但是如果决定在正常的工作流程中使用它,你必须确保团队中的每一个人都理解如何这样做。
如果没有,你将会花费大量时间帮助其他人找出并用签名的版本重写提交。
在采用签署成为标准工作流程的一部分前,确保你完全理解 GPG 及签署带来的好处。