npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2024 – Pkg Stats / Ryan Hefner

precise-commits

v1.0.2

Published

precise-commits

Downloads

46,571

Readme

Why precise-commits?

🔎 It is simply the most exact and least disruptive way to add consistent code formatting (by Prettier) to an existing codebase.

✨ You only reformat the exact code you have modified anyway as part of your normal development!

| Tool | Staged files | Existing commits | PR Build | Arbitrary commands | Precision | | ------------------- | ------------ | ---------------- | -------- | ------------------ | ------------------------------- | | precise-commits | ✅ | ✅ | ✅ | ❌ | Individual character ranges | | lint-staged | ✅ | ❌ | ❌ | ✅ | Entire File | | pretty-quick | ✅ | ❌ | ❌ | ❌ | Entire File |

Background

Implementing a new code-style in an existing codebase can be really tricky.

Prettier is an amazing automated code formatting tool, but that does not mean that introducing it into an existing codebase is trivial.

Regardless of how consistent the existing code-style might be, introducing Prettier will result in larger diffs, which:

  1. Increases the complexity and review time burden of PRs on senior team members.
  2. Potentially increases the amount of time it takes to complete a PR in the first place.
  3. Can block concurrent work on the same codebase and/or result in nasty merge conflicts with outstanding feature branches.

Other tools, such as lint-staged, made an excellent first step towards mitigating the scope of the impact of the points above, by only running linters and formatters on files which have changed.

This is great for small codebases, in which the authors do not mind much that they are polluting the git history of the files they are touching, but it is not enough.

In large and enterprise codebases (particularly those organized as monorepos), the git history of each file is really important.

If I make a change on line 10 of a 4000 line file, I shouldn't be forced to reformat all 4000s lines (thus making me the last git user to update all of them) as part of my PR.

I should just need to reformat line 10.

This is where precise-commits comes in!

Our ideal end-goal...

  1. All developers on our team develop using consistent, automated formatting as they write their code. e.g. Running an IDE-based plugin, such as "vscode-prettier" with "format on save" enabled.

  2. Each time they commit, a precommit hook is triggered to ensure that the staged code is formatted consistently.

  3. Each time a Pull Request opened on our remote repo, a build is triggered on a CI server, during which the formatting is checked to ensure that all the files touched for that PR were formatted consistently.

How precise-commits helps us get there...

  1. All developers on our team write their code as they always have.

  2. Each time they commit, a precommit hook is triggered which will run precise-commits on the code and ensure that the exact code they already modified is formatted consistently. Any untouched existing code will not be mutated.

  3. Each time a Pull Request opened on our remote repo, a build is triggered on a CI server, during which precise-commits runs to ensure that all the committed lines of code for that PR was formatted consistently.

...and after enough time has passed, our codebase will be formatted consistently, despite us never having to disrupt our feature-building momentum!

How it works

Through analyzing your staged files (or any files modified between two given commit SHAs) precise-commits will work out exactly what lines and characters within those files have actually been changed or added.

It then uses this information to run Prettier in a very focused way, allowing it to only reformat what is relevant for your current work, and allowing you to keep your PRs small and explicit!

Installation

precise-commits expects prettier to be available as a peerDependency, so you will need to install this yourself as a devDependency of your project.

npm install --save-dev prettier precise-commits

Usage

It is intended that you will run precise-commits as a CLI, and it will automatically pick up on any of the standard Prettier configuration files you may have in your project, including .prettierignore files.

1. Running it manually

  1. Add an npm script to your package.json, such as:
{
  //...
  "scripts": {
    "precise-commits": "precise-commits"
  }
  //...
}
  1. Execute the npm script, e.g. for the one above run:
npm run precise-commits

2. "Precommit" Hook

The recommended way to run precise-commits is as a "precommit" hook.

A great tool for setting up the hook is husky. You can install and run it as follows:

npm install --save-dev husky

Update the "scripts" section of your package.json:

{
  //...
  "scripts": {
    "precise-commits": "precise-commits",
    "precommit": "npm run precise-commits"
  }
  //...
}

3. As part of a PR build

When running a build for your PR, you can run precise-commits to ensure that the author's changes are all formatted consistently.

The key things you need to configure are:

  1. The --check-only flag for precise-commits so that it will error out if it finds any inconsistent formatting
  2. The --head and --base flags so that precise-commits knows what commits it should consider when resolving modified files. Most CI servers will have environment variables you can use to resolve these.

For example, if your PR is building on Travis, your config might look like this:

.travis.yml

# ... Other config options here ...
install:
  - yarn install
script:
  - 'if [ "$TRAVIS_PULL_REQUEST" != "false" ]; then precise-commits --whitelist="src/**/*.ts" --check-only --head=$TRAVIS_PULL_REQUEST_SHA --base=$(git merge-base HEAD $TRAVIS_BRANCH); fi'
  - yarn test
  - yarn e2e
# ... Other config options here ...

CLI Configuration Options

As was hinted at above, the precise-commits CLI supports a few different configuration options:

  • --whitelist: [String, Default: "*"]
    • Whitelist is a glob pattern (the glob syntax from the glob module is used).
    • It is used to inform what files are considered when resolving modified files (by default all are considered).
    • Don't forget the quotes around the globs! The quotes make sure that precise-commits expands the globs rather than your shell.
  • --formatter: [String, Default: "prettier"]
    • Currently only prettier is supported
    • If you are interested in adding support for a different formatter, all you need to do is provide an object which implements this interface.
  • --check-only: [Boolean, Default: false]
    • Only check the code formatting is consistent with the resolved config
  • --base: [String, NO DEFAULT]
    • Base commit SHA to be used in conjunction with the --head flag
  • --head: [String, CONDITIONAL DEFAULT]
    • Later commit SHA (e.g. the HEAD of a PR branch) to be used in conjunction with the --base flag
    • NOTE on conditional default: If no value is provided for --head, but a value is given for --base, it will default to checking "HEAD"