{"id":18456208,"url":"https://github.com/nicohood/gpgit","last_synced_at":"2025-10-09T08:48:42.888Z","repository":{"id":48801866,"uuid":"76652889","full_name":"NicoHood/GPGit","owner":"NicoHood","description":"A shell script that automates the process of signing Git sources via GPG","archived":false,"fork":false,"pushed_at":"2023-11-21T12:58:30.000Z","size":708,"stargazers_count":94,"open_issues_count":7,"forks_count":10,"subscribers_count":7,"default_branch":"master","last_synced_at":"2025-04-08T04:34:28.394Z","etag":null,"topics":["git","gpg","security","signature"],"latest_commit_sha":null,"homepage":"","language":"Python","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/NicoHood.png","metadata":{"files":{"readme":"Readme.md","changelog":"CHANGELOG.md","contributing":null,"funding":".github/FUNDING.yml","license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null},"funding":{"github":"nicohood","patreon":"nicohood","open_collective":null,"ko_fi":null,"tidelift":null,"community_bridge":null,"liberapay":null,"issuehunt":null,"otechie":null,"custom":"https://www.buymeacoffee.com/nicohood"}},"created_at":"2016-12-16T12:40:35.000Z","updated_at":"2025-03-29T21:28:40.000Z","dependencies_parsed_at":"2024-11-06T08:10:53.365Z","dependency_job_id":"25ae5e9d-ae3c-4e91-85c5-58573a8e4e71","html_url":"https://github.com/NicoHood/GPGit","commit_stats":null,"previous_names":[],"tags_count":22,"template":false,"template_full_name":null,"purl":"pkg:github/NicoHood/GPGit","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/NicoHood%2FGPGit","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/NicoHood%2FGPGit/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/NicoHood%2FGPGit/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/NicoHood%2FGPGit/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/NicoHood","download_url":"https://codeload.github.com/NicoHood/GPGit/tar.gz/refs/heads/master","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/NicoHood%2FGPGit/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":279001054,"owners_count":26082991,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","status":"online","status_checked_at":"2025-10-09T02:00:07.460Z","response_time":59,"last_error":null,"robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":true,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["git","gpg","security","signature"],"created_at":"2024-11-06T08:10:44.060Z","updated_at":"2025-10-09T08:48:42.861Z","avatar_url":"https://github.com/NicoHood.png","language":"Python","funding_links":["https://github.com/sponsors/nicohood","https://patreon.com/nicohood","https://www.buymeacoffee.com/nicohood"],"categories":[],"sub_categories":[],"readme":"# GPGit\n\n![gpgit.png](img/gpgit.png)\n\n# Introduction\nAs we all know, today more than ever before, it is crucial to be able to trust our computing environments. One of the main difficulties that package maintainers of GNU/Linux distributions face, is the difficulty to verify the authenticity and the integrity of the source code. With GPG signatures it is possible for packagers to verify source code releases quickly and easily.\n\n#### Overview of the required tasks:\n* Create and/or use a **[4096-bit RSA/Ed25519 ECC keypair][1]** for the file signing\n* Use a **[strong, unique, secret passphrase][2]** for the key\n* Upload the public key to a **[key server][3]** and **[publish the full fingerprint][4]**\n* **[Sign][5]** every new Git **[commit][6]** and **[tag][7]**\n* Create **[signed][8], [compressed release archives][9]**\n* Upload a **[strong message digest][10]** of the archive\n* Configure **[HTTPS][11]** for your download server\n\n\u003ca href=\"https://www.buymeacoffee.com/nicohood\" target=\"_blank\"\u003e\u003cimg src=\"https://www.buymeacoffee.com/assets/img/custom_images/orange_img.png\" alt=\"Buy Me A Coffee\" style=\"height: auto !important;width: auto !important;\" \u003e\u003c/a\u003e\n\n### GPGit\n[GPGit][12] is meant to bring GPG to the masses. It is not only a shell script that automates the process of [creating new signed Git releases with GPG][13], but also includes a [quick-start-guide][14] for learning how to use GPG. GPGit integrates perfectly with the [Github Release API][15] for uploading. It can even automatically add a [Keep A Changelog](https://keepachangelog.com/) formatted changelog to the release.\n\nThe security status of GNU/Linux projects will be tracked in the [Linux Security Database][16]. If you have any further questions, do not hesitate to [contact me][17] personally. Thanks for your help in making GNU/Linux projects more secure by using GPG signatures.\n\n[1]: https://github.com/NicoHood/gpgit#12-key-generation\n[2]: https://github.com/NicoHood/gpgit#11-strong-unique-secret-passphrase\n[3]: https://github.com/NicoHood/gpgit#21-send-gpg-key-to-a-key-server\n[4]: https://github.com/NicoHood/gpgit#22-publish-full-fingerprint\n[5]: https://github.com/NicoHood/gpgit#31-configure-git-gpg-key\n[6]: https://github.com/NicoHood/gpgit#32-commit-signing\n[7]: https://github.com/NicoHood/gpgit#33-create-signed-git-tag\n[8]: https://github.com/NicoHood/gpgit#42-sign-the-archive\n[9]: https://github.com/NicoHood/gpgit#41-create-compressed-archive\n[10]: https://github.com/NicoHood/gpgit#43-create-the-message-digest\n[11]: https://github.com/NicoHood/gpgit#51-configure-https-download-server\n[12]: https://github.com/NicoHood/gpgit\n[13]: https://github.com/NicoHood/gpgit#script-usage\n[14]: https://github.com/NicoHood/gpgit#gpg-quick-start-guide\n[15]: https://github.com/NicoHood/gpgit#52-upload-to-github\n[16]: https://github.com/NicoHood/LSD\n[17]: http://contact.nicohood.de\n\n# Index\n* [Introduction](#introduction)\n* [GPGit Documentation](#gpgit-documentation)\n* [GPG Quick Start Guide](#gpg-quick-start-guide)\n\n# GPGit Documentation\n\n## Installation\n\n### Arch Linux\n\nGPGit is available as [official Arch Linux distribution package](https://archlinux.org/packages/community/any/gpgit/):\n\n```bash\nsudo pacman -S gpgit\n# Optional dependencies for Github API uploading\nsudo pacman -S curl jq\n```\n\n### Debian\n\nFirst install the following dependencies, then follow the manual installation instruction.\n\n```bash\n# Install dependencies\nsudo apt-get install bash gnupg2 git tar xz-utils coreutils gawk grep sed util-linux\n# Optional dependencies\nsudo apt-get install gzip bzip lzip zstd file jq curl\n```\n\n### MacOS\n\nFirst install the following dependencies with [Homebrew](https://brew.sh/), then follow the manual installation instructions.\n\n```bash\n# Install dependencies\nbrew install bash git xz gnu-getopt coreutils\n# Install a GPG suite, such as https://gpgtools.org/\nbrew install --cask gpg-suite\n# Optional dependencies\nbrew install gzip bzip2 lzip zstd jq curl\n```\n\n### Manual Installation\n\n#### Dependencies\n\n* bash\n* gnupg2\n* git\n* tar\n* xz\n* grep\n* sed\n* gnu awk\n* gnu getopt (util-linux)\n* gnu date (coreutils)\n\n#### Optional Dependencies\n\n* gzip (Compression option)\n* zstd (Compression option)\n* bzip (Compression option)\n* lzip (Compression option)\n* file (Github API upload)\n* jq (Github API upload)\n* curl (Github API upload)\n* shellcheck (Development: `make test`)\n\n#### Installation Instructions\n\n```bash\n# Download and verify source\nVERSION=1.5.0\nwget \"https://github.com/NicoHood/gpgit/releases/download/${VERSION}/gpgit-${VERSION}.tar.xz\"\nwget \"https://github.com/NicoHood/gpgit/releases/download/${VERSION}/gpgit-${VERSION}.tar.xz.asc\"\ngpg2 --keyserver hkps://keyserver.ubuntu.com --recv-keys 97312D5EB9D7AE7D0BD4307351DAE9B7C1AE9161\ngpg2 --verify \"gpgit-${VERSION}.tar.xz.asc\" \"gpgit-${VERSION}.tar.xz\"\n\n# Extract, install and run GPGit\ntar -xf \"gpgit-${VERSION}.tar.xz\"\nsudo make -C \"gpgit-${VERSION}\" PREFIX=/usr/local install\ngpgit --help\n```\n\n## Script Usage\nThe script guides you through all 5 steps of the [GPG quick start guide](#gpg-quick-start-guide). Run GPGit with the tag name as parameter. All other options will get auto detected. When running the script for the first time GPGit runs in interactive (`-i`) mode and guide you through all steps of secure source code signing.\n\nIf you add and commit a `CHANGELOG.md` file to your Git with the [Keep a Changelog](https://keepachangelog.com/) format, GPGit will autodetect that file and add the corresponding changelog section to the tag message and Github release notes.\n\n### Sample Usage\n![screenshot](img/screenshot.png)\n\n### Parameters and Configuration\n```\n$ gpgit --help\nUsage: gpgit [options] \u003ctagname\u003e [\u003ccommit\u003e | \u003cobject\u003e]\n\nGPGit 1.5.0 https://github.com/NicoHood/gpgit\nA shell script that automates the process of signing Git sources via GPG.\n\nMandatory arguments:\n  \u003ctagname\u003e                The name of the tag to create.\n\nOptional arguments:\n  -h, --help               Show this help message and exit.\n  -m, --message \u003cmsg\u003e      Use the given \u003cmsg\u003e as the commit message.\n                           If multiple -m options are given, their values are\n                           concatenated as separate paragraphs.\n  -C, --directory \u003cpath\u003e   Run as if GPGit was started in \u003cpath\u003e instead of the\n                           current working directory.\n  -u, --local-user \u003ckeyid\u003e Use the given GPG key (same as --signingkey).\n  -o, --output \u003cpath\u003e      Safe all release assets to the specified \u003cpath\u003e.\n  -a, --asset              Add additional Github assets, e.g. software bundles.\n  -t, --title              Custom Github release title (instead of tag name).\n  -p, --pre-release        Flag as Github pre-release.\n  -f, --force              Force the recreation of Git tag and release assets.\n  -i, --interactive        Run in interactive mode, step-by-step.\n      --\u003coption\u003e           Temporary set a 'gpgit.\u003coption\u003e' from config below.\n  \u003ccommit\u003e, \u003cobject\u003e       The object that the new tag will refer to.\n\nExamples:\n  gpgit 1.0.0\n  gpgit -p -m \"First alpha release.\" 0.1.0 --hash \"sha256 sha512\"\n  gpgit -C git/myproject/ -o /tmp/gpgit -n -m \"Internal test release.\" 0.0.1\n\nConfiguration options:\n  gpgit.signingkey \u003ckeyid\u003e, user.signingkey \u003ckeyid\u003e\n  gpgit.output \u003cpath\u003e\n  gpgit.token \u003ctoken\u003e\n  gpgit.compression \u003cxz | gzip | bzip2 | lzip | zstd | zip\u003e\n  gpgit.hash \u003csha512 | sha384 | sha256 | sha1 | md5\u003e\n  gpgit.changelog \u003cauto | true | false\u003e\n  gpgit.github \u003cauto | true | false\u003e\n  gpgit.githubrepo \u003cusername/projectname\u003e\n  gpgit.project \u003cprojectname\u003e\n  gpgit.keyserver \u003ckeyserver\u003e\n\nExamples:\n  git config --global gpgit.output ~/gpgit\n  git config --local user.signingkey 97312D5EB9D7AE7D0BD4307351DAE9B7C1AE9161\n  git config --local gpgit.compression \"xz zip\"\n```\n\n# GPG Quick Start Guide\nGPGit guides you through 5 simple steps to get your software project ready with GPG signatures. Further details can be found below.\n\n1. [Generate a new GPG key](#1-generate-a-new-gpg-key)\n    1. [Strong, unique, secret passphrase](#11-strong-unique-secret-passphrase)\n    2. [Key generation](#12-key-generation)\n2. [Publish your key](#2-publish-your-key)\n    1. [Send GPG key to a key server](#21-send-gpg-key-to-a-key-server)\n    2. [Publish full fingerprint](#22-publish-full-fingerprint)\n    3. [Associate GPG key with Github](#23-associate-gpg-key-with-github)\n3. [Use Git with GPG](#3-use-git-with-gpg)\n    1. [Configure Git GPG key](#31-configure-git-gpg-key)\n    2. [Enble commit signing](#32-enable-commit-signing)\n    3. [Create signed Git tag](#33-create-signed-git-tag)\n4. [Create a signed release archive](#4-create-a-signed-release-archive)\n    1. [Create compressed archive](#41-create-compressed-archive)\n    2. [Sign the archive](#42-sign-the-archive)\n    3. [Create the message digest](#43-create-the-message-digest)\n5. [Upload the release](#5-upload-the-release)\n    1. [Configure HTTPS download server](#51-configure-https-download-server)\n    2. [Upload to Github](#52-upload-to-github)\n\n## 1. Generate a new GPG key\n### 1.1 Strong, unique, secret passphrase\nMake sure that your new passphrase for the GPG key meets high security standards. If the passphrase/key is compromised all of your signatures are compromised too.\n\nHere are a few examples how to keep a passphrase strong but easy to remember:\n* [Creating a strong password](https://support.google.com/accounts/answer/32040?hl=en)\n* [How to Create a Secure Password](https://open.buffer.com/creating-a-secure-password/)\n* [Mooltipass](https://www.themooltipass.com/)\n* [Keepass](https://keepass.info/), [KeepassXC](https://keepassxc.org/)\n* [PasswordCard](https://www.passwordcard.org/en)\n\n### 1.2 Key generation\nIf you don't have a GPG key yet, create a new one first. You can use RSA (4096 bits) or ECC (Curve 25519) for a strong key. GPG offers you the option to use the most future-proof key algorithm available. Use the most recent version gnupg2, not gnupg1!\n\nEd25519 ECC GPG keys are still not supported by every software/platform. To generate an RSA key use `rsa4096`  instead of `future-default` as parameter.\n\n**Make sure that your secret key is stored somewhere safe and use a unique strong password.**\n\n##### Example key generation:\n```bash\n$ gpg2 --quick-generate-key \"John Doe \u003cjohn@doe.com\u003e\" future-default default 1y\nWe need to generate a lot of random bytes. It is a good idea to perform\nsome other action (type on the keyboard, move the mouse, utilize the\ndisks) during the prime generation; this gives the random number\ngenerator a better chance to gain enough entropy.\ngpg: key 2F8E73B1D445CCD3 marked as ultimately trusted\ngpg: revocation certificate stored as '/home/john/.gnupg/openpgp-revocs.d/6718A9A63030E182A86FEE152F8E73B1D445CCD3.rev'\npublic and secret key created and signed.\n\npub   ed25519 2017-09-24 [SC] [expires: 2018-09-24]\n      6718A9A63030E182A86FEE152F8E73B1D445CCD3\nuid                      John Doe \u003cjohn@doe.com\u003e\nsub   cv25519 2017-09-24 [E]\n```\n\nThe generated key has the fingerprint `6718A9A63030E182A86FEE152F8E73B1D445CCD3` in this example. Share it with others so they can verify your source. [[Read more]](https://wiki.archlinux.org/index.php/GnuPG#Create_a_key_pair)\n\nIf you ever move your installation make sure to backup `~/.gnupg/` as it contains the **private key** and the **revocation certificate**. Handle it with care. [[Read more]](https://wiki.archlinux.org/index.php/GnuPG#Revoke_a_key)\n\n## 2. Publish your key\n\n### 2.1 Send GPG key to a key server\nTo make the public key widely available, upload it to a key server. Now the user can get your key by requesting the fingerprint from the keyserver: [[Read more]](https://wiki.archlinux.org/index.php/GnuPG#Use_a_keyserver)\n\n```bash\n# Publish key\ngpg2 --keyserver hkps://keyserver.ubuntu.com --send-keys \u003cfingerprint\u003e\n\n# Import key\n# Alternative keyserver: hkps://hkps.pool.sks-keyservers.net\ngpg2 --keyserver hkps://keyserver.ubuntu.com --recv-keys \u003cfingerprint\u003e\n```\n\n### 2.2 Publish full fingerprint\nTo make it easy for everyone else to find your key it is crucial that you publish the [**full fingerprint**](https://lkml.org/lkml/2016/8/15/445) on a trusted platform, such as your website or Github. To give the key more trust other users can sign your key too. [[Read more]](https://wiki.debian.org/Keysigning)\n\n### 2.3 Associate GPG key with Github\nTo make Github display your commits as \"verified\" you also need to add your public [GPG key to your Github profile](https://github.com/settings/keys). [[Read more]](https://docs.github.com/github/authenticating-to-github/adding-a-new-gpg-key-to-your-github-account)\n\n```bash\n# List keys + full fingerprint\ngpg2 --list-secret-keys --keyid-format LONG\n\n# Generate public key\ngpg2 --armor --export \u003cfingerprint\u003e\n\n# If you have multiple uids or signatures you can minimize the output:\ngpg2 --armor --export --export-filter keep-uid=\"uid =~ \u003cemail\u003e\" --export-options export-minimal \u003cfingerprint\u003e\n```\n\n## 3. Use Git with GPG\n### 3.1 Configure Git GPG key\nIn order to make Git use your GPG key you need to set the default signing key for Git. [[Read more]](https://help.github.com/articles/telling-git-about-your-gpg-key/)\n\n```bash\n# List keys + full fingerprint\ngpg2 --list-secret-keys --keyid-format LONG\n\ngit config --global user.signingkey \u003cfingerprint\u003e\n```\n\n### 3.2 Enable commit signing\nTo verify the Git history, Git commits needs to be signed. You can manually sign commits or enable it by default for every commit. It is recommended to globally enable Git commit signing. [[Read more]](https://help.github.com/articles/signing-commits-using-gpg/)\n\n```bash\ngit config --global commit.gpgsign true\n```\n\n### 3.3 Create signed Git tag\nGit tags need to be created from the command line and always need a switch to enable tag signing. [[Read more]](https://help.github.com/articles/signing-tags-using-gpg/)\n\n```bash\n# Creates a signed tag\ngit tag -s 1.0.0\n\n# Re-tag an older, unsigned tag\ngit tag -sf 1.0.0 1.0.0\n\n# Verifies the signed tag\ngit tag -v 1.0.0\n```\n\n## 4. Create a signed release archive\n### 4.1 Create compressed archive\nYou can use `git archive` to create archives of your tagged Git release. It is highly recommended to use a strong compression which is especially beneficial for those countries with slow and unstable internet connections. [[Read more]](https://git-scm.com/docs/git-archive)\n\n```bash\n# .tar.gz\ngit archive --format=tar.gz -o gpgit-1.0.0.tar.gz --prefix gpgit-1.0.0/ 1.0.0\n\n# .tar.xz\ngit archive --format=tar --prefix gpgit-1.0.0/ 1.0.0 | xz \u003e gpgit-1.0.0.tar.xz\n```\n\n### 4.2 Sign the archive\nType the filename of the tarball that you want to sign and then run:\n```bash\ngpg2 --personal-digest-preferences SHA512 --armor --detach-sign gpgit-1.0.0.tar.xz\n```\n**Do not blindly sign the Github source downloads** unless you have compared its content with the local files via `diff.` [[Read more]](https://wiki.archlinux.org/index.php/GnuPG#Make_a_detached_signature)\n\nTo not need to retype your password every time for signing you can also use [gpg-agent](https://wiki.archlinux.org/index.php/GnuPG#gpg-agent).\n\nThis gives you a file called `gpgit-1.0.0.tar.xz.asc` which is the GPG signature. Release it along with your source tarball and let everyone know to first verify the signature after downloading. [[Read more]](https://wiki.archlinux.org/index.php/GnuPG#Verify_a_signature)\n\n```bash\ngpg2 --verify gpgit-1.0.0.tar.xz.asc\n```\n\n### 4.3 Create the message digest\nMessage digests are used to ensure the integrity of a file. It can also serve as checksum to verify the download. Message digests **do not** replace GPG signatures. They rather provide and alternative simple way to verify the source. Make sure to provide message digest over a secure channel like https.\n\n```bash\nsha512sum gpgit-1.0.0.tar.xz \u003e gpgit-1.0.0.tar.xz.sha512\n```\n\n## 5. Upload the release\n### 5.1 Configure HTTPS download server\n* [Why HTTPS Matters](https://web.dev/why-https-matters/)\n* [Let's Encrypt](https://letsencrypt.org/)\n* [SSL Server Test](https://www.ssllabs.com/ssltest/)\n\n### 5.2 Upload to Github\nCreate a new \"Github Release\" to add additional data to the tag. Then drag the .tar.xz .sig and .sha512 files onto the release.\n\nThe script also supports [uploading to Github](https://developer.github.com/v3/repos/releases/) directly. Create a new Github token first and then follow the instructions of the script. How to generate a Github token:\n* Go to [\"Settings - Personal access tokens\"](https://github.com/settings/tokens)\n* Generate a new token with permissions `public_repo` and `admin:gpg_key`. In order to access private repositories you must allow access to the whole `repo` scope.\n* Store it safely\n* You can also store the token inside the git config: `git config --global gpgit.token \u003ctoken\u003e`\n\n# Appendix\n\n## Email Encryption\nYou can also use your GPG key for email encryption with [thunderbird](https://support.mozilla.org/en-US/kb/openpgp-thunderbird-howto-and-faq).\n\n## Update key expire date\n\nAfter renewing the GPG key expire date make sure to [publish your GPG key](https://github.com/NicoHood/gpgit#2-publish-your-key) again to the keyserver and update your website accordingly. A more detailed instruction can be found at [G-Loaded Journal](https://www.g-loaded.eu/2010/11/01/change-expiration-date-gpg-key/).\n\n```\ngpg2 --edit-key \u003cfingerprint\u003e\ngpg\u003e expire\ngpg\u003e 1y\ngpg\u003e key 1\ngpg\u003e expire\ngpg\u003e 1y\ngpg\u003e save\n```\n\n## Contact\nYou can get securely in touch with me [here](https://contact.nicohood.de). My GPG key ID is `9731 2D5E B9D7 AE7D 0BD4 3073 51DA E9B7 C1AE 9161`. Don't hesitate to [file a bug at Github](https://github.com/NicoHood/gpgit/issues). More cool projects from me can be found [on my Website](https://www.nicohood.de).\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fnicohood%2Fgpgit","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fnicohood%2Fgpgit","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fnicohood%2Fgpgit/lists"}