167

I've noticed that my application uses different version of NodeJS when running from sudo.

$ node -v
v0.10.23
$ sudo node -v
v0.11.8-pre

This v0.11.8-pre caused me some problems, so I definitely don't want to use it, but I can't change it for root.

$ sudo nvm use v0.10.23
sudo: nvm: command not found

I've tried to install nvm from root user, but got error "NVM already installed", but still nvm not found when running from sudo. What is my problem?

Vitalii Korsakov
  • 45,737
  • 20
  • 72
  • 90

14 Answers14

301

My solution is to create symbolic links from the versions of node and npm I'm using to /usr/local/bin:

sudo ln -s "$NVM_DIR/versions/node/$(nvm version)/bin/node" "/usr/local/bin/node"
sudo ln -s "$NVM_DIR/versions/node/$(nvm version)/bin/npm" "/usr/local/bin/npm"

This makes npm and node available to all users.

SimpleJ
  • 13,812
  • 13
  • 53
  • 93
  • 1
    Great solution. just add " at the end of second line...(I could not edit this myself for some reason) – Rayee Roded Apr 24 '17 at 21:46
  • 1
    Great, this is by far the best solution. This way , root will always use the same npm / node version you are using on the nvm user, thanks! – luiscvalmeida Jul 27 '17 at 15:13
  • 7
    Great solution, but if you change the version of node you're using, you'll have to re-run the above commands. – door_number_three Apr 29 '18 at 20:39
  • 6
    I use `npx` quite often. So I added it as well: `sudo ln -s "$NVM_DIR/versions/node/$(nvm version)/bin/npx" "/usr/local/bin/npx"` – thomas Dec 18 '18 at 08:30
  • @SimpleJ how would you do the same for `babel-node` – user566245 Feb 22 '19 at 20:31
  • @user566245 I think the comment above yours should work for `babel-node` as well. It's just a matter of creating a symbolic link from the binary you're trying to use as `sudo` to a directory in the sudo user's PATH. – SimpleJ Feb 22 '19 at 22:44
  • I used this, but replaced the path with the which command, ex. >sudo ln -s `which npm` /usr/local/bin >sudo ln -s `which node` /usr/local/bin – Chris Jul 14 '20 at 12:12
  • I was having trouble with NVM on Windows with WSL2 and this solution worked. – Cleanshooter Jul 21 '20 at 20:20
  • In my case, it didn't work until I added the symlink in the `/usr/bin/` directory instead of `/user/loca/bin/` – Sebastian Kaczmarek Mar 01 '21 at 18:34
  • This is the answer to all of the endless questions about sudo and npm. Should be the top answer on Stack Overflow on the topic – PaulIsLoud Apr 06 '21 at 12:44
  • This was helpful for most of my node issues but wanted to share that I still had issues with this solution on a Raspberry Pi when trying to run PM2 commands as root with the symlinked node and npm solution... Not sure if anyone also ran into this but I ended up just installing the latest Node version manually in root without NVM. – jshaw3 Jul 01 '21 at 18:07
  • Does not help. Installed global packages are not available ( installation is done under sudo ) – Kos Sep 21 '21 at 08:43
  • This helped me - Here was my situation: I logged in as a user who is in the root group, installed nvm, the version of node I needed and tried to `sudo node` a file, but it gave me `sudo: node: command not found`. I did the above and it works like a charm now. I did NOT install a global version of node anywhere. It all resides in the user's nvm folder – ntgCleaner Dec 07 '21 at 21:36
266

The below list of commands (source: digitalocean) seems to fix the problem

WARNING!!!! In some circumstances, these commands can break your system! Make sure you know what do these command do!!! related

