DRY way to change working directory for npm scripts - npm

I'm just trying out NPM as my build system for a small project and I'd like to ask if there is a clean and easy to maintain way to change the working directory for the build scripts. My first thought was something like
"scripts": {
"cd:workdir": "cd src/path/to/my/work/dir/",
"task:1": "npm run cd:workdir && command1",
"task:2": "npm run cd:workdir && command2",
[...]
}
But it seams command* is executed in a different process then npm run cd:workdir, so this doesn't work.
The only working way I found so far is:
"scripts": {
"task:1": "cd src/path/to/my/work/dir/ && command1",
"task:2": "cd src/path/to/my/work/dir/ && command2",
[...]
}
But there must be a better way to do this to keep it DRY and better maintainable. Thanks!

I think you can use child_process.exec to execute some commands from a javascript file:
// task.js
const { exec } = require('child_process');
exec('command', {
cwd: 'src/path/to/my/work/dir/'
}, (error, stdout, stderr) => {
// handle error, stderr...
console.log(stdout)
});
and execute that javascript file using node in npm script: "task:1": "node task.js"

Related

How to modify npm scripts in package.json for Windows [duplicate]

issue:
in script:
we want to check env. variable {dev/test/mock} and do following script run based on it.
if $mock is true the run script start-mock else go on reach real test server
scenario 1:
we added commands aggregated in package.json script section
e.g. : "test": "export NODE_ENV=dev; grunt", [on linux]
which is "test": "(SET NODE_ENV=dev) & (grunt)", [on win32]
scenario 2:
could be bat/sh script sitting in package and we called them out from package.json
scenario 3: (permanent solution)
not sure if its already available out there
something like
get arguments from script section: to give flexibility and freedom to end user.
e.g. : "test": "solution.env NODE_ENV=dev; solution grunt"
where we can have script to process (input with process.platform) out put depends on OS.
"start-pm2": "if \"%MOCK%\" == \"true\" ( npm run mock & pm2 start process.json --env test ) else ( pm2 start process.json )", [windows] for linux if.. fi
Use: run-script-os
For example:
// from pacakge.json
"scripts": {
// ...
"dist": "run-script-os",
"dist:win32": "tar -C dist -cvzf %npm_package_name%-%npm_package_version%.tgz .",
"dist:linux": "tar -C dist -cvzf $npm_package_name-$npm_package_version.tgz ."
},
Lets consider implementation of 3-th solution like e.g.
package.json
"scripts": {
"command" : "node bin/command.js"
}
bin/command.js
const spawn = require("child_process").spawn
const platform = require("os").platform()
const cmd = /^win/.test(platform)
? `${process.cwd()}\\bin\\command.bat`
: `${process.cwd()}/bin/command.sh`
spawn(cmd, [], { stdio: "inherit" }).on("exit", code => process.exit(code))
depends on environments script will execute command.bat or command.sh
You will need to implement solution 3.
You can use cross-env package that does it for you.

how to change "npm scripts" directory

"scripts": {
...
...
"puppeteer": "cd test/UI-tests/src && set BROWSER=chrome && mocha test.js"
}
I want to wrap all the commands in "puppeteer", so once I type npm run puppeteer, it can set the browser and run the test.js file.
The way I write it does not work.

How add variable npm run build in package.json

I have 6 projects in an Angular workspace and I have to build each. Instead of write six lines in my package.json for each projet, for example :
"build_a":" npm run build a"
"buiild_b": "npm run build b"
I would like to create only one line like this :
"build_app": "npm run build name="aaa""
How I can do it ?
you could rely on environment variables in order to discover such names.
however it depends on which operating system you're using on how to define env variables.
"scripts":{
"build:a":"cross-env NAME=a npm run build",
"build:b":"cross-env NAME=b npm run build",
"build:c":"cross-env NAME=c npm run build",
"build":"browserify src/main.js -o build.js"
}
You would end up with a script section more or less like this.
Finally I found the solution using a node.js script: build-subproject.js.
const { exec } = require('child_process');
const args = process.argv.slice(2).join(' ');
console.log(`RUNNING build with args: ${args}`);
exec(
`ng build ${args} && cd dist/${args} && npm pack `,
(error, stdout) => {
if (error) {
console.error(`exec error: ${error}`);
return;
}
console.info(`stdout: ${stdout}`);
}
);
In package.json,
"build-subproject": "node ./build-subproject.js",
Then run , npm run build-subproject my-project-name

