sh: syntax error near unexpected token `}' - node.js

I feel like a real moron posting a syntax error question but I really don't know how to fix this one
I'm trying to setup a build process in my node package.json file with the following script
"scripts": {
"build": "NODE_ENV=production { echo '// mypkg-x.y.z'; browserify -r ./client/main.js:mypkg | uglifyjs -cm; } > dist/mypkg.min.js"
}
which runs the following in sh
NODE_ENV=production { echo '// mypkg-0.0.0'; browserify -r ./client/main.js:mypkg | uglifyjs -cm; } > dist/mypkg.min.js
sh error outupt
sh: -c: line 0: syntax error near unexpected token `}'
When I run the command in bash it works just fine, but nodejs uses sh :{
End Goal
I am browserifying some javascript code and I want to prefix the bundled output with the package's name/version
// mypkg-x.y.z
<bundle output here>

Add a semicolon after you set NODE_ENV:
"build": "NODE_ENV=production; { echo '// mypkg-x.y.z'; browserify -r ./client/main.js:mypkg | uglifyjs -cm; } > dist/mypkg.min.js"

#Ray's answer worked great, I just wanted to post an alternate solution to the same problem
// this works too !
{ echo '// mypkg-0.0.0'; NODE_ENV=production browserify -r ./client/main.js:mypkg | uglifyjs -cm; } > dist/mypkg.min.js
To highlight the difference, all I did was move the NODE_ENV=production bit to just before the browserify bit. In this case, no semicolon is needed.
This is actually a little specific to my use case too, as the environment variable is only needed for that part of the build process.

Related

Change terminal tab name when running a command on package.json

I have multiple apps that need to be run at the same time, but it's complicated keeping up with which one is which in the terminal. Is there a way that I can rename their respective tabs through the command on package.json?
The area with the scripts looks something like this right now:
{
...
"scripts": {
"app1:dev": "[SCRIPT_TO_NAME_TAB] && cd app1 && nodemon server",
"app2:dev": "[SCRIPT_TO_NAME_TAB] && cd app2 && nodemon server",
"app3:dev": "[SCRIPT_TO_NAME_TAB] && cd app3 && nodemon server",
}
...
}
Is there anything I can replace on [SCRIPT_TO_NAME_TAB] with so that the tab is properly named whenever I run each of these scripts on my package.json? Thanks!
Edit: To add more to this I have found other threads that suggest I use something like
echo -n -e "\033]0;MY TITLE\007"
Unfortunately, that is not working and I get an error on the package.json file. So anyone know what is going on there?
This is a case that I ended up lacking some escape slash. So for me to get it to work, in package.json scripts I did the following:
{
...
"scripts": {
"app1:dev": "echo -n -e \"\\033]0;MY TITLE\\007\" && cd app1 && nodemon server",
...
}
...
}

npm command doesn't update json

This command works fine:
json -I -f ./src/environments/build.json -e 'this.patch++'
I'm trying to create a custom build NPM command in my package.json file that runs this command before the actual build, but first I just tried to run the json command, just to see if it's working, but it doesn't :/
package.json
{
...
"scripts": {
...
"svrge-build-dev": "json -I -f ./src/environments/build.json -e 'this.patch++'",
...
}
then I get this output (which is exactly the same as when I run the JSON code by itself) which means that the command is definitely running
> web-client#1.0.0 svrge-build-dev D:\repos\test\web-client
> json -I -f ./src/environments/build.json -e 'this.patch++
json: updated "./src/environments/build.json" in-place //<- this is exactly the same'
However, the build.json file is not being updated
No errors in the terminal
any idea how I can get it to work? I can't seem to find anything regarding that.
I would appreciate any help, been scratching my head for hours
Tom
Re-stating what I said in the comment: try to replace the single quotes with double quotes:
{
// ...
"scripts": {
// ...
"svrge-build-dev": "json -I -f ./src/environments/build.json -e \"this.patch++\"",
// ...
}
What triggered that thought was this line in the output:
> json -I -f ./src/environments/build.json -e 'this.patch++
After doing some digging, I think it depends on the OS and/or command line interpreter. It shows the command that was run, but not with the finishing single quote.
After some searching, it appears that is indeed a bug: see this issue and this issue. You might want to give the maintainers a heads up about it: the last issue I've linked to, makes it seem like it's a Windows issue.

How do I conditionally output eslint results to a file using npm scripts?

I am trying to make a simple npm script to run eslint and check if it's in CI or not and output the results to a file if it is.
This works to output the results to the terminal:
"lint": "eslint src --cache --format $(if [ -z ${SOMEVAR} ]; then echo \"stylish\"; else echo \"checkstyle\"; fi)",
But I want to save them to a file if there is an ENV var present using > checkstyle.xml
Is there a way to tack this onto that command? I've tried several ways, but no luck getting the file to output.
Edit:
I was able to get this working by adding --color | tee checkstyle.xml which writes the xml file regardless of ENV var value and displays a colorized version to terminal. This is not ideal, but does work. Open to other ideas though.
I found this great chart that shows what combos of output you can use together to achieve this: https://askubuntu.com/a/731237/541276
Do you mean something like this?
if [ "$somevar" ]; then exec >checkstyle.xml; fi; eslint ...

Get stdout from NPM Script into a variable

I have this node script that parse a .YAML and output a field named version
node node/getAssetsVersion.js
=> "2.1.2"
I'm trying to get that stdout into a varible and use it in a NPM Script
This is what I'm trying to do in my package.json:
"scripts": {
"build": "cross-env VERSION=\"$(node node/getAssetsVersion.js)\" \"node-sass --include-path scss src/main.scss dist/$VERSION/main.css\""
}
Thanks!
Instead of this:
VERSION=\"$(node node/getAssetsVersion.js)\"
you may need to use:
VERSION=\"$(node node/getAssetsVersion.js | cut -d'\"' -f2)\"
if the output of your program is this as you wrote in the question:
=> "2.1.2"
If it's just this:
"2.1.2"
then the above will still work but you can use a simpler command:
VERSION=$(node node/getAssetsVersion.js)
with no quotes.
But in the later part the $VERSION will likely not get substituted as you expect.
Since you tagged you question with bash I would recommend writing a Bash script:
#!/bin/bash
VERSION=$(node node/getAssetsVersion.js | cut -d'\"' -f2)
node-sass --include-path scss src/main.scss dist/$VERSION/main.css
or:
#!/bin/bash
VERSION=$(node node/getAssetsVersion.js)
node-sass --include-path scss src/main.scss dist/$VERSION/main.css
depending on what is the output of getAssetsVersion.js and put this in package.json:
"scripts": {
"build": "bash your-bash-script-name"
}
I would avoid any quotes that are escaped more than once.

Colored logging in terminal with NPM run script

I'm trying to setup a project exclusively with NPM as a build system (no Gulp or Grunt) so I'm a bit of a beginner, but so far it's working pretty nicely except for this little road block.
The scripts section of my package.json looks something like that :
"scripts": {
"clean:task": "rimraf dist/*",
"clean:notify": "notify --t 'Cleaning done.' --m 'dist/ has been cleaned successfully.",
"clean": "npm run clean:task -s && npm run clean:notify -s",
"serve": "browser-sync start --p 'xxx.dev/app' --host 'xxx.dev' --port '3000' --open 'external' --f 'app'",
"styles:task": "node-sass --output-style nested -o app/assets/css app/assets/css",
"styles:notify": "notify --t 'Styles compilation' --m 'Styles have been compiled successfully'",
"styles:build": "npm run styles:task && npm run autoprefixer",
"imagemin": "imagemin app/assets/img dist/img -p",
"scripts:lint": "jshint --reporter=node_modules/jshint-stylish app/assets/js/scripts.js"
}
I have notifications to announce successful tasks, but ideally I'd like some nice colored messages directly in the terminal. I know this can be done with Gulp via colored logging but I can't fin any NPM package that has a CLI that would be able to do that.
Any ideas ? Is it even possible ?
Thanks for your help.
Individual scripts defined in package.json can output a message to Mac's Terminal in color by following a syntax that boils down to echo + ANSI color reference + some text although you can get more complicated than this, as well.
Step 1: Define your scripts
"scripts": {
"greeting": "echo \"\\033[32mHello World\"",
"notification": "echo \"\\033[33mThe Server Has Started\"",
"timestamp": "echo \"\\033[31m--------\";date \"+%H:%M:%S\n--------\n\" && echo \"\\033[00m\""
{
Step 2: Run your scripts
npm run greeting
npm run notification
npm run timestamp
Some things to note
Escaping is inherently a part of this. A comment by James Lim on StackOverflow mentions the use of -e which apparently ensures that echo honors escaping slashes. I found this was necessary when running the command directly in Terminal but unnecessary when firing it as part of npm run <script>.
The ANSI code that sets the color is made up of eight characters that always begin with a backslash, like this \033[32m. Also, notice that the text I am outputting in my scripts above begins immediately after the last character in the ANSI code– this is so the message will be flush left in the Terminal.
In the timestamp script above, the semicolon separates the echo and date commands but maintains the same color we set at the beginning. In fact, this color will affect everything defined in this script and, in my case, even changed the color of a message output by a separate script that immediately followed this one. For this reason, I included another echo that simply resets the color to the Terminal's default color (in this case, black).
For reference, I could have used && in place of the semicolon and achieved the same results. If you do not already know the difference between these two operators, see this post.

Resources