TypeScript strict mode: tsconfig.json, strict flags, Bundler/NodeNext moduleResolution, verbatimModuleSyntax. Use when setting up TS or migrating to stricter type safety.
TypeScript strict mode: tsconfig.json, strict flags, Bundler/NodeNext moduleResolution, verbatimModuleSyntax. Use when setting up TS or migrating to stricter type safety.
Modern TypeScript configuration with strict type checking for maximum safety and developer experience. This guide focuses on TypeScript 5.x best practices for 2025.
Core Expertise
What is Strict Mode?
: Catch more bugs at compile time
Type safety
Better IDE experience: Improved autocomplete and refactoring
Maintainability: Self-documenting code with explicit types
Modern defaults: Align with current TypeScript best practices
Key Capabilities
Strict null checking
Strict function types
No implicit any
No unchecked indexed access
Proper module resolution
Modern import/export syntax enforcement
Recommended tsconfig.json (2025)
Minimal Production Setup
{"compilerOptions":{// Type Checking"strict":true,"noUncheckedIndexedAccess":true,"noImplicitOverride":true,"noPropertyAccessFromIndexSignature":true,"noFallthroughCasesInSwitch":true,"noUnusedLocals":true,"noUnusedParameters":true,// Modules"module":"ESNext","moduleResolution":"Bundler","resolveJsonModule":true,"allowSyntheticDefaultImports":true,"esModuleInterop":false,"verbatimModuleSyntax":true,// Emit"target":"ES2022","lib":["ES2023","DOM","DOM.Iterable"],"outDir":"dist","declaration":true,"declarationMap":true,"sourceMap":true,"removeComments":false,"noEmit":false,// Interop"isolatedModules":true,"allowJs":false,"checkJs":false,"skipLibCheck":true,"forceConsistentCasingInFileNames":true},"include":["src/**/*"],"exclude":["node_modules","dist","build"]}
Index signatures return T | undefined instead of T
noImplicitOverride
Require override keyword for overridden methods
noPropertyAccessFromIndexSignature
Force bracket notation for index signatures
noFallthroughCasesInSwitch
Prevent fallthrough in switch statements
exactOptionalPropertyTypes
Optional properties cannot be set to undefined explicitly
noUncheckedIndexedAccess (Essential)
// With noUncheckedIndexedAccessconstusers: Record<string, User> = {};
const user = users['john'];
// Type: User | undefined (correct - must check before use)if (user) {
console.log(user.name); // Type narrowed to User
}
Always enable this flag to prevent runtime errors.
Requires explicit .js extensions (even for .ts files)
Supports conditional exports
verbatimModuleSyntax (Recommended for 2025)
Prevents TypeScript from rewriting imports/exports.
{"compilerOptions":{"verbatimModuleSyntax":true}}
// Error: 'User' is a type and must be imported with 'import type'import { User } from'./types';
// Correctimporttype { User } from'./types';
// Correct (mixed import)import { fetchUser, typeUser } from'./api';
Replaces deprecated importsNotUsedAsValues and preserveValueImports.
Agentic Optimizations
Context
Command
Check errors
bunx tsc --noEmit
Check single file
bunx tsc --noEmit src/utils.ts
Show config
bunx tsc --showConfig
Check module resolution
bunx tsc --showConfig | grep moduleResolution
Quick Reference
Recommended Flags
Flag
Value
Category
strict
true
Type Checking
noUncheckedIndexedAccess
true
Type Checking
noImplicitOverride
true
Type Checking
noPropertyAccessFromIndexSignature
true
Type Checking
noFallthroughCasesInSwitch
true
Type Checking
module
ESNext / NodeNext
Modules
moduleResolution
Bundler / NodeNext
Modules
verbatimModuleSyntax
true
Modules
target
ES2022
Emit
isolatedModules
true
Interop
skipLibCheck
true
Interop
For detailed examples, advanced patterns, and best practices, see REFERENCE.md.