Maintaining Code Quality with Husky and lint-staged
Keeping your codebase clean and consistent is vital, especially when working on large projects or in a team setting. While tools like linters and formatters help maintain code quality, ensuring these tools are run consistently can be challenging. That’s where Husky
and lint-staged
come into play!
In this post, I’ll introduce you to Husky
and lint-staged
, explain how they work together, and walk you through setting them up to automatically maintain your code quality.
What is Husky?
Husky
is a tool that allows you to easily manage Git hooks in your project. Git hooks are scripts that run at various points in the Git workflow, like before a commit or push. With Husky
, you can automatically run scripts or commands before certain Git actions. This is incredibly useful for enforcing standards, such as running linters or tests before committing code.
What is lint-staged?
lint-staged
is a tool that works alongside Husky
to run scripts on staged files in Git. It allows you to define specific linting or formatting commands that will only run on the files you're about to commit, rather than your entire codebase. This makes it faster and ensures that only the relevant files are checked.
Why Use Husky and lint-staged Together?
Combining Husky
and lint-staged
ensures that:
Code quality checks (like linting and formatting) run automatically before every commit.
Only the files being committed are checked, reducing the time and overhead of these operations.
You enforce consistent code standards across your entire team without relying on manual processes.
Setting Up Husky and lint-staged
Let's walk through setting up Husky
and lint-staged
in a JavaScript/TypeScript project.
Step 1: Install Dependencies
First, add Husky
and lint-staged
to your project:
npm install husky lint-staged --save-dev
If you're using Yarn:
yarn add husky lint-staged --dev
Step 2: Initialize Husky
To initialize Husky
, use the following command:
npx husky install
This command will create a .husky/
directory in your project, which will store your Git hooks.
To automatically set up Husky in your project, add this command to the scripts
section of your package.json
:
"scripts": {
"prepare": "husky install"
}
This ensures Husky
is installed every time you run npm install
or yarn install
.
Step 3: Add a Pre-commit Hook
Now, let’s create a pre-commit hook that will run lint-staged
. You can add a hook using the command:
npx husky add .husky/pre-commit "npx lint-staged"
This creates a pre-commit hook that triggers lint-staged
every time you try to commit changes.
Step 4: Configure lint-staged
In your package.json
, add a lint-staged
configuration. This is where you specify the commands to run on the staged files:
"lint-staged": {
"*.js": [
"eslint --fix",
"prettier --write"
],
"*.ts": [
"eslint --fix",
"prettier --write"
],
"*.{js,ts,json,css,md}": "prettier --write"
}
In this configuration:
*.js
and*.ts
files are linted with ESLint (eslint --fix
) and formatted with Prettier (prettier --write
).Any JavaScript, TypeScript, JSON, CSS, or Markdown files (
*.{js,ts,json,css,md}
) are formatted using Prettier.
Step 5: Testing Your Setup
Now, make some changes to a file and attempt to commit it. The pre-commit hook set up by Husky
will automatically run lint-staged
, which, in turn, will run ESLint and Prettier on the staged files.
If there are linting or formatting issues, they will be fixed automatically before the commit is finalized. If the issues can't be fixed automatically, the commit will fail, allowing you to address them manually.
The Benefits of Using Husky and lint-staged
Automated Code Quality Checks: By running linters and formatters automatically before each commit, you ensure that all code in the repository adheres to your standards.
Time-saving:
lint-staged
only processes files that are staged for commit, so you don't waste time linting or formatting the entire codebase on every commit.Consistency: Whether you work solo or in a team, this setup ensures consistent code style across your project. This reduces bugs and makes your code easier to read and maintain.
Prevent Bad Commits: By running quality checks at the commit stage, you prevent issues from entering your codebase, reducing the chances of problems later in the development process.
Bonus: Using Husky for Other Git Hooks
While this post focuses on using Husky
for pre-commit hooks with lint-staged
, you can also use Husky
to run scripts at other stages of the Git workflow, like:
pre-push: Run tests before pushing code to a remote repository.
commit-msg: Enforce commit message conventions.
Here's an example of a pre-push hook that runs tests:
npx husky add .husky/pre-push "npm test"
Conclusion
Setting up Husky
and lint-staged
is a simple yet powerful way to automate code quality checks in your project. By integrating these tools into your Git workflow, you enforce consistent coding standards across your team and ensure that only high-quality code enters your codebase.
Give this setup a try in your next project, and you'll find that maintaining code quality becomes much easier and more reliable!
Subscribe to my newsletter
Read articles from Frank Lam directly inside your inbox. Subscribe to the newsletter, and don't miss out.
Written by