The Stochastic Game

Ramblings of General Geekery

7 year old kid: “That’s super old, super super old. Like, from the 20th century.”

Mercurial Advent Blogging

Here’s another advent blog series! This time it’s from Kamal Marhubi and it’s on the subject of Mercurial. It’s pretty interesting, especially for giving a fresh perspective on Mercurial’s user experience.

The introduction post lays down some of what makes Mercurial interesting (phases, changeset evolution, extensibility) while the third post catches up to another cool thing (revsets, one of my favourite Mercurial features) that was missing from that initial list.

Extensions and papercuts

There’s a good article in the series about how Mercurial’s reliance on extensions (and more specifically the need to explicitely enable them) is one of the several “papercuts” you get when you start using it. This reminded me of Josef Sipek’s “Modern Mercurial” blog series which starts with an article precisely about that problem:

Then it suddenly hit me —- before these tweaks, I had been using Mercurial like it’s still 2005!

I think this is a very important observation. Mercurial didn’t seem to be improving because none of the user-visible changes were forced onto the users.

The problem is that the Mercurial devs have an extremely strict approach to how the CLI should behave, and how no breaking changes should ever be introduced. This means that:

  1. No “dangerous” commands should be accessible by default (“_don’t give the user opportunities to shoot their own foot_”), which explains why history rewriting commands like rebase are disabled out-of-the-box.
  2. Things that were later added (like colours, pager support, etc.) were often done in an optional extension to not break previous behaviour.

Arguably, these strict rules are partially the reason why the Mercurial CLI is so nice to use compared to other CLIs like Git’s, but they’re also obviously causing a lot of pain elsewhere.

I naively think this might be somewhat fixable by:

  • Making the first hg run setup some sane default if it doesn’t find any user .hgrc (i.e. better bootstrapping).
  • Relaxing some of the strict CLI rules by realizing that most use-cases that rely on specific historical behaviours (like automated scripts) are already most probably setting environment variables like HGPLAIN, in which case Mercurial can disable some of the more “human facing” features.

But of course, it’s lot more complicated than this… and to some degree, this was addressed with the tweakdefaults setting (formerly known as “friendly hg”), but, ironically enough, you still need to know about enabling it, since it default to false, of course.

Staging areas

The fourth post talks about how Mercurial doesn’t have a staging area (a.k.a. index) like in Git.

It’s kind of funny to me that we have people who started with Git as their first (and sometimes only) VCS, and it will soon dawn on them that, frankly, there’s nothing out there quite like Git’s index (well, at least not in any of the half-dozen VCSes I’ve used so far). Git’s pretty unique on that front.

Although I don’t recommend trying to emulate a tool’s idiosyncratic workflow when using another tool, people coming from Git invariably ask about this so there’s always been some partial answer for Mercurial. A few years ago, the MQ extension was that answer (it kinda gives you something that looks like multiple staging areas!), but it seems that most of the Mercurial community has moved away from it (I have too). MQ is still available for those who want it, but these days it seems that using secret phases and history rewriting is more common (and it also kinda gives you multiple staging areas too!).

I don’t really do that, but I imagine it would work along the lines of:

newstage = commit -s -m "STAGING AREA"
upstage = commit --amend

So when you start working on something new, you push your work-in-progress with hg newstage into a secret commit called “STAGING AREA”. Since it’s secret, it won’t get pushed and will stay local. Then, as you keep working, you run hg upstage every now and then to “grow” that commit. When it’s ready, you change that commit’s phase to draft. It’s a bit clunky (there are 2 aliases when ideally there would be only one) but you get the idea, and with a bit of scripting I’m sure that it’s possible to get it down to a similar UX as Git’s.

Twelve days to go

Anyway, we’re still half-way to Christmas so check out Kamal’s blog for the rest of the series (assuming he keeps it going :) ).

When I’m done with your buddy here, you’re next, tasty little marzipan pig

Vimways Advent Blogging

Advent blogging, i.e. blogging about a specific subject every day between December 1st and December 24th, seems to be picking up steam quite a bit this year. In the previous years, FastMail was pretty much the only one in my feeds doing this but, ironically, as they stopped doing it this year, it’s been replaced by others like’s Manton Reece (although he’s only doing half of it) or Vimways.

Inspired by 24ways, another advent blog dating back a dozen years, Vimways is, as you might guess, about Vim!

I was flattered to have Gutentags, my little Vim plugin, mentioned in the 2nd entry of the blog, even if the Daniel Moch, the author, said he stopped using it a while ago. Since the various methods mentioned in the article are not all equivalent, I figured I would add some clarifications here.


Stockholm people! I’ll be in your beautiful city next week for the annual Frostbite DevDays, so ping me if you want to meet for fika or even just say hi!