22
$ source /etc/environment 

$ sudo source /etc/environment 
[sudo] password for t: 
sudo: source: command not found

It seems that a different shell than bash is run to execute source /etc/environment and that shell doesn't have source as builtin.

But my and the root's default shells are both bash.

$ echo $SHELL
/bin/bash

If sudo indeeds uses a different shell, why is it? I saw slm's reply, but don't understand in my case.

3
  • 5
    source is a shell builtin..you can not use sudo to run a shell builtin like an external command..
    – heemayl
    May 8, 2015 at 22:12
  • Is the issue that you cannot read the file, or that you want the environment defined in the file to apply to subsequent sudo commands?
    – Random832
    May 9, 2015 at 5:07
  • @Random832: want the environment defined in the file to apply to subsequent sudo commands
    – Tim
    May 9, 2015 at 13:02

3 Answers 3

34

source is a shell builtin, so it cannot be executed without the shell. However, by default, sudo do not run shell. From sudo

Process model

When sudo runs a command, it calls fork(2), sets up the execution environment as described above, and calls the execve system call in the child process

If you want to explicitly execute shell, use -s option:

# sudo -s source /etc/environment

Which is still useless because after shell is exited, environment changes are lost.

1
  • This worked for me. I just ran into an error though which I thought I might share it and its workaround as it might happen to you too. /root: Is a directory. I think it is a common problem when inserting your environment variables using vi or vim. I turned out that the .sh file which I tried to source has a tilde character (" ` ") at the end of it. By removing it from the file, sudo -s source /etc/environment worked without no error. May 28, 2020 at 5:42
12

In the realm of solving the problem rather than answering the question, here's the most obvious (to me) way to source a file which only root can read:

source <(sudo cat /etc/environment)

This uses process substitution. It takes the output of the cat command and turns it into a pseudo-file, which you can pass to source. source then runs the commands in the current shell.

Note that on most systems, /etc/environment is world-readable, so you ought to be able to just run this:

source /etc/environment
1
  • 1
    this works, the accepted one doesn't Aug 3, 2018 at 9:50
2

sudo expects a command but you are giving a shell builtin so it cannot find the command. If you write type source, you can see the output: source is a shell builtin and the output of which source is empty.

For example sudo strace will work and which strace will give output because strace is a command.

Edit: Also, you can see sudo su;sudo source /etc/environment works nicely so different shell is not used.

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .