Run specs/tests from within vim without blocking your flow

Everyone knows how great Guard is for running tests automatically. However, I hit :w involuntarily all the time, I’ve spent so much time in vim that I cannot go even a few seconds without hitting :w. I even do it in text areas on web pages, But I digress. Because of this, I unintentionally trigger my specs even before I complete them.

I have seen many people use tmux to get it working on demand. However, I use xmonad and I don’t want to learn another app to tile/organize my terminals. I can do them easily in xmonad.

So, my first attempt was to create a daemon in go which would listen for new commands on a unix domain socket. I almost finished it (You can check it here: https://github.com/minhajuddin/cmdrunner). However, it seemed too much work for something simple. We all know that we can run a command in background on linux by appending an & to the end. My final setup turned out to be much simpler than I anticipated. Too much thinking cost me a couple of hours.

The setup contains two parts.

###1. A script to run commands in background by redirecting the stderr and stdout properly

1
2
3
4
5
6
7
8
9
10
11
12
13
#!/bin/bash
#~/.scripts/runinbg
#Author: Khaja Minhajuddin
#Script to run a command in background redirecting the
#STDERR and STDOUT to /tmp/runinbg.log in a background task
echo "$(date +%Y-%m-%d:%H:%M:%S): started running $@" >> /tmp/runinbg.log
cmd="$1"
shift
$cmd "$@" 1>> /tmp/runinbg.log 2>&1 &
#comment out the above line and use the line below to get get a notification
#when the test is complete
#($cmd "$@" 1>> /tmp/runinbg.log 2>&1; notify-send --urgency=low -i "$([ $? = 0 ] && echo terminal || echo error)" "$rawcmd")&>/dev/null &

###2. Vim function to call this script with the current filename

1
2
3
4
5
6
function! RunSpecs()
:silent!!runinbg bundle exec rspec % "you can tweak this to your liking
redraw! "without this the screen goes blank
endfunction
nnoremap <C-d> :call RunSpecs()<cr>

You can check the log of your tests by running tail -f /tmp/runinbg.log

Update: Added a version with notification


I am currently working on Zammu which makes Automatic Deployment of static websites to Github Pages very easy. I would love to get your feedback on it, Use the invitation code KHAJA