Technical notes › Use ‘sudo’ with aliases in fish
Something that’s slightly annoying on the command-line is that
sudo only works with executable binaries, and cannot know about shell aliases.
I have a bunch of
ls-related aliases, like these:
alias l 'exa' alias ls 'exa' alias ll 'exa --long --git --header' alias la 'exa -a --long --git --header'
(As mentioned in Make fish start faster by avoiding
alias, they are actually functions rather than aliases, but the effect is the same for both.)
I’ve been writing
ll instead of
ls -l for so long now that I instinctively try to use it with
sudo as well.
However, sudo has no idea that it exists, because it’s an alias, rather than a file in the
$PATH it can execute.
This means that whenever I try to run this command using sudo, instead of a long file listing, I see this:
sudo: ll: command not found
I deal with this by having a fish wrapper function that runs the output through a sub-fish if it’s a function.
The ‘sudo’ fish wrapper
I have this function defined, which is also called
function sudo -d "sudo wrapper that handles aliases" if functions -q -- $argv set -l new_args (string join ' ' -- (string escape -- $argv)) set argv fish -c "$new_args" end command sudo $argv end
It works by testing if the command that sudo is going to run — the first argument — is a defined function or fish alias, and if it is, it runs a new temporary fish session through sudo instead. The command that gets run looks like this:
sudo fish -c 'll'
fish that gets run under
sudo reads my list of aliases before running the command, so when it tries to execute
ll, it’ll run the contents of the alias with root privileges.
Some notes about how this is implemented:
- The uses of the
stringbuilt-in are there to properly escape spaces before the function arguments get handed to the temporary fish process. Because this process takes two arguments (‘
-c’ and a line of shell script to run) we need to take care when combining multiple arguments into one single string.
- We need to run the result though
commandto stop the wrapper function from recursing and calling itself.
- Finally, we need the ‘
--’ meta-argument before the calls to
stringto stop arguments to the program being run under sudo being treated as arguments to the
The function above is an improved version of one given in an answer to this Stack Overflow question. That one has issues with arguments containing spaces; the function on this page has that issue fixed.∎