Linting is the first step to ensure and enforce code consistency, best practices, and avoid silly errors.
ESLint is the gold standard of NodeJs code linter, easy to set up, and heavily configurable it can automatically analyze code and fix problems. It’s one thing to write a NodeJs application, and another being production-ready.
In this series we will explore how you can make your side project production-ready. The first step in this series is linting and pre-commit hooks. This is an opinionated post and we will be using
- ESLint
- Prettier
- Husky
Note, we will be using the Visual Studio Code editor (VSCode).
ESLint
ESLint is a static code analysis tool used for identifying problematic patterns found in a JavaScript code.
ESLint can be installed using the following command:
$ npm install eslint --save-dev
This command holds for local installation, you can install it globally too.
After a successful installation, the next step will be the configuration. For this either you can use a standalone .eslintrc or .eslintrc.json file or generate the config file using the following command:
If you have installed locally
$ ./node_modules/.bin/eslint --init
If you have installed it globally
$ eslint --init
Now you can configure rules like this
{ "rules": { "semi": ["error", "always"], "quotes": ["error", "double"] } }
The names “semi” and “‘quotes” are names of rules in ESLint.
The first value is the error level which can be one of these values:
- “Off” or 0, to turn off the rule.
- “warn” or 1, turn the rule on as a warning
- “error” or 2, turn the rule on as an error
We are already using VSCode along with prettier which has some nice defaults and is one of the best auto-formatter around, you need to have the formatOnSave option turned on in VSCode settings for it to work properly.
We are using Airbnb config for ESLint. Here is our eslintrc.json config
{ "env": { "browser": true, "commonjs": true, "es6": true }, "extends": ["airbnb-base"], "globals": { "Atomics": "readonly", "SharedArrayBuffer": "readonly" }, "parserOptions": { "ecmaVersion": 2018 }, "rules": { "arrow-parens": ["error", "as-needed"], "no-param-reassign": ["error", { "props": false }], "consistent-return": 0 } }
Prettier
Prettier is an opinionated code formatter. It enforces a consistent style by parsing your code and re-printing it with its own rules that take the maximum line length into account, wrapping code when necessary.
It’s an awesome VSCode plugin as it auto formats our code with a little headache and works great with Reactjs and well with NodeJs.
We have to make a separate file for prettier configs .prettierrc since there are some conflicting rules.
{ "singleQuote": true, "arrowParens": "avoid", "trailingComma": "all", "useTabs": false, "printWidth": 70 }
These configs will ensure that there are no conflicts between ESLint and prettier rules. For linting, you can use
$ eslint file1.js file2.js
or
$ eslint lib/**
Husky
The above-explained methods are one way of doing things, but it’s mundane to run the same command periodically. How about we set up some sort of checkpoint where the command runs automatically. We will use husky along with lint staged for achieving this.
Linting makes more sense before committing code. By doing this code style can be enforced.
Running linter on the whole codebase is slow and makes little sense, instead of running linter on files that are going to be committed makes more sense.
Setting up Husky
$ npm install --save-dev husky lint-staged
Next step will be husky config in package.json file
"husky": { "hooks": { "pre-commit": "lint-staged" } }, "lint-staged": { "*.{js,tsx}": [ "./node_modules/.bin/eslint --fix", "git add" ], "*.{js}": [ "./node_modules/.bin/prettier --write", "git add" ] }
This husky object is used to specify which hook to use, and lint-staged is to be run on it.
"./node_modules/.bin/eslint --fix",
This means that the linter will try to fix any errors it can fix automatically.
You are all set up, now every time you commit the code husky triggers pre-commit hook lint staged which ensures there are no errors in the files being committed.