What does the TypeScript "lib" option really do?
Typescript does not have any built-in types all types come from a set of base definitions (located in the lib
folder in the typescript install directory). By default the target
defines which libs
are included. For example the docs state:
Note: If --lib is not specified a default list of librares are injected. The default libraries injected are:
► For
--target ES5: DOM,ES5,ScriptHost
► For
--target ES6: DOM,ES6,DOM.Iterable,ScriptHost
The basic idea is that while target is deals with language features (more specifically which language features need to be down compiled, ex: for-of, or arrow functions), the lib
option deals with what facilities the runtime environment has (ie. what built-in objects look like, what they are).
Ideally the default libs
for a given target
should be used. We may, however, have an environment which supports some of the runtime facilities but not the language features, or we may target runtime with a lower es
version and poly-fill some of the runtime facilities, which can be in general done for some things (ex: Promises).
Remember, TS never injects polyfills in your code. It's not its goal. Complementing the accepted anwer:
target
tells TS which ES specification you want the final/transpiled code to support. If you configure it as ES5
, TS will down compile the syntactic features to ES5, so any arrow functions () => {}
in your code will be transformed to function () {}
.
Whatever you choose for target
affects the default value of lib
which in turn tells TS what type definitions to include in your project. If you have "target": "es5"
, the default value of lib
will be ["dom", "es5", "ScriptHost"]
. It's assuming which functional features the browser will support at runtime. Adding things to lib
it's just to make TS happy - you still need to import the polyfill yourself in the project.
So in short: configure target
first, and if you need any extra polyfill in your project OR you know your browser(s) will support this little extra feature, lib
is how to make TS happy about it.
Example: You need to support IE11 but also you would like to use promises. IE11 supports ES5, but promises is an ES6 feature. You import a promises polyfill, but TS is still giving an error. Now you just need to tell TypeScript that your code will target ES5 and it's safe to use promises in the codebase:
"target": "es5",
"lib": ["dom", "es5", "ScriptHost", "es2015.promise"]