-
Notifications
You must be signed in to change notification settings - Fork 84
Formatting
Formatting code is a job for computers. We can make the rules so exact, and have such confidence that we understand the language grammar, that the formatter is safe to automate.
Bazel has its own formatter, called Buildifier. Since there are fewer BUILD files in a typical project, we currently don't have a way to incrementally re-format only the changed code - we always re-format everything.
This will be documented on bazel.build - in the meantime check out the example:
- Add a devDependency on
@bazel/buildifier
- scripts in
package.json
https://github.com/angular/angular-bazel-example/blob/30bcbba7b2804721f2b2d0e7c0a4804280966edd/package.json#L58-L60 - CI setup to enforce it https://github.com/angular/angular-bazel-example/blob/30bcbba7b2804721f2b2d0e7c0a4804280966edd/.circleci/config.yml#L46-L53
The big advantage of machine-formatting is that it makes us more productive! Some of the productivity comes from skipping a few keystrokes to make the code look good, but the majority is from time saved interacting with your co-workers. When humans try to make an objective decision about something so subjective, we spiral into unproductive discussions during code reviews.
However, we want to avoid a massive disruptive re-format of the whole repository. Such a re-format is a big cost - you pollute your blame layer in version control so that it always takes an extra hop to a previous change to understand authorship. Plus, all the pending pull requests at the time of the change will need an ugly rebase. The same thing can happen later if you upgrade or re-configure the formatter.
While a formatter is nice for making the code uniform to read, in practice you read code from many different sources, or in different languages, and also the formatting choices may have changed over time, so we must accept non-uniformity. Really, uniformity isn't our objective. We just need our code formatted in some reasonable way, and we trust that it stays that way. If we give up the uniformity requirement, there's a big advantage: we can introduce or upgrade a formatter without messing up the version control history.
All of the above means two things: you should use a formatter, and we should be able to check that our developers are using the formatter without checking the entire codebase. That means the formatter should be incremental, at the granularity of changed regions (not whole files).
My project, Angular "ABC" (http://g.co/ng/abc) is all about scalability, so we want a formatting setup that works when our repository gets large. The Angular project takes about 90s to check the format of everything, which is too long for such a common developer task. An incremental formatter is great here too - checking the formatting of a change scales with the size of the change - these rarely increase as quickly as a big repository.
To be incremental, the formatter must work together with the version control system, finding the lines changed by the commit and then formatting only regions of the file.
I recommend checking out https://github.com/nrwl/precise-commits