At NeoSmart Technologies, we’re huge fans of the new Windows Subsystem for Linux,1 and have spent a lot of time trying to make the transition between the native Win32 subsystem and the Linux/WSL subsystem as seamless as possible.
For those of you that haven’t already seen it, we recommend reading our previous article Meet $, your new best friend for WSL for an introduction to WSL and
$, our nifty helper utility that lets you directly run Linux commands in your Windows workflow. In brief, we developed
$ (also known – though less affectionately – as
RunInBash) to make it possible to run Linux utilities directly from within a Windows workflow, complete with arguments,
stderr redirection, and more.
$ makes it dead simple to run any Linux command by prefixing it with — yup, you guessed it —
$, sometimes even that isn’t easy enough. For example, a lot of the developers at NeoSmart don’t use bash as their primary shell;2 so having to run another shell, say fish, by keying in +R then having to type in
$ fish, while still a distinct improvement over
bash -c fish, just didn’t cut it. And it’s not just a shell – there are a lot of “stand alone” command line utilities that developers rely on enough to launch directly without first entering a shell, such as
The ultimate solution we’ve landed on is a simple
bash batch script that you can copy locally as many times as you like to launch any Linux tools you desire – without ever writing or changing a line of code.
Let’s jump straight into the batch file and then we’ll talk about how it works:
@echo off set cmd=%~n0 $ %cmd% %*
Disappointed? Why, were you expecting more? That’s really all there is to it. The batch file above, when copied to a file called, let’s say,
ssh.bat will run
ssh under WSL, forwarding any arguments you pass to it along. All you have to do is put it in your
So how does it work? First, the batch file gets its own name via the
%~n0 magic syntax.3 This gives us the file name without the directory component, so in this case,
ssh – which will be taken as the name of the command to run on the Linux side of things.
The rest of the magic is all thanks to
$, which takes care of escaping arguments and passing them to
bash.exe in such a way that you can keep your sanity instead of pulling out your hair trying to figure out how to double-escape an
' in an argument enclosed in
" when your command contains spaces and you need to pass it in to
bash -c enclosed in another… forget it. That’s what
$ is there for.
Have another Linux tool you use often? Just copy your
ssh.bat over to
tool.bat and you’ll be on your merry way. If you want to get all fancy, you can even create a symlink instead, and then if you ever want to make some changes to this batch file (though hopefully you’ll never need to) you’ll only need to change one and the rest will automatically follow suit. It really couldn’t get any easier than this.
If you don’t already have
$ installed, you can either download it here or install it with chocolatey via
choco install RunInBash.