When I discover the repository git-blame-someone-else, which you can change the author of the commit, I realized that someone can alter the commit metadata to record anybody name on it. And I was thinking: what if someone use it to alter some commit to assign my name on it, and blame me for the bad code? It could possibly happen, right?
So, signed your commit to prevent commit's metadata changed by anyone but you.
Introduction to git commit signature
You can add a cryptographic signature to the commits that you make with a GPG, SSH, or S/MIME key. With this extra step, you provide the assurance that a commit is originated from you, rather than an impersonator.
Other people can not modify a signed commit if they don't have the private key that is used to sign. And remote repository storage provider like Github, Gitlab can display the status "Verify" on your commit listing on their UI.
Steps to configure commit signing
To sign commits, you will need to configure both on your local machine and the remote git storage provider. Also remember to back up your key so you will not lose it.
In this post, I will guide you to sign commit using GPG key.
Configure with git
I. Create a GPG key
- Please install GPG for your operating system, then generate the key pair with this command
$ gpg --full-gen-key
2. Select the algorithm your key should use, or press
Enter to select the default option,
RSA and RSA (default).
3. Select the key length, in bits. It must be at least
4096 bits, press
Enter to accept the default.
4. Enter the length of time the key should be valid. Press
Enter to specify the default selection, indicating that the key doesn't expire.
5. Verify that your answers are correct, press
6. Enter your name and email address. Note that email address should match that email in your remote repository storage account (ex: github, gitlab) inorder to display commit as
Verified in their UI.
7. Verify you information once again and confirm to continue
8. Enter a strong password and then confirm it.
9. It is done, now display created key with this command:
10. In the output, identify the
sec line, and copy the GPG key ID. It begins after the
/ character. In this example, the key ID is
sec rsa2048/E93131EB80810CC7 2019-05-02 [SC] 3CB2CF2EB3CEB0C721BF3A00E93131EB80810CC7 uid [ultimate] hoangddt (MacPro key) <reacted email> ssb rsa2048/4E177431166EC61C 2019-05-02 [E]
11. To show the associated public key, run this command, replacing
<ID> with the GPG key ID from the previous step:
$ gpg --armor --export <ID>
Copy the public key to use in the next step, beginning with
-----BEGIN PGP PUBLIC KEY BLOCK----- and ending with
-----END PGP PUBLIC KEY BLOCK-----.
II. Associate your GPG key with git
After you create your GPG key, you must configure git to use this key
- Run this command to list the private key you want to use, replace
<EMAIL>with the email address you use for your key:
$ gpg --list-secret-keys --keyid-format LONG <EMAIL>
2. Copy the GPG private key ID that starts with
3. Run this command to configure git to sign your commit with your key, replace
<KEY ID> with your GPG key ID:
$ git config --global user.signingkey <KEY ID>
III. Sign your git commits
1.Sign individual Git commits manually
$ git commit -S -m "My commit message"
2. Enter the passphrase of your GPG key when asked
3. Sign all Git commits by default by running this command:
$ git config --global commit.gpgsign true
4. View and update global config:
$ git config --global --edit
Set up on the online repository storage like Github
When you add your public key to the online repository storage account. Commits signed by any of the corresponding private keys will show as verified. If you haven't add any GPG key to the provider, it won't show the marked verified even though commit is signed.
I. Add a GPG key to your account
This will be the steps on github and gitlab
- In upper right corner, click on you profile page, then click Settings
- In the Access section of the sidebar, click SSH and GPG keys
- Click New GPG Key
- In the "Key" field, paste the public GPG key. Confirm action by enter you Github password.
- In the upper right corner, click on your avatar
- Select Edit profile.
- On the left sidebar, select GPG Keys
- In Key, paste your public GPG key and select Add key
II. Push your commit
Push your commit as normal, you should see the marked "Verified" in the commit listing
1. Failed to sign commit
If you got error
error: gpg failed to sign the data. fatal: failed to write commit object.
➜ git commit -m "init" error: gpg failed to sign the data fatal: failed to write commit object
GIT_TRACE=1 then run the commit again to see what is the actual problem. Example:
➜ GIT_TRACE=1 git commit -m "init" 12:05:55.591085 exec-cmd.c:139 trace: resolved executable path from Darwin stack: /Library/Developer/CommandLineTools/usr/bin/git 12:05:55.591488 exec-cmd.c:238 trace: resolved executable dir: /Library/Developer/CommandLineTools/usr/bin 12:05:55.591935 git.c:460 trace: built-in: git commit -m init 12:05:55.593151 run-command.c:654 trace: run_command: gpg --status-fd=2 -bsau 6A3B2EFE956B5B36 error: gpg failed to sign the data fatal: failed to write commit object
This show us that there is something wrong with the gpg command, so let run the standalone gpg command to see what is the problem.
➜ echo "dummy" | gpg -bsau 6A3B2EFE956B5B36 gpg: signing failed: Inappropriate ioctl for device gpg: signing failed: Inappropriate ioctl for device
Hmm, something about
ioctl, after some google search, the fix for this is to append this to your start-up bash file, in my case is
The above did the trick and the commit signing now work properly.
If you got error message:
Unusable secret key, it means your key has expired, you will have to generate new key and use new key.
2. Show the signature on commit
To make sure the commit is signed, you can show it signature by using this command, it will show signing information by prefix gpg:
$ git log --show-signature commit c180cc5a0e1ba42d74a0dd5541fb940f08717f97 gpg: Signature made Sat Apr 8 10:24:49 2023 +07 gpg: using RSA key 9EA3..redacted..56B5B36 gpg: Good signature from "hoangddt <q...@gmail.com>" [ultimate] Author: hoangddt <q...@gmail.com> Date: Sat Apr 8 10:24:49 2023 +0700 add: test file
3. Verified mark on remote git storage system
If the git storage doesn't show "Verified" mark, make sure the email address of the GPG key match with the email address of your account, and email in git commit message.
This extra step of configuration will make sure your commit are protected, if anyone want to change the commit's metadata, they are required to have the private key.
Remember to configure the signing public key with the git storage provider so your commit can be mark "Verified", indicate that is really come from you.
Next step, you might want to configure GPG passphrase so you don't have to type it every time in MacOS.