Removing log statements in Create React App without ejecting

I use lots of console.log() statements while developing Apps (and I mean LOTS). How exactly can I remove them without "ejecting" from a
Create React App
What I considered but not sure how exactly to implement:
In my package.json:
"build": "react-scripts build && uglifyjs --compress drop_console build/static/js/main.xxxxx.js -o build/static/js/main.xxxxx.js
However How exactly can I know the hash suffix on the main.js file so I can call this command and save the output js file with same filename
Add this to index.js
if (process.env.NODE_ENV !== 'development') {
console.log = () => {}
}
Note that this will only suppress the messages, it will not strip them from your deployed code.
Note Nov 2020
Don't do this for library modules, it will disable console.log for the parent project.
Update Sept 2020
There is some movement on this issue on the CRA repo... go give it support/thumbs up here https://github.com/facebook/create-react-app/pull/9222
References:
How to quickly and conveniently disable all console.log statements in my code?
If you just want to suppress log output you could wrap console.log and use that instead
const log = (...msgs) => {
if (process.env.NODE_ENV === 'development') console.log(...msgs)
}
You can import / export this, but that sounds like a pain. Seems like a good thing to add to global
global.log = log
global.log('will only log in dev')
Do this in package.json scripts:
"build": "./scripts/build.sh"
and then in your project:
scripts/build.sh looks like:
#!/usr/bin/env bash
set -e;
cd "$(dirname $(dirname "$BASH_SOURCE"))" # cd to project root
react-scripts build
for f in build/static/js/*.js; do
uglifyjs --compress drop_console "$PWD/$f" -o "$PWD/$f"
done
You can try this combo of packages to override the config:
Note: from the document of react-app-rewired, this would break the the "guarantees" that CRA provides. So you should be careful before using it.
npm i -D customize-cra react-app-rewired babel-plugin-transform-remove-console
Modify your package.json, replace react-scripts to react-app-rewired except the reject. Once complete, your scripts should look like this:
"scripts": {
"start": "react-app-rewired start",
"build": "react-app-rewired build",
"test": "react-app-rewired test",
"eject": "react-scripts eject"
}
Then create a file under the root directory:
touch config-overrides.js
// config-overrides.js
const { override, addBabelPlugins } = require('customize-cra')
module.exports = override(
addBabelPlugins(
"transform-remove-console"
)
)
Finally, after running npm run build, all console.log gone.
I use this setup. I still need console log while in dev.
// config-overrides.js
const { override, addBabelPlugins } = require('customize-cra')
module.exports = override(
process.env.NODE_ENV !== 'development' && addBabelPlugins(
"transform-remove-console"
)
)

Add `jshint` worker into `scripts` for package.json

Dear stackoverflowers.
I have decided to include jshint into my project to helps me detect errors and potential problems in my JavaScript code. I have installed it at the project's root and I'm able to run next code from the console:
jshint --config .jshintrc ./app/
It returns me several notifications.
Then I've decided to create a special section inside my package.json scripts section. It looks like that:
"scripts": {
"jshint": "jshint --config .jshintrc ./app/"
}
And when I try to run
npm run jshint
It returns me an exception...
please check it out https://github.com/npm/npm/issues/6124, you can prevent this error if you set your script with following || true like in code snippet bellow
{
"scripts": {
"test": "jshint || true"
}
}
in this case your script will finish with exit code = 0, and npm will no throw an error