How to Use Sudo to Redirect Output to a Location I Don't Have Permission to Write To

How do I use sudo to redirect output to a location I don't have permission to write to?

Your command does not work because the redirection is performed by your shell which does not have the permission to write to /root/test.out. The redirection of the output is not performed by sudo.

There are multiple solutions:

  • Run a shell with sudo and give the command to it by using the -c option:

    sudo sh -c 'ls -hal /root/ > /root/test.out'
  • Create a script with your commands and run that script with sudo:

    #!/bin/sh
    ls -hal /root/ > /root/test.out

    Run sudo ls.sh. See Steve Bennett's answer if you don't want to create a temporary file.

  • Launch a shell with sudo -s then run your commands:

    [nobody@so]$ sudo -s
    [root@so]# ls -hal /root/ > /root/test.out
    [root@so]# ^D
    [nobody@so]$
  • Use sudo tee (if you have to escape a lot when using the -c option):

    sudo ls -hal /root/ | sudo tee /root/test.out > /dev/null

    The redirect to /dev/null is needed to stop tee from outputting to the screen. To append instead of overwriting the output file
    (>>), use tee -a or tee --append (the last one is specific to GNU coreutils).

Thanks go to Jd, Adam J. Forster and Johnathan for the second, third and fourth solutions.

How to use output redirection with sudo?

The normal pattern to do this is:

ssh user@host 'cat | sudo tee the-file'

tee redirects output to a file and can be run with sudo.

If you want to mimic >> where the file is appended-to, use sudo tee -a.

You'll also need to be sure to quote your command as above, so that the pipe isn't interpreted by the local shell.

Edit

The tee command is part of POSIX, so you can rely on it existing.

To redirect Standard Error as well:

ssh user@host 'some_command 2>&1 | sudo tee output-file'

How to use tee when using sudo

You don't need to use tee, just put the redirection inside the command that's executed with bash -c:

sudo -H -u myuser bash -c 'timeout 2s ./binaryfile -gentoken > "$1"' _ "${save_log_dir}/update-${now}.log"

If you redirect outside, your original shell is trying to open the file, but it doesn't have permission. Putting it inside the bash argument executes it in the target user's shell, with their permissions.

The _ in the command line is a dummy value for the $0 parameter of the shell. You need that placeholder to be able to supply the filename as $1.

sudo echo something /etc/privilegedFile doesn't work

Use tee --append or tee -a.

echo 'deb blah ... blah' | sudo tee -a /etc/apt/sources.list

Make sure to avoid quotes inside quotes.

To avoid printing data back to the console, redirect the output to /dev/null.

echo 'deb blah ... blah' | sudo tee -a /etc/apt/sources.list > /dev/null

Remember about the (-a/--append) flag!
Just tee works like > and will overwrite your file. tee -a works like >> and will write at the end of the file.

sudo doesn't work when redirecting the output of sed to a file

Use the in place option, -i. Your syntax would be:

sed -i [pattern] filename

sudo cat EOF File doesn't work, sudo su does

Output redirection (e.g., >) is performed by bash, not by cat, while running with your UID. To run with root's UID use sudo:

sudo bash -c 'cat << EOF > /etc/yum.repos.d/some-name.repo
line1
line2
line3
EOF'

what alternative methods for sudo echo without bash -c

The problem you are encountering here is that the output redirection >/file.tmp has to happen with elevated privileges. This means that you either have to launch the script as it is with sudo my.sh, or perform the redirection in a way that gives it elevated privileges. It is not enough to run sudo echo because only echo would have elevated privileges, but the output redirection would run as your non-root user because it is a shell builtin feature, not an external command.

There is a standard tool called tee that can help with this. This method is commonly used when running curl to fetch data that needs to be fed to root, such as installing debian apt repository configurations and signing keys.

$ whoami
dho
$ whoami | sudo tee whoami.txt >/dev/null
$ ls -la whoami.txt
-rw-r--r-- 1 root root 4 2022-06-03T09:08:22 whoami.txt

So you can see that I launched whoami with my own user, but the file ended up being written with root permissions because tee, which replaces the output redirection from your original example, was launched as sudo tee.

Why cannot root writes on a file that it owns and has write access to?

The redirection happens before the commands are run, i.e. using the original user.

Work-around:

sudo sh -c 'echo "hi" >> a.txt'


Related Topics



Leave a reply



Submit