Compiler Options and Strictness
Know what tsc checks, what it emits and what it never does at runtime. Then know the handful of options that change type safety, module output and build behaviour, including the defaults that changed in TypeScript 6.0.
Key points
- 1
Types are erased: tsc adds no runtime checks, emits even on errors unless
noEmitOnErroris set, and never polyfills APIs. - 2
strict(on by default since TypeScript 6.0) bundles strictNullChecks, noImplicitAny, strictFunctionTypes, strictBindCallApply, strictPropertyInitialization, noImplicitThis, useUnknownInCatchVariables and alwaysStrict.noUncheckedIndexedAccessandexactOptionalPropertyTypesare separate opt-ins. - 3
targetcontrols emitted syntax;libcontrols which API types exist. Raisinglibwithout a polyfill only hides runtime crashes. - 4
Under
module: "nodenext", relative imports need the runtime extension (./b.js).pathsnever rewrites emitted imports. - 5
isolatedModules,verbatimModuleSyntaxanderasableSyntaxOnlymake tsc report code that single-file transpilers or Node's type stripping would get wrong. - 6
Project references need
compositeandtsc -b. Plaintsc -pchecks against whatever.d.tsfiles a referenced project last emitted. - 7
TypeScript 6.0 defaults
typesto[], enablesnoUncheckedSideEffectImports, tiesrootDirto the tsconfig folder, and deprecates baseUrl, node10 resolution, ES5 targets and outFile.
Common traps
excludedoes not keep a file out of the program if another file imports it.skipLibCheckalso skips your own hand-written.d.tsfiles.Deleting
dist/but keeping a.tsbuildinfostored elsewhere makes the next incremental build emit nothing.
Test yourself on Compiler Options and Strictness
Ten questions, with the answer and explanation after each one.