You might not need `lib` in `tsconfig.json`
TypeScript has one of the most complex configuration schemas in the JavaScript ecosystem, beaten only by bundlers like Webpack. At the time of writing, there are 105 separate options in the TypeScript config schema!
Given this size and complexity, it is not surprising that people make mistakes in their tsconfig.json. It helps that the file allows comments in the JSON – when building your own tsconfig.json, I highly recommend documenting your choices with comments. Also, when copying a boilerplate tsconfig.json, I recommend taking a few minutes to find the docs for each preconfigured option and make sure you understand what it’s doing and whether you actually need or want it. Understanding what your code is actually doing is the first step in building maintainable software.
lib and target
One of the most common mistakes I see is with the target and lib options. It is extremely common to find lib declared in tsconfig.json, but it is very rarely needed, especially for browser-based projects. As the docs themselves explain:
Changing
targetalso changes the default value oflib. You may “mix and match”targetandlibsettings as desired, but you could just settargetfor convenience.
The problem
If you’ve ever seen a tsconfig.json with something like the following in it, then you’ll know why it causes confusion and uncertainty:
{ "target": "es5", "lib": ["dom", "es2016", "es2017.object"] }
This is from a real tsconfig.json I found in use in a large company. Why is it targetting es5, but then including the es2016 library? What is es2017.object? Does anyone really know?
The transpiling step for this project used Babel, and @babel/preset-env, so there was absolutely no reason to limit the TS target to es5. In fact, it should have targetted es2020, because that matched the version of Node being used and the latest version of Babel can handle everything in es2020.
The solution
So how do you choose what options to set? A good set of principles to follow are:
You probably don’t need
libat all. If you’re writing a pure Node project, you may want to remove thedomlibrary by setting lib to match yourtarget, e.g.:"lib": ["es2020"], but otherwise, just leave it out until you find you actually need to control this.Choosing your
targetis actually quite simple, although it requires answering a question that we might not already know the answer to: What ES version are you using in your development environment? In most cases, this will match the Node version you are using, and you can find the ES version that matches your Node version by checking this table: node.green. Find your Node version along the top, then scroll down until red boxes start appearing in that column. The last section that has all green boxes, is your ES version.
Every line of code is tech debt, so by removing config you don’t actually need (and might even be doing you harm), you’re reducing tech debt and making you project easier to maintain.