I recently migrated my dotfiles from rcm to GNU Stow . I didn’t
really have a reason, I wasn’t unhappy with rcm at all, but I saw Stow mentioned
somewhere and felt like trying it out. After migrating, I still don’t have
strong feelings – both tools are appropriately good and boring – but I can at
least now speak to the differences and maybe that would…
I had to URI-encode the components of a URL in node the other day. You’d think
this would be trivial, particularly in the language of the browser. Turns out,
not so much. I ended up deep-diving the relevant RFCs, so I thought I’d
summarize here to save you (well, future me) the effort. 
 Let’s get into it. 
 The URL in Question 🔗 Given…
GitHub’s enshittification has gotten entirely out of hand. Not only are they so
obviously and unethically exfiltrating all of my code into their
drain-lake-give-wrong-answer box, but they’re simultaneously forcing the
business they’ve illegally built on it down my throat in every part of the UI
that still functions, which is becoming fewer and fewer these days.…
I see a lot of this-setup or setup-that GitHub actions around. They all wrap
the @actions/tool-cache library to install some pre-compiled binary. If
 tool-cache exists, why do we need all these separate actions? What happens if
I can’t find a -setup action for the tool I want to use? What if there are
multiple? Do I need to write yet-another curl | tar or gh release download…
Semigroups are, quite possibly, my favorite part of Haskell. I’m constantly
surprised how much business logic can be expressed by a single foldMap using
the correct Semigroup. My co-worker Evan has said as much , and
better. 
 One perhaps unfamiliar Semigroup is Endo . Don’t let the heady name confuse you
too much, it’s a newtype over (a -> a) , any…
Test coverage is a tricky topic. I’m of the opinion that 100% test coverage is
not a useful goal. Some take this opinion and discard the idea of tracking
coverage altogether. However, there are interesting things you can do with test
coverage information in the context of a Pull Request, such as asking if the
lines introduced in the Pull Request are covered by tests, or if…
This may be obvious or well-known to some, but I discovered the other day that
you can make a MonadReader env instance for any MonadState env m trivially.
This makes total sense conceptually, since State is just Reader with the extra
ability to modify. 
 I’m going to talk it through at length, how it works and why I needed it, but if
