10

How to install npm package from a python script?

When I use subprocess.Popen(["node", "app.js"]) it is OK.
When I use subprocess.Popen(["npm", "install", "open"]) it is throwing an error.

Sorry, but Google and DuckDuckGo are not my friends today(

The main problem — automatic local installation required packages for my small utility because global packages are not working in windows.

PS. I have to ask this question because I’m trying to develop a plugin for Sublime Text 2.

This is the error in Sublime python console:

Reloading plugin …\stsync.py
Traceback (most recent call last):
  File ".\sublime_plugin.py", line 103, in create_application_commands
    cmds.append(class_())
  File ".\stsync.py", line 16, in __init__
  File ".\subprocess.py", line 633, in __init__
  File ".\subprocess.py", line 842, in _execute_child
WindowsError: [Error 2] 

line 16: subprocess.Popen(["node", "npm", "install", "open"])


If I change line 16 to subprocess.Popen(["node", "npm", "install", "open"]) then the python script will successfully invoke the nodejs terminal, but then it will fail with error:
cannot find npm module
nodejs error

Vladimir Starkov
  • 19,264
  • 8
  • 60
  • 114

2 Answers2

4

set the shell argument to True

subprocess.Popen(["node", "npm", "install", "open"], shell=True)
Evan Siroky
  • 9,040
  • 6
  • 54
  • 73
  • 1
    Is there any other option besides using shell=True? As per the documentation https://docs.python.org/2/library/subprocess.html#frequently-used-arguments, using shell=True is a security hazard and and its use is strongly discouraged. – SaurabhM Aug 09 '15 at 20:36
  • Hi there, this one doesn't seem to be working for me? It gave me some weird error – destroyer22719 Jul 16 '21 at 21:52
2

On Windows, many of the Node.js "binaries" are actually suffixed with the .cmd filename extension, which for whatever reason during the invocation through subprocess.Popen, it doesn't expand (even though PATHEXT might contain .cmd).

So for a proper solution (that does not use shell=True), try append .cmd to the Node.js binaries needed:

Python 3.5.2 (v3.5.2:4def2a2901a5, Jun 25 2016, 22:01:18) [MSC v.1900 32 bit (In
tel)] on win32
Type "help", "copyright", "credits" or "license" for more information.
>>> import subprocess
>>> subprocess.Popen(['npm.cmd', 'install'])
<subprocess.Popen object at 0x005E18B0>
>>> npm ERR! install Couldn't read dependencies

Of course it throws an error because I don't have a package.json in that directory. Try again using some other commonly used programs, such as webpack:

>>> subprocess.Popen(['webpack'])
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
...
FileNotFoundError: [WinError 2] The system cannot find the file specified

Oh right, add that .cmd:

>>> subprocess.Popen(['webpack.cmd'])
<subprocess.Popen object at 0x008A18B0>
>>> No configuration file found and no output filename configured via CLI option
metatoaster
  • 17,419
  • 5
  • 55
  • 66