• CIDER 1.0

    You can’t really know where you are going until you know where you have been.

    – Maya Angelou

    CIDER started its life as an effort to replace a hacked version of SLIME1 with a proper environment for Clojure development on Emacs. Many of you probably don’t remember those days, but initially almost everyone was using a modified version of SLIME for Clojure development, as there weren’t many (any?) alternatives back in the day. The creation of CIDER was fueled mostly by the advent of nREPL, which was the first project that aimed to provide a common tool-agnostic foundation for Clojure development tools, and by the desire to address the impedance mismatch between SLIME and Clojure.

    CIDER was started in spring 2012 (under the name nrepl.el) by Phil Hagelberg (of Leiningen fame), who hacked a prototype of an nREPL client in Emacs Lisp on a flight to San Francisco. He got a bit stuck on the socket-based bencode functionality and dropped it after the flight, but not before pushing the code out and mentioning it on the Clojure mailing list. What followed is the best example of the power of open-source software…

    Tim King came across Phil’s post, picked nrepl.el back up, and it quickly became a respectable competitor to SLIME. The project evolved at a rapid pace and eventually superseded SLIME in August 2012.2 Unfortunately in early 2013 Tim ran out of time for nrepl.el and after another period of stagnation, handed it over to me, as I was the main contributor to nrepl.el besides him back then. I have been the project’s steward ever since. Third time’s a charm, right?

    My tenure at the helm started with a bit of controversy as I renamed nrepl.el to CIDER in version 0.3 to avoid the common case of confusion between the nREPL server and the nrepl package for Emacs.3 If I have to be completely honest - I also wanted the project to have a name as cool as SLIME, and I’m fairly certain I succeeded in that regard.

    Eventually CIDER became one of the most popular development environments in the Clojure community and it spawned many important projects (e.g. cider-nrepl and orchard), that are widely used by other development tools (e.g. vim-fireplace, Conjure, iced-vim and Calva). My work on CIDER also led to me becoming the maintainer of nREPL and restarting its development after a long period of hibernation. In hindsight probably the work I did on nREPL was even more important than the work I did on CIDER.

    Over the years a big ecosystem of packages grew around CIDER and nREPL and they became important parts of the Clojure development tooling. Today CIDER and nREPL face a lot of competition, but they are still evolving at a steady pace, occasionally innovating, and serving as inspiration for other tools. That makes me proud of the work we’ve done over the past 8 and a half years, even if fewer and fewer people are using CIDER and Emacs every year.

    One thing that constantly eluded me, however, was a 1.0 release. I guess I’m the one to blame for this not happening sooner, as I had some really grand ambitions for CIDER 1.0 (and some rather high quality standards to go with them) and I was optimistic that somehow my plans would become a reality in a reasonable amount of time. Clearly I was mistaken. Between me having to split my time between a dozen OSS projects and most of them currently having no other active maintainers but me, it eventually became obvious that the grand plans will have to wait for CIDER 2.0. Grand plans and ambitions for world domination aside, CIDER has been pretty stable for a while now and it seems to get the job done. And there’s also the theory that if a piece of software has some (happy) users then it qualifies for a 1.0 release… Oh, well…

    Today the long wait is over - CIDER 1.0 (“Sofia”) is officially out!4 There’s nothing particularly interesting in this release - it’s almost the same as CIDER 0.26. If you notice one difference, it would probably be that commands that act on the symbol at point (e.g. cider-doc) will no longer prompt you to confirm the symbol. The old default was a mistake and I decided to adjust it for this grand release. If you notice another difference, it’d probably be that CIDER is officially using SemVer now. I still have to define what exactly is going to constitute a breaking change going forward (e.g. are changes to keybindings breaking changes?), but I’m reasonably sure the adherence to SemVer will make CIDER upgrades less painful for everyone.

    There are many things that prompted me to do the 1.0 release now, but probably the most important factor was that 2020 was such a horrible year for all of us. I felt we needed all the good news we could get to counter all the pain and suffering we’ve had to endure. While I can’t help the fight against the pandemic, I hope I can cheer you up a bit, by delivering another iteration of your favorite software that rocks.

    So, what’s next? I don’t really have any particular plans for CIDER 1.1, so we’ll see how exactly it’s going to shape up. Some vague ideas that have been floating in my mind are proper support for sideloading, adding support for dynamic middleware loading, and improvements to the session management. No promises, though. I’m also aiming to finally do an nREPL 1.0 release at some point. There are plenty of tickets marked with the label “Good First Issue” on CIDER’s issue tracker, so if you’re looking for more fun challenges after the end of the “Advent of Code” be my guest. I can definitely use all the help I can get.

    One thing is certain, though - CIDER will always stay true to its guiding principles:

    • REPL-first (as opposed to relying on static code analysis)
    • Community-first (CIDER is defined by its community)
    • Keep on rocking in a Lisp world!

    I’m writing this article while enjoying a bottle of proper (hard) French cider, so I think I should wrap it up before I start enjoying myself too much. Thanks to everyone who has been a part of CIDER’s community over the years! Thanks to everyone who has contributed to the project and supported it! Thanks to everyone who still loves Emacs and CIDER! This release is for all of you! Cheers!

    1. A legendary Common Lisp interactive programming environment. 



    4. The most important CIDER release to date can only be named after the greatest city in the world. 

  • Making Sense of All My Blogs

    I’ve noticed recently that some of the people who follow my open-source work and my writings are wondering why am I publishing articles on 3 different blogs and can’t figure how I decide where to publish something. This short article is an attempt to shed some light on this.

    Let’s go over each of my blogs in the order of their creation.


    (think) was my first attempt to write. I failed miserably and I produced some pretty crappy content, but I also learned a lot in the process.

    I’ve started (think) on the 5th of May, 2008. Frankly, I don’t remember at all one I wanted to achieve with the blog originally. I guess I just thought it was cool to have a blog and I decided to create one. Over the course of a decade the blog saw quite a few transformations and shifts in my focus and interests. For a few years it was named DevCraft1 and it was hosted on Afterwards I adopted the domain, the (think) title and switched to Jekyll, Octopress and then again to Jekyll. Originally I was writing mostly tutorials on topics like Linux, Java, Emacs and Ruby, but eventually I started writing some essays as well (my favorite type of posts). As my OSS portfolio grew it started to gain significant coverage in my blog as well. (think) was a bit messy and without a clear direction, but I guess it was a somewhat accurate reflection of myself as well.

    I’ve thought at times about deleting some of my lame articles and heavily copy-editing the rest to make them fit my current beliefs and standards of quality, but this approach felt like cheating to me. I was who I was and I wrote what I wrote. To me that certainly has a lot of value. I’ve been thinking lately that being (very) critical of your old work is a good indicator that you’re moving in the right direction. We can always do better, but we need to reach a certain level of experience to see that.

    For various reasons (mostly a combination of frustration with Octopress and my (immense) laziness), I didn’t write anything between 2015 and 2018 and when I finally mustered the will to return to writing I decided to go with a clean slate and a new blog.2 That’s how “Meta Redux” was born.

    These days I use (think) mostly for short (and somewhat random) tutorial-like articles, that don’t fit very well with my vision for Meta Redux. Perhaps at some point I should retire (think) completely, but we’ve had a good run together and I’m not ready for us to part ways just yet.

    Emacs Redux

    Emacs Redux was my second blog. I started it in 2013 with the clear goal to write there short Emacs tutorials. That’s what I’ve been doing for the past 7 years with a various degree of commitment and quality. Still, I consider it a great success that I’ve kept writing there for so long. For a while I wasn’t very active there, again due to frustration with Octopress, but once I converted Emacs Redux to Jekyll, I’ve managed to rekindle my passing for it.3

    It’s important to understand that I don’t write about Emacs exclusively on Emacs Redux. Often when an article is more “meta” in its nature (e.g. musings on the role of Emacs in modern society) it will end up on Meta Redux. Articles related to CIDER usually end up on Meta Redux as well, as I consider them more of Clojure articles, than Emacs articles.

    Meta Redux

    After the previous couple of sections, there’s little to add here. Meta Redux is my primary blog these days, where I try to share my thoughts on the topics I consider the most important to me. These days those topics are still mostly programming related, but this may very well change down the road.

    Closing Thoughts

    I have to admit that my fondness for the word “redux” turned out to be a major SEO problem due to the massive popularity of React in recent years. Just Google “meta redux” and you’ll see what I mean. That being said at some point I was thinking of doing “Ruby Redux” and “Clojure Redux” as well, but then I came back to my senses and I realized I don’t have nearly enough time for so much writing, plus I still prefer writing code to writing articles.

    You might have noticed that all my blogs are pretty spartan when it comes to the visuals. A while ago I realized that a blog is all about the content and we can’t have a fancy theme distract us from what matters the most. On top of this - my CSS skills are a complete zero, so there’s that as well. A bit of Jekyll, a bit of minima (its default theme), and lots of quality time writing articles in Emacs. That’s my recipe for a rewarding blogging experience.

    That’s all I have for you today. I hope now you’re finally making some sense of how I leverage my different blogs.

    1. I used to be a huge StarCraft fan. 

    2. I also wanted a blog with a cool (for some definition of cool) name this time around. 

    3. A bad tooling decision can really kill your enthusiasm for doing pretty much anything. 

  • Migrating from Disqus to Hyvor Talk

    For a very long time1 I’ve been using Disqus as the commenting service for all of my Jekyll blogs.2 Today that’s no longer the case.

    I’ve never been particularly happy with Disqus for various reasons:

    • The service is tracking its users for marketing purposes
    • Their JS payload is huge and slows down your site
    • The formatting options they support are limited, especially if you run a blog focused on programming and people are often discussing code snippets in the comments.

    I’m guessing the readers of my blogs were not particularly fond of Disqus either, as I’d rarely get any Disqus comments, even on articles that would generate a lot of feedback on third-party platform like Reddit, HN or Lobsters.

    Note: This great article digs deeper into all the issues with Disqus.

    I did tolerate them, however, because Disqus is the only commenting service supported by Jekyll out-of-the-box, and because they were free. Lately, however, Disqus started to insert some horrible ads in my blogs automatically, without giving me any options to opt-out of this in advance. I’ve managed to disable the ads for a couple of my sites (based on them being small and non-commercial), but for some reason I couldn’t disable them for Meta Redux and for me this was it. Obviously I could have paid Disqus to disable the ads, but given my other concerns about their service I preferred to pay someone else if I had to.

    I looked around for Disqus alternatives and several articles suggested the privacy focused Hyvor Talk as a great option. As a bonus it supports Markdown-like markup in the comments and works well with code snippets.

    Note: Hyvor is a small startup that reached a 100 paying customers only a month ago. Normally, I’m cautious about such small companies, but given my very positive experience with their product I’m feeling optimistic about their future.

    Now, let’s the discuss the actual migration process.

    Migration Steps

    The migration itself is pretty simple and literally took me 5 minutes.3 The instructions I wrote are for Jekyll in particular, but the process is fairly generic, so I’m confident the bulk of them are applicable to most cases.

    Export Data from Disqus

    First you need to export your comments from Disqus. The process is described in their docs. If you’re too lazy to read them just go here and export the data for each site you have with them individually.

    They’ll send you the exported data for each site as a gzipped XML via email. For me this happened almost immediately, but for people running popular sites with lots of comments the process will probably take longer.

    Setup Hyvor Account

    At this point you have to sign up for Hyvor Talk, create a site there and import the Disqus data.

    The import process is pretty simple, but there are a couple of things to keep in mind:

    • You need to upload the export data unzipped (first I tried to upload the export in its gzipped form)
    • You have to specify “Absolute URL” as the identifier used by Disqus to map URLs to comments (I’ve never changed this myself, so I assume that’s their default)

    After the import is successful you are now ready to enable Hyvor Talk for your Jekyll site.

    Add Hyvor to Jekyll

    First, remove any Disqus configuration from your _config.yml. Normally you’d have there something like:

      shortname: sitename

    Now you need to add the following HTML snippet to every Jekyll layout that you want Hyvor comments enabled for:

    <div id="hyvor-talk-view"></div>
    <script type="text/javascript">
     var HYVOR_TALK_CONFIG = {
         url: '{{ page.url | absolute_url }}',
         id: '{{page.url | absolute_url }}'
    <script async type="text/javascript" src="//"></script>

    That’s the trickiest part of the migration process, as you’ll have to tweak some Jekyll layouts manually. Normally, you want comments only for posts, so you’ll need to modify the post.html layout. The layout files are bundled with Jekyll’s themes so you have to create a _layouts directory in your site, and copy the post.html from your site’s theme (e.g. minima) there. I usually just grab the file from the theme’s GitHub repo, you can also get it from the locally installed theme:

    $ cd mysite
    $ mkdir _layouts
    $ bundle info --path minima
    $ cd /home/bozhidar/.rbenv/versions/2.7.1/lib/ruby/gems/2.7.0/gems/minima-2.5.1
    $ tree
    ├── LICENSE.txt
    ├── _includes
    │   ├── disqus_comments.html
    │   ├── footer.html
    │   ├── google-analytics.html
    │   ├── head.html
    │   ├── header.html
    │   ├── icon-github.html
    │   ├── icon-github.svg
    │   ├── icon-twitter.html
    │   ├── icon-twitter.svg
    │   └── social.html
    ├── _layouts
    │   ├── default.html
    │   ├── home.html
    │   ├── page.html
    │   └── post.html
    ├── _sass
    │   ├── minima
    │   │   ├── _base.scss
    │   │   ├── _layout.scss
    │   │   └── _syntax-highlighting.scss
    │   └── minima.scss
    └── assets
        ├── main.scss
        └── minima-social-icons.svg
    $ cp /home/bozhidar/.rbenv/versions/2.7.1/lib/ruby/gems/2.7.0/gems/minima-2.5.1/_layouts/post.html _layouts/

    That’s it! Now just add the Hyvor snippet to the end of the layout file and publish your updated site. All of your old comments should be attached to their respective blog posts.

    One thing to keep in mind is that by default the Hyvor snippet for Jekyll looks like:

    url: '{{ page.url | absolute_url }}',
    id: '{{}}'

    This implies that comments are mapped to URLs by using relative URLs. However, the exported data from Disqus was using absolute URLs. I needed to change it the default, so the Hyvor IDs would match what Disqus was using in my case (absolute instead of relative page URLs):

    url: '{{ page.url | absolute_url }}',
    id: '{{page.url | absolute_url }}'

    Closing Thoughts

    I told you that the process was pretty easy. I really regret not doing this earlier, but then again - if I had left Disqus earlier probably I wouldn’t have discovered Hyvor Talk (as it wouldn’t have existed). There’s always some silver lining.

    If you are not paying for it, you’re not the customer; you’re the product being sold.

    Hyvor Talk doesn’t have a free plan, which might be a deal-breaker for some, but I’m more than happy to pay $5/month for a service that is respecting the privacy of my users and could be used on unlimited number of sites. If you’d like to give Hyvor a try I’d appreciated it if you used my affiliate link to sign up.

    That’s all I have for you today. Keep hacking!

    1. Something like 10 years. 

    2. I currently have 4 of those. 

    3. Writing this article took way longer than the actual migration. 

  • Semantic Clojure Formatting

    Programs must be written for people to read, and only incidentally for machines to execute.

    – Harold Abelson, Structure and Interpretation of Computer Programs

    The above maxim has guided most of my career as a software engineer and has been one of the central guiding principles of the community Clojure style guide, that I’ve been maintaining for the past (almost) 8 years.

    While the style guide was well received by the Clojure community in general, and universal agreement was reached on most points in it, one aspect remains controversial to this day - namely the style guide’s preference towards “semantic indentation” over “fixed indentation” for function/macro arguments. Today I want to address an article that suggested that fixed indentation is preferable, as it’s simpler and it’s easier to provide tooling support for it. That article is named Better Clojure Formatting1, which admittedly is catchy and made me consider naming my response to it “The Best Clojure Formatting” or “Superb Clojure Formatting”, but I’ve opted for a more modest title in the end.

    1. For the record, I’ve got nothing but immense respect for Nikita and his work, even if I disagree with him on this topic. 

    Read More
  • Advent of Open Source

    Ah, it’s again this magical time of the year - the Advent! When I was little I associated it mostly with advent candy boxes with a different candy for each day of the Advent, but these days I mostly associate this period with the famous Advent of Code.1

    As much as I love solving puzzles, I’ve realized lately that probably it’s not the best use of my limited free time. Last year I opted to do an blogging challenge, instead of the Advent of Code, and this year I’m challenging myself to contribute something (meaningful) to my open-source projects every day from the 1st of December to Christmas. Fun times ahead!

    Today is the 3rd of December already, so I guess I have to report what I’ve done so far.

    Dec 1

    • Shipped RuboCop 1.5
    • Lots of improvements to the Clojure Style Guide
      • New sections on guiding principles and consistency
      • Documented the sources of inspiration
      • Added lots of new code examples (e.g. here)
      • Fixed many headings that had broken wording after the automated conversion to the current structure last year (each guideline now has a title, and the titles were auto-generated from the old permalinks associated with the guidelines)

    I hope to gradually clean up the backlog for improvements of the style guide in the months to come. I’ll also mention here that I wouldn’t mind some volunteers willing to help document the best practices for working with cljc and clojure.spec.

    Dec 2

    • Shipped RuboCop 1.5.1
    • Projectile
      • Groomed the backlog (replied to some tickets, closed some tickets that were addressed/irrelevant, added tags to everything else)
      • Merged a few outstanding PRs (see the changelog for details)
      • Lots of improvements to the documentation site
        • Improved Usage page (better basic setup instructions, plus coverage of the mighty but elusive Projectile Commander)
        • Improved Projects page (in particular, you’ll find there a lot of information about the mythical and mystical projectile-project-root-functions)
        • Improved Configuration

    It always feels great to revisit Projectile, as it’s both the first open-source project I ever created and the project I use more than anything else.

    Dec 3 (today)

    • More work on Projectile’s documentation and grooming the backlog
    • Preparing for another RuboCop bug-fix release (1.5.2 might land later today)

    Looking Forward

    So, what’s next? My main priorities for the Advent of OSS are currently:

    • Polish the Clojure Style Guide
    • Ship CIDER 1.0
    • Ship Emacs Prelude 1.1
    • Clean up Projectile’s backlog

    I probably won’t be able to achieve them all, but I’ve been told it’s good to be ambitious. If someone wants to help me out, be my guest. My projects have plenty of tickets tagged with Good First Issue that you might try tackling.

    I’ll try to post some updates here every few days, both to keep it up-to-date with my progress and to keep myself honest. That’s all from me for now. Keep hacking!

    P.S. In the time-honored tradition of the Advent, I’m inviting all of you to join my on the Christmas OSS adventure and see how far are you willing to go! It will be fun!

    1. Half my Twitter timeline is about the “Advent of Code” these days. 

Subscribe via RSS | View Older Posts