SFTP, root access and sudo

Suppose you log into a server with your own SSH user, have password-less sudo access and want to access files as root over SFTP.

Your attempt would probably look like this:

# sftp user@remote
Connected to remote.
sftp> cd /root
sftp> ls
remote readdir("/root"): Permission denied
sftp> sudo ls
Invalid command.

Not possible, right?

The answer is no! It actually is possible, albeit with some extra steps.

In my case the solution was simply this:

# sftp -s "sudo /usr/libexec/ssh/sftp-server" user@remote
Connected to remote.
sftp> cd /root
sftp> ls
files  here   some

What is happening here that instead of sftp running ssh -s user@remote sftp behind the scenes (you can tell by looking at the process list) it runs ssh user@remote sudo /usr/libexec/ssh/sftp-server. This way we manually run the standalone SFTP server shipped with OpenSSH after first elevating our privileges.

The problem with this idea is that sftp-server is stored away at a location that is not standardized and inconsistent in practice - as normally you don't run it directly.

Here are some differences I found:

System

Location

Arch, Alpine

/usr/lib/ssh/sftp-server

Debian/Ubuntu

/usr/lib/openssh/sftp-server

Fedora/RHEL

/usr/libexec/openssh/sftp-server


Handling this automatically is possible, but considerably less elegant:

sftp -s "exec bash -c 'for x in /usr/lib{exec,}/{open,}ssh/sftp-server;do [ -x \$x ]&&exec sudo \$x;done'" user@remote

Lastly, note that you can also use this to switch to a different user. It doesn't have to be root. For example:

# sftp -s "sudo -u john /usr/libexec/ssh/sftp-server" jack@remote
Connected to remote.
sftp> ls -l /home/jack/
remote readdir("/home/jack/"): Permission denied
sftp> ls -l /root
remote readdir("/root"): Permission denied
sftp> cd /home/john
sftp> ls -l
drwxr-xr-x    ? john  john      4096 May  4 15:37 documents
[...]