n=$(which node); \
n=${n%/bin/node}; \
chmod -R 755 $n/bin/*; \
sudo cp -r $n/{bin,lib,share} /usr/local

The above command is a bit complicated, but all it's doing is copying whatever version of node you have active via nvm into the /usr/local/ directory (where user installed global files should live on a linux VPS) and setting the permissions so that all users can access them.

starball
  • 20,030
  • 7
  • 43
  • 238
Venkat Selvan
  • 3,116
  • 1
  • 15
  • 12
  • 8
    Thank you! This saved me a lot of time – Quinton Pike Feb 15 '16 at 12:55
  • 4
    Perfect! Thank you so much. – Jean-Baptiste Louazel Apr 07 '16 at 15:52
  • 2
    Awesome! Last night I ruined my entire RasPi 3 system by desperately changing permissions for npm all over the place, today I spent 3h looking for the best solution to install node/npm globally without the need of sudo for each npm call. Your solution went well with this post https://www.losant.com/blog/how-to-install-nodejs-on-raspberry-pi – bosch Sep 25 '16 at 14:21
  • 3
    This sounds like a great option, but I keep getting these errors : `chmod: cannot operate on dangling symlink ‘/home/ec2-user/.nvm/versions/node/v7.1.0/bin/node-debug’ chmod: cannot operate on dangling symlink ‘/home/ec2-user/.nvm/versions/node/v7.1.0/bin/node-inspector’` – trex005 Nov 14 '16 at 20:23
  • Thanks it works! why do they have to make things so complicated?! – Rayee Roded Mar 27 '17 at 23:25
  • 1
    @RLaaa because it's node. By the way it works, but use with caution, in your user console, not in your root console, and you SHOULD test it be echoing $n before copying in your usr/local/bin – pdem Nov 16 '17 at 15:14
  • Helped me alot, I'm using Linode VPS and I had a problem with nvm installed as root, but not accessible for another users. This solves it, thanks. – Milen Radkov Jun 11 '18 at 14:10
  • Thank you & Love You ;) – Bilal Ahmed Yaseen Dec 19 '18 at 10:13
  • @pdem speaking from personal and recent experience, **YES TO THIS** – Sandy Gifford Jan 28 '19 at 19:18
  • I believe this will copy the current version of node that nvm has, but I guess your system version will then be stuck at whatever version nvm is currently running when you runt his command. Just a heads up. Also could be better to use a symlink here instead of duplicating files. – CTS_AE Feb 09 '19 at 08:24
  • this solution although appears to work, but defeats the purpose of NVM. with nvm we are changing what directory is in the part depending on which node version you have loaded. this command will just copy whatever directory was loaded at that time – user566245 Feb 22 '19 at 20:20
  • THANKS **FOR LINODE VPS.** – Jasper Martin Feb 27 '19 at 13:59
  • 3
    ` sudo su` `sudo: /usr/bin/sudo must be owned by uid 0 and have the setuid bit set` oh come on – tryingHard Apr 19 '19 at 14:42
  • 2
    After running this got the `sudo: /usr/local/bin/sudo must be owned by uid 0 and have the setuid bit set` as well. **LOOKS LIKE IT WILL REQUIRE A SERVER REBUILD!** – joe Mar 12 '20 at 16:46
  • Perfect! Thanks. – awmidas Oct 26 '20 at 13:07
  • 1
    PLEASE add a test for empty $n. Just bricked my entire system by not checking that first :P – Bix Jun 28 '21 at 19:49
28

The fundamental reason is because nvm is not a real program. It's a bash function that gets loaded in the user's .profile, .bashrc, or ... So sudo doesn't automatically pick it up from the $PATH like most other programs.

An alternative node version manager is n: https://github.com/tj/n . That is a real program, so sudo will pick it up via the $PATH without any hacks (as long as sudo has /usr/local/bin in its $PATH).

sudo npm install -g n  # install 'n' globally
which n                # should be /usr/local/bin/n

sudo n lts             # need sudo to switch node versions
node --version         # v6.10.0
sudo node --version    # v6.10.0
wisbucky
  • 33,218
  • 10
  • 150
  • 101
  • 2
    Perfect. Thanks "nvm is not a problem, but a bash function" :) – another May 02 '18 at 21:20
  • Haha, just realized about my misspelling "problem" instead of "program" ;). – another May 02 '18 at 21:29
  • For mw `which npm` gives `/home/asc/.nvm/versions/node/v16.17.0/bin/npm` and doing `sudo npm install -g n` followed by `which n` gives `/home/asc/.nvm/versions/node/v16.17.0/bin/n`. – Rnj Sep 17 '22 at 13:17
20

Your problem is, that nvm is not in the path when you use sudo.

So type

$ which nvm

and the result will be something like

/home/abc/mynvm/nvm

Try again now with sudo:

sudo /home/abc/mynvm/nvm use v0.10.23

I assume you then run into the issue that the root user can't find the 0.10.13-version, but lets see the next error message...

CFrei
  • 3,552
  • 1
  • 15
  • 29
  • 66
    `which nvm` outputs nothing – Vitalii Korsakov Jan 29 '14 at 10:13
  • try as root `which nvm` and then go with `sudo /nvm use v0.10.23`. What happens now? (By the way - this is not a node or any programming language issue. That is something with your linux machine configuration...) – CFrei Jan 29 '14 at 13:32
  • 8
    it outputs nothing for root as well – Vitalii Korsakov Jan 29 '14 at 15:38
  • Hmmm... "locate nvm"? How did you produce this 'already installed' message? – CFrei Jan 30 '14 at 07:31
  • Look at the source of this script: It says `NVM_DIR="$HOME/.nvm"; ... if [ -d "$NVM_DIR" ]; then echo "=> NVM is already installed in $NVM_DIR, trying to update"`. With `sudo` you use your local home dir and not root home dir. Install as real root user and it should work. – CFrei Jan 30 '14 at 16:37
  • 4
    Problem is that I never log in as root. Why should I? If I need any root access I always use `sudo`. Yes, I can log in as root and install nvm, but in future I couldn't run `sudo nvm use v0.10.25`. So I couldn't use `sudo node` from user as well. – Vitalii Korsakov Jan 30 '14 at 22:25
  • Then set the appropriate env variables by hand. Or do `sudo bash`. The issue you have is about wrongly set env variables due to different handling of `sudo` and `login`. – CFrei Jan 31 '14 at 09:18
  • 5
    `which nvm` doesn't ever work, does it? `nvm` isn't an executable, it's a shell function. https://github.com/creationix/nvm/issues/540 – Matt May 03 '17 at 21:15
  • 4
    I recently asked a similar question about `which nvm` here: https://stackoverflow.com/questions/49156104/what-is-the-equivalent-to-which-for-commands-that-dont-refer-to-scripts-or-ex Use `type nvm` to reveal its definition. As Matt said, it's a shell function. – Martin Braun Mar 07 '18 at 16:11
  • 1
    From [nvm documentation](https://github.com/nvm-sh/nvm#verify-installation); "Please note that which nvm will not work, since nvm is a sourced shell function, not an executable binary." So use ```shell command -v nvm ``` – ozanmuyes Sep 04 '21 at 01:18
  • echo $NVM_DIR outputs where nvm resides for me it was /home/USER_NAME/.nvm – Safeer Raees Feb 24 '23 at 14:11
19

According to README

When using nvm you do not need sudo to globally install a module with npm -g, so instead of doing sudo npm install -g grunt, do instead npm install -g grunt

Need sudo npm?

In my case, I need to sudo npm run start which needs the access to some file requiring root access. According to this issue,

You don't use sudo. You should instead chmod/chown the file so that the user that has nvm has access to the file;.

In sum

The maintainer of nvm strongly believe we don't need to sudo :P

lzl124631x
  • 4,485
  • 2
  • 30
  • 49
7

I had your problem too. Finally I have worked around it. Here is my solution:

  1. Uninstall nvm and nodejs. Here are some helpful links: Uninstallation of nvm. If you installed nodejs using apt-get, you can uninstall it with the command apt-get purge nodejs.
  2. Install a global nvm. See this page : nvm global. As it says, "Standard nvm has known difficulties working in multi-user or rooted environments."

After restarting your terminal, you can run the command sudo nvm ls.

MiniGod
  • 3,683
  • 1
  • 26
  • 27
Qianyue
  • 1,767
  • 19
  • 24
  • 2
    This branch is 12 commits ahead, 1123 commits behind creationix:master. taken straight from the xtuple repo for nvm – MrMesees Sep 08 '16 at 08:42
7
$ sudo bash -ic "nvm use stable; npm -v"
Now using node v6.3.1 (npm v3.10.3)
3.10.3
pmontrasio
  • 541
  • 6
  • 10
6

By extending @SimpleJ solution I have created a useful bash script that could be used to link all binaries from actual nvm bin dir to /usr/local/bin:

#!/bin/bash
. ~/.nvm/nvm.sh

DIR=$NVM_DIR/versions/node/$(nvm version)/bin/*
DEST=/usr/local/bin

for filename in $DIR; do
    filename=$(basename $filename)
    DEST_FILE=$DEST/$filename
    echo "Copying $filename to $DEST_FILE"
    sudo ln -sf "$NVM_DIR/versions/node/$(nvm version)/bin/$filename" "$DEST_FILE"
done
robertsLando
  • 189
  • 1
  • 4
4

I have tried the same on my machine where I have nvm as well and I have a slighlty different response:

$ sudo node --version                                                                                                                                                                    
sudo: node: command not found

My guess is that you have installed node 0.11 outside of nvm. (Via package manager or even from source)

Therefore, running node via sudo would pick up this standalone node instead.

Does that make sense or am I mistaken?

Aurélien Thieriot
  • 5,853
  • 2
  • 24
  • 25
  • Yes, you are right. I've installed *node* and then *nvm*. But everything works OK for normal user and does not work for the root. – Vitalii Korsakov Jan 19 '14 at 16:08
  • 1
    Oh alright. Then, I think that nvm is not meant to be runned as root. In fact I am pretty that running in user land is a wanted feature. However, this might help you: https://github.com/creationix/nvm/issues/5 – Aurélien Thieriot Jan 19 '14 at 16:40
  • This guy apparently made a special nvm that run in sudo mode: https://github.com/xtuple/nvm. Unfortunately only in sudo mode. I don't know if it's acceptable – Aurélien Thieriot Jan 22 '14 at 09:40
0

The easiest solution to this will likely be to just hit the nvm.sh executable wherever it is.

sudo /home/ubuntu/.nvm/nvm.sh install node

This works fine for me (assuming that's the install path).

The full install procedure would look like

curl -o- https://raw.githubusercontent.com/creationix/nvm/v0.33.0/install.sh | bash
export NVM_DIR="/home/ubuntu/.nvm"

[ -s "$NVM_DIR/nvm.sh" ] && \. "$NVM_DIR/nvm.sh"

And then you can run the command above to hit the newly installed nvm.sh

0

I wanted to just install latest node-js from NVM API, without going for additional packages-purged versions. So I was looking to SUDO nvm install-latest-npm. Mb this will work for you - it definetely worked for me without installing/removing any apts. (Obviously change YOUR_USER_DIRECTORY for something suitable on ur system)

sudo /home/YOUR_USER_DIRECTORY/.nvm/nvm.sh | nvm install-latest-npm 
EakzIT
  • 602
  • 5
  • 8
0

I had installed nvm and node as an unprivileged user.

To use these as sudo, I added this to the superuser's .bashrc file:

$ sudo bash -c 'echo $HOME/.bashrc'
/root/.bashrc

Contents to add to /root/.bashrc (replace <your-user>):

# Lazy load NVM/NPM/Node
lazynvm() {
  unset -f nvm node npm
  export NVM_DIR=/home/<your-user>/.nvm
  [ -s "$NVM_DIR/nvm.sh" ] && . "$NVM_DIR/nvm.sh"  # This loads nvm
}

nvm() {
  lazynvm
  nvm $@
}

node() {
  lazynvm
  node $@
}

npm() {
  lazynvm
  npm $@
}
Charlie
  • 2,876
  • 19
  • 26
0

The simplest approach would be by making PATH variable to include your /bin location of your NVM_DIR. Here is the example:

export NVM_DIR="$HOME/.nvm"
  [ -s "/opt/homebrew/opt/nvm/nvm.sh" ] && \. "/opt/homebrew/opt/nvm/nvm.sh"  # This loads nvm
  [ -s "/opt/homebrew/opt/nvm/etc/bash_completion.d/nvm" ] && \. "/opt/homebrew/opt/nvm/etc/bash_completion.d/nvm"  # This loads nvm bash_completion

Add this line to make PATH variable contains your binary of Node from NVM

export PATH="$NVM_DIR/versions/node/$(nvm version)/bin:$PATH"

Hope it helps.

azwar_akbar
  • 1,451
  • 18
  • 27
-3

Install nvm globally with
wget -qO- https://raw.githubusercontent.com/creationix/nvm/v0.32.1/install.sh | sudo bash

Ricky Sahu
  • 23,455
  • 4
  • 42
  • 32
  • 1
    creationix authors nvm, i'd be very careful about this third-party nvm... – MrMesees Sep 08 '16 at 08:39
  • 4
    This branch is 12 commits ahead, 1123 commits behind creationix:master. This is a problem, please remove the link – MrMesees Sep 08 '16 at 08:41
  • 12
    This answer makes my eyes bleed. You just **shouldn't** download anything and run it in a sudo bash, wtf – CharlyDelta Nov 27 '16 at 16:31
  • 1
    Actually, the wget command these days ends in `| bash`, no sudo anywhere: [nvm-sh/nvm: Node Version Manager](https://github.com/nvm-sh/nvm#installation-and-update) – Elise van Looij Aug 19 '19 at 13:25