Sam Thorogood

Sam's dotfiles highlights

Most developers end up creating some sort of dotfiles repo to contain configuration files for their *nix-like machines (macOS, Linux, etc). Rather than just setting up every machine you access in an ad-hoc way, you can create a repo to keep the same environment for your terminal everywhere.

There's a lot of starting points out there that you could clone from. If you know git, my advice would be to follow how to manage them with git—this guide lets you use a special dotfiles command.

My dotfiles are pretty boring, but I think there's a few parts that make mine special. Let's talk through them. I use bash, the default in most places.

  1. Layout—what calls what and how things are run
  2. Platform Help—distinguish macOS and Linux
  3. Helpers—take a look inside my scripts

Layout

My layout is pretty simple. The .bash_profile file immediately runs .bashrc, so there's no difference in how you log in (the two files being different is a big source of confusion for newbies—so just merge them! 🤣).

Bash layout

One file that I've used for years is .bash_functions (originally written by a friend back in ~2009). It provides a few helpers that make dealing with paths "safe". Here's a simple example—both pathprepend and ssource check that the path or file exists before using it:

#!/bin/bash

source "${HOME}/.bash_functions"  # first line of .bash_profile

# adds to $PATH if the directory exists
pathprepend "/opt/local/sbin"
pathprepend "/opt/local/bin"
pathprepend "${HOME}/.local/bin"

# runs contents of .bash_local if it exists (not checked in, for
# custom changes on each machine)
ssource "${HOME}/.bash_local"

A Note On SSH

🚨 While I do check in my id_rsa.pub file to every machine—this is the public, sharable part of your identity—I don't include id_rsa in my dotfiles repo. I keep it only on machines I have physical access to, such as my laptop or a server in my house.

This is important. Your id_rsa (or id_dsa?) is private and even if it has a password, is going to be cracked if you accidentally upload it somewhere public.

Platform Help

At the top of my .bashrc, I set a handy variable:

IS_MAC=""
UNAME=$(uname)
if [ "${UNAME}" == "Darwin" ]; then
  IS_MAC="yes"
fi

I switch between macOS (which is really BSD and has older versions of things) and Linux, so this helps make a choice if things work differently, as it does for the params to ls:

if [ $IS_MAC ]; then
  alias ls='ls -lGho'  # macOS doesn't support `--color=auto`, needs `-G`
else
  alias ls='ls -lh --color=auto'  # on Linux, `-G` means "no groups"?!
fi

Helpers

I've got a few scripts inside my ~/.local/bin folder. Some of which I use almost daily. 📜❗#️⃣

Image Compression

I have two scripts—crush and pcrush—which compress a single PNG image, or compress many in parallel. I never remember the arguments to run the tools pngcrush or zopflipng (better), but it's always worth shrinking your images before you upload them (gotta go fast!).

I built pcrush so I could also take advantage of multiple CPUs—turns out both the tools above run on a single CPU only, but if I have 100s of images, I want to crush them fast. I can make my CPUs do this:

parallel compression

Git Status

I have a script called gstate which outputs a number of things based on the current Git repository. It includes branches, normal status, any stashed changes, and known divergence from upstream (i.e., the remote repo you've mirrored from).

It's handy and honestly burned into my muscle memory forever now. 💪

If you're curious, check it out here.