Run node module from powershell - node.js

Say that I have a folder with a node module installed inside. How can I, using powershell, run this module ? For example, I have a folder with webpack installed inside and I'd like to be able to do something like
node webpack
This does not work because it can't find the module. However, it works if I do:
node ".\node_module\webpack\bin\webpack.js"
However, I can't really use this because I'm working on a powershell script that allows the user to define a json file with actions. For example:
{
"type": "run-node",
"options": {
"module": "webpack",
"parameters": "--configFile=config/webpack.prod.js"
}
}
As the module to execute is dynamic, I don't know where it will be (except if all module are installed in ".\node_modules\module\bin\module.js" ?), so I can't launch it.

You can define a webpack script in your package.json:
"scripts": {
"webpack": "node \"./node_module/webpack/bin/webpack.js\""
}
Then you can use npm run webpack or yarn webpack to run it.

If you're trying to execute the command within the node.js script, use the __dirname variable.
__dirname (almost) always refers to the directory that contains the script.

Related

Passing CLI options to rollup via package.json

I am using this script in package.json
"scripts": {
"build": "rollup -c"
}
And would like to dynamically pass options to the rollup.config.js file, such as npm run build home, where 'home' is a variable that will build a particular bundle.
I manage to get to the rollup config file using "build": "rollup -c rollup.config.js" and I can access 'home' within an array by using
var argv = require('minimist')(process.argv.slice(2));
but still, as it was doing before without the addition in the package.json script, I get the error [!] Error: Could not resolve entry module (home). and no bundle gets created.
Using --home in the CLI hides it completely in the 16.17 version of node I'm using (managed fine with 14.x) for whatever reason.
Going in circles as ever with existing answers online. Thanks for the help!

How to run node.js cli with experimental-specifier-resolution=node?

Our team has built a small CLI used for maintenance. The package.json specifies a path for with the bin property, and everything works great; "bin": { "eddy": "./dist/src/cli/entry.js"}
Autocompletion is achived by using yargs#17.0.1. However we recently converted the project to use es6 modules, because of a migration to Sveltekit, i.e. the package.json now contains type: module. Because of this, the CLI now only works if we run with:
what works
node --experimental-specifier-resolution=node ./dist/src/cli/entry.js help
However, if we run this without the flag, we get an error "module not found":
Error [ERR_MODULE_NOT_FOUND]: Cannot find module...
So the question is
Can we somehow "always" add the experimental-specifier-resolution=node to the CLI - so we can continue to use the shorthand eddy, and utilize auto completion?
There are two probable solutions here.
Solution 1
Your entry.js file should start with a shebang like #!/usr/bin/env node. You cannot specify the flag directly here, however, if you could provide the absolute path to node directly in the shebang, you can specify the flag.
Assuming you have node installed in /usr/bin/node, you can write the shebang in entry.js like:
#!/usr/bin/node --experimental-specifier-resolution=node
(Use which node to find the absolute path)
However, this is not a very portable solution. You cannot always assume everyone has node installed in the same path. Also some may use nvm to manage versions and can have multiple version in different path. This is the reason why we use /usr/bin/env to find the required node installation in the first place. This leads to the second solution.
Solution 2
You can create a shell script that would intern call the cli entry point with the required flags. This shell script can be specified in the package.json bin section.
The shell script (entry.sh) should look like:
#!/usr/bin/env bash
/usr/bin/env node --experimental-specifier-resolution=node ./entry.js "$#"
Then, in your package.json, replace bin with:
"bin": { "eddy": "./dist/src/cli/entry.sh"}
So when you run eddy, it will run the entry.js using node with the required flag. The "$#" in the command will be replaced by any arguments that you pass to eddy.
So eddy help will translate to /usr/bin/env node --experimental-specifier-resolution=node ./entry.js help
Just add a script to your package.json:Assuming index.js is your entry point and package.json is in the same directory
{
"scripts": {
"start": "node --experimental-specifier-resolution=node index.js"
}
}
Then you can just run on your console:
npm start

pm2 cannot start express application

I wrote a simple Express application. It ran correctly with "npm start". The scripts in package.json is this:
"type": "module",
"scripts": {
"start": "src/bin/www.js"
}
But I couldn't execute it like this:
pm2 start ./src/bin/www.js
I checked pm2.log. It shown "had too many unstable restarts(16)".
Then ran it with pm2-dev:
pm2-dev start ./src/bin/www.js
Reported the error:
Error [ERR_REQUIRE_ESM]: Must use import to load ES Module:
Pm2 can't work well with import/export? The node version is 14.16.0.
First make sure if you have following two points:
Node version >= 14. It only works with latest version of node.
Make sure your package.json includes a line for "type": "module", Without this line node assumes you want to use Common JS modules rather than ESM.
If both are true and it's still not working then you might be victim of following github issue
https://github.com/Unitech/pm2/issues/4540
For now you can try running it with babel!

'standard' is not recognized as an internal or external command

I want to integrate some kind of code linting for node.js in webstorm so I installed standard to my node.js project using:
npm instal standard --save-dev
It was installed and listed in the "devDependencies" section of package.json but when I run the command:
standard
in the console I get
'standard' is not recognized as an internal or external command
if you want to use it locally you have to include it in you scripts first in package.json
"scripts": {
"standard": "standard",
"standard::fix": "standard --fix"
}
and use npm run standard to run it. or if you are using yarn type yarn standard
The scripts are in node_modules\.bin.
So, either:
Add this to PATH before running standard, e.g.:
set PATH=%PATH%;node_modules\.bin
Run it in using node_modules\.bin\standard
Use #tarek's approach using package.json: https://stackoverflow.com/a/49026837/122441
"scripts": {
"test": "standard middlewares/validations.js"
}
Add above lines in package.json.
Here middlewares/validations.js is the path of the file to check.
Run -> npm test
If this file have any error you will get.

local node js module not executing script

I am trying to create a simple node js plugin. Here is what I have done till now.
package.json
{
"name": "testcli",
"version": "0.0.1",
"description": "Test CLI Tool",
"main": "index.js",
"author": "BJ",
"license": "ISC",
"bin": {
"testx": "index.js"
}
}
Beside the package.json I have a file index.js that has a single line console.log('Hi!')
now when I install the package with npm install -g (from the same directory) and then run the command testx it gives me the following error
.../AppData/Roaming/npm/testx: line 1: /node_modules/testcli/index.js: No such file or directory
How can I solve this?
You need to add a shebang to tell the shell how to invoke this script.
Try adding #! /usr/bin/env node at the beginning of your script.
A lot of packages have one or more executable files that they'd like to install into the PATH. npm makes this pretty easy (in fact, it uses this feature to install the "npm" executable.)
To use this, supply a bin field in your package.json which is a map of command name to local file name. On install, npm will symlink that file into prefix/bin for global installs, or ./node_modules/.bin/ for local installs.
For example, myapp could have this:
{ "bin" : { "myapp" : "./cli.js" } }
So, when you install myapp, it'll create a symlink from the cli.js script to /usr/local/bin/myapp.
If you have a single executable, and its name should be the name of the package, then you can just supply it as a string. For example:
{ "name": "my-program"
, "version": "1.2.5"
, "bin": "./path/to/program" }
would be the same as this:
{ "name": "my-program"
, "version": "1.2.5"
, "bin" : { "my-program" : "./path/to/program" } }
Please make sure that your file(s) referenced in bin starts with #!/usr/bin/env node, otherwise the scripts are started without the node executable!

Resources