Sunday, March 3, 2013

Signing and Promoting your Clojure libraries on Clojars

Phil Hagelberg, the creator and primary maintainer of Leiningen, has been advocating that Clojurians sign their Clojure libraries for the releases repository in Clojars. By itself, this isn't sufficient to provide security to avoid malicious code from causing havoc with public code repositories, but it is a necessary first step. Phil has talked about his ideas on how to get to a more complete model of security in a couple of places:

/* ---[ Signing your Clojure libraries ]--- */

My first experience deploying a signed jar to Clojars was a little rocky, so I'm providing this how-to report to help others (including future me).

I have only done this on (Xubuntu) Linux, but I imagine it will work fairly similarly on Macs. Not sure about Windows, as I seem to have constant trouble getting Clojure and Windows to play nicely together. I have used GPG on Windows that comes with mysysgit, so that will probably work with these instructions as well, but I haven't tried it.

/* ---[ STEP 1: Generate GPG Keys ]--- */

Clojars security is based on PGP keys, so you need to a have a PGP public/private keyset. GnuPG (GPG) is the generally recommended tool for that.

If you already have GPG installed and can't remember if you've already created a keyset, try this first:

gpg --list-keys

If you see your name and email in the list, then you have. If not, generate them with:

gpg --gen-key

Accepting the defaults you are prompted with is fine. See this article for details on this step. When completed this will create your public key ring and secret/private key ring:

$ ls ~/.gnupg
pubring.gpg  pubring.gpg~  random_seed  secring.gpg  trustdb.gpg

/* ---[ STEP 2: Publish your public GPG key to a keyserver ]--- */

By publishing your public key, others can download it and verify that your signed library is in fact signed by you.

To publish your key you will need to get its ID.

$ gpg --list-keys
pub   2048R/5414B325 2012-11-12
uid                  Michael Peterson <>

The 8 characters after the '/' on the "pub" row of your key is your key's ID. Now publish it:

$ gpg --send-key 5414B325

If you don't specify a key server it will choose the GnuPG keyserver. If you want to target a specify keyserver use the --keyserver option as shown here.

/* ---[ STEP 3: Add your GPG key to your Clojars account ]--- */

When you sign up for Clojars there is a section in your Profile to add two keys: 1) an SSH public key and a PGP public key. The SSH key is for secure transport of the library from your system to the Clojars repo via scp. It is not related to signing your jars.

Your library will be signed with your PGP private key that resides only on your system. That signature indicates that the owner of the private key (the one paired with the public key you just published) signed this code artifact. It allows someone else to know who signed it and whether the code artifact has been changed since it was signed and deployed.

By having your PGP public key on Clojars, you allow Clojars to verify that one of its members signed the artifact. This check happens when you promote your release to the release repo (more on that below).

Note: Clojars is not a keyserver, so putting it there will not allow others to verify the signature. That is why in step 2 we published it to a public keyserver.

To add your public key to Clojars you create an "ASCII-armored" version of the binary public key, which you generate with:

gpg --armor --export code

Once you have it, what exactly do you paste into the Clojars text box? The BEGIN and END delimiter lines and everything in between, like so:

Version: GnuPG v1.4.11 (GNU/Linux)


/* ---[ STEP 4: Prepare your project and its metadata ]--- */

