Using npm pre- and post- hooks

“A close-up of a person using a vintage typewriter.” by rawpixel on Unsplash

NPM scripts are incredibly useful, they make those hard-to-remember commands accessible just by naming the script:

npm run your_script_name

You can create them in your package.json like so:

{
"scripts": {
"your_script_name": "echo some_command_here"
}
}

However, there’s a useful feature available which you may not be aware of…

Pre and Post hooks!

Sometimes it’s useful to have one script run before or after another — for example; to delete some test logs before running the tests, and to run a linter afterwards.

In this case, you have two choices:

  1. Use && between the commands:
{
"scripts": {
"test": "rm -rf ./logs && mocha --recursive && jslint ."
}
}

As you can see, each individual command is pretty short and it’s already unclear what the npm script does. Moreover, if the script encounters an error it can be difficult to see which part of it failed.

2. Use pre- and post- hooks

{
"scripts": {
"pretest": "rm -rf ./logs",
"test": "mocha --recursive",
"posttest": "jslint ."
}
}

This makes the function of each script much clearer, and errors are a lot easier to debug as you can see exactly which script failed.

Although if you have a lot of scripts — each with their own pre- and post- hooks — then your package.json could end up looking very messy.

You can use pre- and post- hooks on all npm scripts, just prepend pre or post to the name of your script.

In conclusion, it’s down to you which method you prefer — and it might depend on the service, or even the individual script. Some commands might have no chance of failing and so don’t need to be separated, whereas others might be unimaginably long so need to be separated for clarity.

You can find out more information about pre- and post- hooks here.