Monday, May 25, 2015

Dotfiles: More Than Meets the Eye

    Dotfiles are pretty important. Anyone who has used a *NIX OS for a while will recognize the truth of this simple statement. For the uninitiated, Linux, Unix, and BSD (and OSX, which is a variant of BSD) operating systems have many things in common. One of these things is that files whose name begins with a period, like .config for example, are treated specially and hidden from the vanilla file list command, ls. Now, they aren't super secret or anything. A simple -a added to the ls command (making it ls -a) will show them again, they are just hidden by default. Due to the naming and pronunciation (.config would be spoken dotconfig by most people) they have become known collectively as dotfiles.

    The assumption is that they will be system files, usually configuration settings and the like, that you won't work with every day and won't want cluttering up your file listings all the time. Which is a pretty good assumption considering that the things multiply like crazy. These days it isn't just dotfiles, you have entire subdirectories that hold all sorts of things for whatever program uses them. Example, I have a .weechat that holds all the config settings, plugins, and chat logs from my irc client. Many programs use these the way Windows programs use their directory under Program Files. It is a good system, as it keeps the config easily findable in the user's home directory and also keeps the config user specific.

    Since they control the configuration of so many different pieces of your system, the dotfiles become important. They are how your system has been configured the way you like it. How it knows the behavior you want. They become very valuable, and over time, very difficult to replace. Some people spend years making small modifications to files like .bashrc and .vimrc until the resulting config is perfect. However, recreating it from scratch might be impossible as you won't remember what the setting you found on that obscure blog 3 years ago that solved this one issue was. You basically have to start over and tweak slowly until you arrive at another working, but inevitably different, config.

    This becomes a real pain point in a few scenarios. One is data loss or wiping your system for any reason. If you didn't have an up-to-date backup that you were sure to configure to include your dotfiles, you just lost all your config and get to start over.  In the past I used JungleDisk as a backup solution. (Disclaimer: JungleDisk is owned by my employer, Rackspace. They weren't owned by Rackspace when I started using it (nor was I employed by Rackspace then either.)) When I was using Windows laptops, it worked great. When I was using it on Linux systems it worked ok, but restored with weird permissions. That was ok because I had the data and could fix the permissions as needed. Now, I use a MacBook Pro running OSX. In the three years I've had it, I have already had the hard drive fail once. After my failed drive was replaced, I was given back a freshly imaged version of OSX that was newer than the one I had been running before. I promptly set JungleDisk to restoring my backup. In short order, I had an unbootable system. It took me many cycles of getting it re-imaged and trying to restore my backup before I was able to figure out the culprit files and exclude them from the restoration. It looked like one of the applications (I've long since forgotten which) was overwriting a system library with an older version when JungleDisk restored it. This was a very bad experience. I've since stopped using JungleDisk (for other reasons) and haven't started using an alternative yet, because I'm lazy and apparently like to live dangerously. Most of my data is backed up or recreatable, but it's those dotfiles that I'm worrying about again, especially as I creep closer to the date when I can get a new laptop.

    Which brings us to the other similar scenario of a system upgrade. If you are like me, you use a work supplied laptop for most things. It becomes heavily customized over time, both to account for your personal tastes and also with little things that make your job and working with your work's environment much easier. In my case, I have bash aliases and ssh config settings that simplify logging into production systems, tunneling through bastion servers, remembering what ssh key is used where and what port is needed. The other thing about a work laptop is that it is usually on a replacement/refresh cycle. In fact, mine is due for refresh this year. At this point I've had 3 years to customize it, and now I am faced with starting over and recreating everything. Having gone through this already when my drive died, I am not looking forward to doing it again.

    The last scenario that comes to mind is someone who frequently works on multiple systems. Maybe you use a desktop at work and another at home, or a laptop mixed with some other systems, or something else where you are either frequently finding yourself at a new machine or maybe one that you haven't used in a little while. You'd like to be able to have any tweaks you make on one system be reflected on the others, or if it is a completely new system you would like to get your configuration onto it as quickly and painlessly as possible.

    So, you start looking for ways to bring your dotfiles with you. The ideal scenario for me would be that I could login to a new system, issue a few commands, maybe manually import a ssh and pgp key I maintain on an encrypted drive somewhere, and have my system configure itself, dotfiles and standard applications I use. Some people claim that Vagrant is perfect for this, and while it does sound useful it has some downsides. First, it is running enclosed environments inside VMs. This is probably good practice, and provides isolation, but it does not do anything for configuring the base system itself. It would also require a serious workflow change, which isn't a show stopper, but does mean a substantial amount of work to get into place. In short, I want to look into using Vagrant in the future, but the problem it solves seems to be a little different than this specific one.

    A growing trend is to store your dotfiles on github. I started down this road, and will go into more details about why, and what problems I ran into, in the next post in this series.