はじめに:gitのcommitterは簡単に偽装できます!
committerはめちゃくちゃ簡単に偽装することができてしまいます。
実際に違うユーザーに化けてcommit・pushしてみます。
やり方は.gitconfigに設定されているusername, emailを変更するだけです。
[user]
name = nisemono
email = nisemono@email.com
これだけで、簡単にnisemonoとしてcommitすることができます。
今回は架空のemail, usernameを用いていますが、実際に存在する他人のemail、usernameを設定すればその人物にcommitを偽装できてしまいます。
これに対応するためにgitでは署名付きコミットというものが用意されています。
GPG、SSH、または S/MIME を使用して、ローカルでタグとコミットに署名できます。 これらのタグやコミットは GitHub で検証済みとしてマークされているため、他のユーザーはその変更が信頼できるソースからのものであると確信できます。
署名付きコミットをすることでコミットにverifiedマークがつき、そのコミットの信頼性を確保することができます。
何よりマークついてかっこいいです。
本記事では署名付きコミットを実現するまでの過程をご紹介します。
GPGでの作成もできますが、sshキーでもSigning keyの設定ができますので、今回はsshキーでの設定方法をご紹介します。
ただし、ssh鍵での署名はgit v2.34からの対応らしいので、必要によってアップデートをしてください。
key作成・登録
ssh-keygenを実行して、keyを生成します。-C
オプションにメールアドレスを入れます。
ssh-keygen -t ed25519 -C "sample@email.com"
生成したキーをsiging keys として登録します。
Githubのコンソールにて、settings -> SSH and GPG keysにて、公開鍵を登録してください。
cat ~/.ssh/id_ed25519.pub | pbcopy
Key typeは"Signing Key"にして、設定します。
~/.ssh/allowed_singers作成
続いて、allowed_signersというファイルを作成します。
このファイルで、SSH署名付きコミットやタグを検証するときに許可された署名者の公開鍵リストを格納したファイルを指定します。
作成するパスはどこでも良いですが、自分は.sshの中に入れてしまっています。
以下のフォーマットで設定します。
<email> <pubkey>
設定例は以下です。
user@email.com ssh-ed25519 AAAAC3Nz...
.gitconfig編集
続いて、.gitconfigを編集します。
追加するのは以下4点です。
- user.sigingekey
- gpg
- gpg.ssh
- commit
[user]
name = user
email = user@email.com
+ signingkey = Users/user/.ssh/id_ed25519.pub
+[gpg]
+ format = ssh
+[gpg "ssh"]
+ allowedSignersFile = /Users/user/.ssh/allowed_signers
+[commit]
+ gpgsign = true
ここまでの設定で、署名ができたと思います!
動作検証
正しく署名コミットができるか確認してみます。
ここまでの設定を行ったのちに任意のcommitをして、以下のコマンドを叩きます。
git log --show-signature
すると、正しく設定されていれば以下のように正しく署名ができていることがわかります。
commit 11d3a20d502232dd4eeca71c234d02b9a317 (origin/main)
+ Good "git" signature for user@email.com with ED25519 key SHA256:XXXXXX
Author: ohnuma-haw <user@email.com>
Date: Mon Jan 1 00:00:00 2024 +0900
sample commit
pushをすることでverifiedマークがつくことを確認できると思います!
(余談) lazygitでの署名付きcommit
ここからはlazygitを使っている方への設定情報です。
lazygitでは.gitconfig内でcommit.gpgsignをtrueに設定するとcommit時にエラーになります。
これに関しては上記Issueで紹介されているように、config.yamlで以下の設定をすることで回避できます。
git:
overrideGpg: true
(余談)複数アカウントでの署名
Githubでは同一のssh鍵を複数アカウントに設定することはできませんので、アカウントごとに個別のキーを生成する必要があります。
commit毎にどのキーを使って署名をするかを意識するのはめんどくさいです。
そんな時には.gitconfig内で設定できるIncludeIfが便利です。
ぜひ、以下の記事をご覧いただければと思います。