With Clojars you can publish SNAPSHOTS or releases. The latter can be "promoted" if you meet all the criteria in your project.clj, which are:

  • you cannot have the word SNAPSHOT in your version
  • you should have your license filled in
  • you need to have the :scm section filled in
    • you can either do this manually, as in the example below
    • or lein in theory can automatically do this for you if you are using GitHub and its remote "ID" is origin (though I've had issues even in that case)

Here is an example project.clj:

 (defproject thornydev/go-lightly "0.4.0"
   :description "Clojure library to facilitate CSP concurrent programming based on Go concurrency constructs"
   :url ""
   :license {:name "Eclipse Public License"
             :url ""}
   :profiles {:dev {:dependencies [[criterium "0.3.1"]]}}
   :dependencies [[org.clojure/clojure "1.5.0"]]
   :scm {:name "git"
         :url ""})

/* ---[ STEP 5: Commit your code ]--- */

Make sure you have committed all your changes into Git (or Hg, SVN or whatever SCM you are using). Tag the release if you are so inclined and (optional) push it to GitHub or your remote or central hosting server.

/* ---[ STEP 6: Deploy to Clojars ]--- */

From the top of your project directory, enter:

lein deploy clojars

In my case, my gpg-agent prompted me twice for my GPG passphrase and then the deploy happened.

When you do this lein will create a pom and a jar and upload those to Clojars. That pom.xml should include SCM information that looks like this:


The tag there should be the SHA1 of the last commit (in the case of Git). Note: Don't confuse it with a "tag" that you create with "git tag".

If the deploy was successful, your jar should be signed and (possibly) ready for Promotion.

/* ---[ STEP 7: Check whether your jar was signed ]--- */

Create a new lein project and make your deployed library one of its dependencies. Then in that new project run:

$ lein deps :verify
:signed [criterium "0.3.1"]
:unsigned [enlive "1.0.1"]
:signed [org.clojure/tools.macro "0.1.1"]
:signed [org.clojure/clojure "1.5.0"]
:bad-signature [thornydev/go-lightly "0.4.0"]

You see that some are signed and some are not. Obviously, you want yours to say :signed. If it has unsigned then you are probably either using Lein 1 or you didn't generate your GPG keys. If it has :bad-signature then something got corrupted on the Clojars server. In my case above, I promoted and tried to redeploy, which uncovered a bug in lein/clojars that caused some files to get overwritten when they shouldn't. This issue should be fixed soon. If you do have that problem, delete your local copy from your ~/.m2 directory and contact someone on the #leiningen IRC channel.

/* ---[ Optional STEP 8: Promote to release status ]--- */

If you are eligible to promote to release status, you will see a "Promote" button on your Clojars page. If you are not, you may be missing SCM information, which is what happened to me recently.

Note that once you promote you can no longer deploy to that version again, so make sure you're ready to make it immutable. After that, you can only add new versions.


  1. Thanks; this is a good overview to a topic that is often confusing to newcomers. We haven't been pushing as hard on promotion and signing recently due to some bugs in the promotion process and plans to replace the Clojars DB first, but once those are straightened out we'll be encouraging all library authors to ensure their past and future releases are signed. Maybe at that point we could get some of this material integrated into Leiningen's own Deploy guide?

    1. Thanks for the info on near-term priorities.

      I'd be happy to help get this into the Leiningen docs. We'll need to test the steps on Macs and Windows as well.

    2. FWIW, I just followed the steps on Mac OS 10.8.4 with lein 2.2.0 and gpg 2.0.20 and everything worked just fine. Thanks for publishing this, too!

  2. We haven't been pushing as hard on promotion and signing recently due to some bugs..

    Pgp software

  3. WhatsApp Status Video Download :WhatsApp introduced the status feature in 2015, in which we can share images, videos, and gifs as our story for 24 hours. Before this feature, WhatsApp had only text status option in which we can write our bio, but the new status feature is different. The story or status disappears after 24 hours and can’t be archived as still in WhatsApp.

    Boy attitude status video download for whatsApp
    Boy attitude status video download
    Boy attitude status video download

    Most romantic status video download for whatsApp
    Sad video status download
    Most Romantic status video download

    video status download for whatsApp

    we have latest & best collection of video status download for whatsapp

  4. Dr Driving is one of the my favourite game ever and today I am going to share Dr Driving Mod Apk

  5. thanks for giving me an opportunity to share my experience in money making with you. Recently I wrote one article on how you can earn money by listening to the music, I think you should check that right now! click on the below link:
    click me

  6. PNJ Sharptech is a leading Social Media Optimization company in India, specializing in handling both organic and paid Social Media Marketing (SMM) campaigns successfully. We have many years of experiencing increasing online social presence on various social media platforms such as Facebook, Twitter, LinkedIn and Pinterest, and many others. Our SMO experts have a rich knowledge of increasing traffic and maintaining the online social reputation for a long period. How our SMO services make you different from others? Our low-cost social media marketing services are very helpful to build your online reputation and increase sales.

  7. Presenting Latest New Bollywood Song Lyrics of Fauj Ki Dahaad Song Lyrics Mr. BratBea From Kartikeye Ojha & Pranshu Jha . The latest Upcomin Movie Code M Song Fauj Ki Dahaad Lyrics are written by Kumaar Mr. BratBeat and Music Directed by Kartikeye Ojha & Pranshu Jha

    Fauj Ki Dahaad Song Lyrics Code M | Mr. BratBeat

  8. 40 Lakh mp3 song download pagalworld, tik tok viral song ,Mr jatt. – Presenting the audio song ” 40 Lakh ” this song by Jerry Burj Ft. Ellde Fazilka , song is been written Ellde Fazilka40 Lakh mp3 song download pagalworld

    1. Really infomational and educative article thanks publisher for sharing this wonderful info i have shared this article on my blog tecktak and whatsaup, and Best smart tv

  9. Excellent Blog! I would like to thank for the efforts you have made in writing this post. I am hoping the same best work from you in the future as well.
    click here

  10. Promote ABHI SEO Services company Delhi are essential when you are looking to rank your website on the search engine result pages. Promote Abhi, being the affordable SEO Company in Delhi, helps you with the result that you expect from a top SEO services company. What are you waiting for, COME ON NOW, FOLLOW MY LEAD!

  11. Get Rapid Solutions For Norton Antivirus Related Problems..

    Visit US:

  12. Really informational and educational article thanks publisher for sharing this wonderful info with us flippzilla
    and whatsaup, and Best smart tv

  13. informative article thanks for shairng this wonderful info gossip mouth

  14. بیلبوردهای روی عرشه پل از نمونه ابزارهای تبلیغات محیطی هستند.

  15. This comment has been removed by the author.

  16. This is very good content you share on this blog. it's very informative and provide me future related information. thnaks For Sharing

  17. Islam Preach website par aapko mukhtalif islamic dua, sunnat tarika, aur deegar islamic posts Roman English aur Hindi me padhne ko milegi.