you’re just interested in…
I love concrete examples that illustrate the day-to-day of the professional
Haskell programmer, and show the inspiration for that entirely-untrue quip, “if
it compiles, it works”. What is true is some variation of “if it compiles, any
logic encoded in the types is correct”. That statement is a tautology (if a
program type checks, it means the types are…
Some may say that you shouldn’t write shell beyond a certain, very low bar of
complexity. If you reach for arrays, certainly associative arrays (gasp!), or
if your script approaches 20, 50, or 100 (how dare you!) lines, maybe you want a
“real” language. 
 Everyone’s bar is different, but I’d wager actual options parsing is above it
for most. I…
For as long as I’ve built Docker images on CI, I’ve fought the layer caching
problem. Working on Haskell projects of many dependencies, an un-cached
multi-stage build can take close to an hour. That’s a deal-breaker for
deployments, where ten minutes is a reasonable maximum. 
 At some point, Circle quietly released a docker_layer_caching flag in their
…
I maintain an Auth plugin for authenticating with Google OAuth2
in a Yesod application. This plugin has always had functionality overlap with
the GoogleEmail2 plugin in the yesod-auth package. Our
Google plugin was present, removed (due to said overlap), then returned again,
along with some discussion about deprecating GoogleEmail2 in
favor of it. What was missing was the…
The following are all the things I want in place for a Haskell project. This is
primarily a copy-paste-able reference for myself, but I’ve also tried to explain
or generalize some things to make it useful for anyone first bootstrapping a
Haskell project. 
 NOTE : if you were brought here after googling something like “how to Haskell
on Circle 2.0”,…
In a recent effort to keep my latest laptop more standard and less customized,
I’ve been experimenting with XTerm over my usual choice of rxvt-unicode. XTerm
is installed with the xorg group, expected by the template ~/.xinitrc , and
is the terminal opened by most window managers’ default keybindings. 
 The only downside so far has been the inability to select and open…
Deleting Git tags that have already been pushed to your remote is something I
have to google literally every time I do it; why the invocation is so arcane, I
don’t know. Finally, I decided to automate it with a custom sub-command: 
 ~/.local/bin/git-delete-tag 
 #!/bin/sh
 for tag ; do 
 git tag -d ' $tag ' 
 git push origin :refs/tags/ ' $tag ' 
 done 
…
A while back, I launched a side project called tee-io . It’s sort of like a
live pastebin. You use its API to create a command and then send it
buffered output , usually a line at a time. Creating the command gives you a
URL where you can watch the output come in in real time. We use it at work to
monitor the commands run by our bot instead of waiting for the…
While reading Understanding Computation again last night, I was going back
through the chapter where Tom Stuart describes deterministic and
non-deterministic finite automata. These simple state machines seem like little
more than a teaching tool, but he eventually uses them as the implementation for
a regular expression matcher. I thought seeing this concrete use for such…
Every time I read Learn You a Haskell , I get something new out of it.
This most recent time through, I think I’ve finally gained some insight into the
 Applicative type class. 
 I’ve been writing Haskell for some time and have developed an intuition and
explanation for Monad . This is probably because monads are so prevalent in
Haskell code that you can’t…
Lately at work, I’ve been fortunate enough to work on a JSON API which I
was given the freedom to write in Yesod . I was a bit hesitant at
first since my only Yesod experience has been richer html-based sites
and I wasn’t sure what support (if any) there was for strictly JSON
APIs. Rails has a number of conveniences for writing concise controllers
and standing up…
In lecture 5A of Structure & Interpretation of Computer Programs,
Gerald Sussman introduces the idea of assignments, side effects and
state. Before that, they had been working entirely in purely functional
Lisp which could be completely evaluated and reasoned about using the
substitution model. He states repeatedly that this is a horrible thing
as it requires a far more complex…
Hspec is a BDD library for writing Rspec-style tests in Haskell.
In this post, I’m going to describe setting up a Haskell project using
this test framework. What we’ll end up with is a series of tests which
can be run individually (at the module level), or all together (as part
of packaging). Then I’ll briefly mention Guard (a Ruby tool) and how
we can use…
In my continuing efforts to strip my computing experience of any
non-essential parts, I’ve decided to ditch my statusbars. My desktop is
now solely a grid of tiled terminals (and a browser). It’s quite nice.
The only thing I slightly missed, however, was notifications when one
of my windows set Urgency. This used to trigger a bright yellow color
for that workspace…
For almost 7 years, now I’ve had a desktop at home, running, serving
(among many things) my personal blog. Doing so is how I learned much of
what I now know about programming and system administration. It gave me
a reason to learn HTML, then PHP, then finally Haskell. It taught me
Postgres, Apache, then lighttpd, then nginx. Without maintaining this
site myself, on my own…
Have you ever wanted to mock a program on your system so you could write
fast and reliable tests around a shell script which calls it? Yeah, I
didn’t think so. 
 Well I did, so here’s how I did it. 
 Cram 🔗 Verification testing of shell scripts is surprisingly easy. Thanks to
Unix, most shell scripts have limited interfaces with their environment.
Assertions…
The recent hullabaloo with Snowden and the NSA is very scary. I agree
with most Americans that The Government is doing some pretty evil things
these days. That said, I also believe that we as cloud users are
primarily responsible for the privacy of our own data. Thankfully, the
problem of transmitting or storing data via a 3rd party without granting
that party access to said…
What if we wanted to write a Haskell program to behave something like
this: 
 $ runhaskell hello.hs
Hello who?

$ runhaskell hello.hs Pat
Hello Pat

$ runhaskell hello.hs -u Pat
Hello PAT
 One implementation may look like this: 
 main :: IO () 
 main = do 
 args <- getArgs
 
 let name = case args of 
 ( '-u' : n : _ ) -> map toUpper…
For the longest time, my interaction with music was via MPD. I had a
substantial collection playing on my always-on desktop. I could connect
from anywhere to control the playlist and pick up the stream via its
HTTP output. I had effectively built my own cloud music service. 
 While that was great, there were a few annoyances: 
 First, I had to juggle two interfaces while…
A while back, I made a post about deploying yesod apps to heroku.
The method used back then is no longer required (thank God!) and
deploying to heroku is super simple these days. So simple, in fact, that
I won’t reiterate those instructions here, this post is about something
a bit more specific. 
 Chances are, your app is using a database. And you probably don’t…
Recently, Yesod released version 1.2. You can read the announcement
 here , the changelog here , and a detailed
blog post about the subsite rewrite here . These resources do
a great job of getting users’ apps up on 1.2. This post won’t rehash
those, it is instead intended for those of you (like myself) who
maintain libraries dependent on Yesod. 
 The large…
I hear and see a lot of passing complaints about dealing with a large
amount of mail. I myself subscribe to a few mailing lists which get
quite a bit of traffic and these are usually the first to be ignored
when I get behind. Once a backlog of unread mail piles up it can be hard
to get any traction. The sad part is I enjoy that content, so I
definitely don’t want to be…
If you’re like me and absolutely abhor the Caps Lock key, you’ve
probably figured out some way to replace it with a more suitable
function. I myself have settled on the following command to make it a
duplicate Ctrl key: 
 $ setxkbmap -option ctrl:nocaps
 This works great when placed in ~/.xinitrc and run as X starts, but
what about USB keyboards which are…
Aurget was one of the first programs I ever wrote. It’s seen decent
adoption as far as AUR helpers go and it’s gradually increased its
feature set over the past number of years. 
 The codebase had gotten a bit krufty and hard to follow. I decided to
refactor to more isolated functions which didn’t rely on so many global
variables. This directed refactor has…
I’ve heard rumors that a Google Chromebook can make a surprisingly
sweet machine for a developer. As someone that works exclusively in the
console, it’s easy enough to SSH into a server to do the actual work.
Since my apps are either command line tools or web sites, I can easily
test them remotely as well. I only need something with a terminal and
browser……
Once I start my new job at thoughtbot , I’ll be working on a variety
of ruby and rails projects at the same time. This, combined with the
current 2.0 transition, means I once again need a ruby version
management tool. 
 Chruby is the third (by my count) “new hotness” when it comes to
these python-inspired virtualenv clones. First there was rvm which
has a…
Recently, while watching Corey Haines and Aaron Patterson
 pair-program , I heard Mr. Haines mention vim’s “hard mode”.
Apparently, this is when you disable the motion commands h, j, k, and l. 
 It’s absurd how great this exercise is for increasing your knowledge of
vim. There are so many better ways to do everything . Just like
complete novices might…
A lot of smarter people than I have come up with the idea that moving
your business logic out of framework based classes and into Plain Old
Ruby Objects (POROs) is a Good Thing. 
 Being less tied to your framework makes upgrades easier. It also means
you can test these objects without loading rails. That’s really the only
way to get super fast unit tests. It’s also…

 BIG FAT WARNING 
 One thing to note, and the reason why I’m no longer using this setup:
screen sessions started from within X cannot survive X restarts. If you
don’t know what that means, don’t worry about it; if you do, you’ve been
warned. 

 

 A while back, Arch switched to systemd for its init system. It’s
pretty enjoyable…
If you work on a project that’s been around for a while, chances are it
might still be using SVN for version control. Even if you can’t get
buy-in from Management or Ops to move to Git, you can still get most of
the benefits by learning the ins and outs of the git svn sub command. 
 Initial Clone 🔗 $ git svn clone --stdlayout svn://svn.example.com/project
 Using…

 for each desired change, make the change easy (warning: this may be
hard), then make the easy change 
 — Kent Beck, September 25, 2012 
 Here’s some code from our main application helper. It provides a small
method for redirecting the user based on a goto parameter. It uses two
helpers itself to append google analytics parameters to the url before
redirecting.…
My latest bash-to-ruby rewrite was dvdcopy to dvd2iso. I changed the
name both to disambiguate, and because my primary use case was no longer
to duplicate disc to disc, but to just generate the ISO. It’s very
simple to just burn that ISO back to disc if I feel like it. 
 The benefits of the new script are: 
 
 Less and simpler code 
 Coded at a higher level 
…

The following was written for [issue 7][issue] of Web & PHP magazine.
Please, if you enjoy this article (or my articles in general), take the
two minutes to register there and download the full PDF to show your
support.
 

 Why Haskell? 🔗 There’s much more to Haskell than just the buzz-words like laziness and
parallelism – which are completely…
Ruby’s open classes are great for adding behavior to existing objects.
Though it’s a language feature, there to be used, I’d argue that the
majority of times it is used, Open classes weren’t the most appropriate
tool. 
 First of all, you may be setting yourself (and other developers) up for
confusion. Not knowing where methods come from or why a method…
Fake S3 is a gem designed to run a small server on localhost that
will correctly handle AWS/S3 GETs and PUTs (among others) while using
the local filesystem as the storage backend. This has a number of
benefits for anyone working on an application with AWS integration. 
 Probably the biggest benefit is offline development. There’s also a
lower configuration burden as…

 Update This post describes compiling a Yesod application locally
using a VM to achieve the compilation on a Heroku-like machine, then
pushing the binary up to Heroku to be run. This is an annoying route
which is no longer necessary (as mentioned in the comments), so don’t
follow it. Instead follow [this][] guide.
 

 The following are the steps I followed to…
Regardless of what editor you choose or how deeply you decide to extend
or configure it, the most important thing for a professional programmer
regarding her tool set is awareness. 
 You need to be acutely aware of situations where you do something
repeatedly or slowly that you should automate or speed up. Quality
editors like vim or emacs expose powerful constructs for doing…
I’m a big fan of Avdi Grimm’s thoughts about writing confident ruby. I
think it’s important to not clutter things with a bunch of nil-checks or
exception handling. When you’re focused in at the method level you
should trust that your objects are valid and the methods you’re calling
behave. 
 
 In this post I use the term “assertive”…
tl;dr: it’s just like aurget but more stable and faster 
 Developing aurget was getting cumbersome. Whenever something went wrong,
it was very difficult to track down or figure out. The lack of standard
tools for things like uri escaping or json parsing was getting a bit
annoying, and the structure of the code just annoyed me. There was also
a lack of confidence when…
Despite the enormous increase in popularity lately, it seems some people
still don’t know about this project or how it can improve your
development work-flow. 
 So, what is it and why should you care? 
 Vagrant is a convenience tool for doing Virtual Machine based
development. The obvious benefits that you get by using VMs for
development are: 
 
 Isolation -…
If you write console based applications in ruby, chances are you’re
going to want to get some test coverage on that eventually. StringIO 
is a great class to use when you want to assert that your application
outputs the correct stuff to the screen. 
 We can modify the global variable $stdout to be an instance of
 StringIO for the duration of our tests. Any method that…
Keter is Michael Snoyman’s answer to the Yesod deployment
“problem”. This is something I’ve been looking for a good solution to
for some time now and keter does a really great job. 
 Keter is meant to run as a service. It sets up its own workspace and
watches for keter “bundles” to be dropped into an incoming/ directory.
A keter bundle is…
Sometimes it’s fun to do something completely useless. 
 Recently, I wrote a post about how awesome the Maybe type
is in Haskell. In the post, I talked about Functors and Monads and how
Maybe can help us understand them. 
 Shortly thereafter, I was bored on the train one day and decided to
implement Maybe and its functor instance in ruby. 
 
In this post…