Skip to content

Instantly share code, notes, and snippets.

Created Jan 22, 2020
What would you like to do?
YubiKey GPG + GitHub setup

Yubikey + GPG + Github + Keybase

The following guide are steps that can be used to generate GPG keys on a YubiKey, use the gpg keys to sign github commits, and publish the public gpg key to Keybase.

Why is this a good idea?

  1. Generating and storing GPG keys on a YubiKey allows the private key to be protected and ported between physical machines.
  2. Signing git commits adds an extra layer of verification that code changes originated from an trusted source.
  3. Using a YubiKey + touch-to-sign requires a physical presence to use the GPG signing key.
  4. GitHub supports restricting commits to a repo to only those that are signed.
  5. Putting a physical stamp on your code commits invokes a feeling of pride.

Install required programs to generate GPG keys

  1. Install gpg tools
    $ brew install gpg
  2. Install pinentry for mac
    $ brew install pinentry-mac
  3. Set pinentry in gpg config
    $ echo "pinentry-program /usr/local/bin/pinentry-mac" >> ~/.gnupg/gpg-agent.conf
  4. Kill the current gpg agent to pick up the change.
    $ killall gpg-agent

Edit GPG settings on the YubiKey

  1. Connect Yubikey to laptop.
  2. Disregard keyboard setup wizard if one tries to recognize the YubiKey.
  3. Use gpg to connect to the opengpg app on the Yubikey.
    $ gpg --edit-card
  4. Switch to admin mode of the Yubikey.
    gpg> admin
  5. Change the Yubikey to generate gpg keys of 4096 bits instead of 2048.
    gpg> key-attr
  6. For Signature key, Encryption key, and Authentication key do the following. Select 1 to use RSA keys.
    (1) RSA
  7. Enter:
  8. At the prompt for the admin pin enter:
  9. Set the admin pin for the card.
  10. Select 3 to set the admin pin.
  11. Enter the default admin pin.
  12. Enter a new admin pin twice. Be sure to save this pin in a secure place
  13. Next, change the user pin.
  14. Enter the default user pin.
  15. Enter a new user pin twice. Be sure to save this pin in a secure place
  16. Next, set the Reset pin.
  17. Enter your admin pin.
  18. Enter a new Reset pin. Be sure to save this pin in a secure place
  19. Select Q to quit the pin menu.
  20. (Optional) Set your name and email on the card.
    gpg> name

Create GPG keys on the YubiKey

  1. From the gpg> prompt, generate GPG keys.
    gpg> generate
  2. Do not make an off-card backup of encryption key
  3. Set the expiration date for the keys to 16 years
  4. Enter your name and e-mail address.
  5. Enter O for Okay
  6. Generating the keys may take several minutes. The YubiKey will blink while keys are generated. During this time, move your mouse and type on the keyboard. This will help with generating random bytes. Without enough random activity, the key generation will fail.
  7. After some time (5-10 minutes) you should see public and secret key created and signed.
  8. quit
  9. If you log back into the card gpg --edit-card, you should see the details of the new keys displayed. You can also display the info using the list command.

Configure Pin retries and touch to sign on the Yubikey

  1. Install the yubikey manager app
    brew install ykman
  2. Use ykman to turn on touch to sign functionality.
    ykman openpgp set-touch SIG ON
  3. Enter the admin PIN to allow modifying the touch setting.
  4. Answer yes (y) to Set touch policy of signature key to on?
  5. Use ykman to set pin retries (5 tries for user pin, reset pin, admin pin)
    ykman openpgp set-pin-retries 5 5 5
  6. Enter the admin PIN to allow modifying the retries setting.
  7. Answer yes (y) to Set PIN retry counters to: 5 5 5?

Test your new signing key

  1. Test by signing a string on the cli. You should be prompted in a pop-up window to enter your YubiKey User PIN. Remember to touch the yubikey with your finger when blinking to sign the message
    echo "foobar" | gpg --sign --armor | gpg --decrypt

Add your public GPG key to Github

  1. Import your public gpg key to github.
    gpg -k # get fingerprint of key to export. This will be a string of characters one line below the line that starts with pub, and one line above the line that starts with uid.
    gpg --armor --export $FINGERPRINT | pbcopy

Reference: Adding a new GPG key to your GitHub account

  1. Update your gitconfig to use the new gpg key to sign.
    git config --global commit.gpgsign true
    git config --global user.signingkey $FINGERPRINT

When you make a git commit, you may be propmted to enter the user pin of the yubikey to unlock it.

Each time you make a git commit, the commit will require access to your private gpg key to sign. You will need to physically touch the yubikey to grant access. Otherwise your commit will timeout and fail.

To see the signature of your commit, use the following command:

git log --show-signature

Import and trust GitHub's Public GPG key

  1. Import Github's public key into local gpg keychain
    curl | gpg --import
  2. Show Github's key
    gpg -k
  3. Edit Github's key to change the level of trust
    gpg --edit-key $GITHUB_PGP_KEY_FINGERPRINT
  4. Change the trust level
    gpg> trust
  5. Enter the level of trust you have for the key (1-5)
    Your decision? 3
  6. Sign Github's key with your gpg public key
    gpg> 1 # select the key to sign (* should appear next to the key name)
    gpg> sign
    Really sign? (y/N) y
  7. Save and quit
  8. Show keys to confirm GitHub's key is signed and has full trust
    gpg -k

(Optional) Setup Keybase with new GPG Public key and prove identity with


  1. Install Keybase
    brew install keybase
  2. Signup for a keybase account but do not import keys.
    keybase signup
  3. Add your public gpg key to keybase
    keybase pgp select
  4. Set the keybase account passphrase.
    keybase passphrase set
  5. Add your keybase identity proof to github
    keybase prove github
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment