TypeScript Advanced Features and Tooling Interview Questions and Answers
15 questions on tsconfig, strict mode, declaration files, modules, satisfies, decorators, and TypeScript in real projects.
Published October 24, 2026 · Updated October 29, 2026 · 15 questions
Edited by Dev Kilaru, Senior Data Analyst. How we make our content
1. What does strict mode enable, and why should you use it?
The strict option turns on a group of checks: strictNullChecks, noImplicitAny, strictFunctionTypes, strictBindCallApply, strictPropertyInitialization, noImplicitThis, useUnknownInCatchVariables, and alwaysStrict. Together they catch the most common bugs, such as null dereferences and untyped values. New projects should always enable it, and old projects can adopt the flags gradually.
2. What are the most important tsconfig options?
target (the JavaScript version to emit), module and moduleResolution (how imports work), strict, outDir and rootDir, include and exclude, esModuleInterop, skipLibCheck (skips checking declaration files for speed), resolveJsonModule, and paths for import aliases. Many frameworks supply a base config you extend.
3. What is the difference between the compiler (tsc) and a transpiler such as Babel, esbuild, or SWC?
tsc performs full type checking and can emit JavaScript and declaration files. Tools such as esbuild, SWC, and Babel only strip types and are much faster, but do not type check. Many projects use a fast tool to build and run tsc --noEmit in CI or the editor to check types.
4. What are declaration files (.d.ts)?
They describe the types of JavaScript code without containing implementation. Libraries ship them with their package (the types field), or you install community types from the @types scope, such as @types/node. You can also write your own to type an untyped module or global variables.
5. What is declaration merging?
When several declarations share a name, TypeScript merges them. Interfaces with the same name combine their members, and namespaces can merge with classes, functions, or enums. It is how libraries let you augment their types, for example adding a property to Express's Request.
6. What does the satisfies operator do?
Added in TypeScript 4.9, satisfies checks that a value matches a type without changing the value's inferred type. You keep precise literal types while still getting errors for mistakes.
const palette = { red: [255, 0, 0], green: '#00ff00', } satisfies Record<string, string | number[]>; palette.red.map((n) => n * 2); // still known to be number[]7. How do modules work in TypeScript, and what is import type?
TypeScript uses the ES module syntax of import and export, and moduleResolution controls how paths are found. import type { User } from './user' imports only the type and is erased entirely, which avoids runtime imports and circular dependency issues. The verbatimModuleSyntax option makes this explicit.
8. What are decorators?
Decorators are functions that annotate and modify classes and their members, used by frameworks like Angular and NestJS. TypeScript 5.0 added support for the standard ECMAScript decorators, which differ from the older experimental ones enabled with experimentalDecorators. Check which style your framework expects.
9. What is the difference between abstract classes and interfaces in TypeScript?
An interface exists only at compile time and describes a shape. An abstract class exists at runtime, can contain implementation and state, cannot be instantiated directly, and can declare abstract members that subclasses must implement. Use an interface for contracts and an abstract class for shared behavior.
10. What are access modifiers and parameter properties?
public, private, and protected control visibility at compile time, while a hash prefix (#field) gives truly private fields at runtime. A parameter property declares and assigns a field in the constructor signature.
class User { constructor(public readonly id: number, private secret: string) {} }11. How do you validate data that comes from outside your program, such as API responses?
Types are erased at runtime, so a type annotation does not prove the data is correct. Validate at the boundary with a runtime schema library (such as Zod, Valibot, or similar) or hand-written type guards, and derive the TypeScript type from the schema so the two never drift apart.
12. How would you migrate a JavaScript project to TypeScript?
Add TypeScript with allowJs and checkJs set up, rename files to .ts one at a time starting from leaf modules, install @types packages, begin with loose settings and tighten the strict flags gradually, and fix any usage one module at a time. Keep the build and tests passing at every step.
13. What is the difference between unknown and generics when writing flexible functions?
unknown accepts any input but loses information, so callers get unknown back and you must narrow it. A generic keeps the relationship between input and output types, so callers get precise results without assertions. Use generics when the output depends on the input, and unknown for values you genuinely know nothing about.
14. How do you type React components and props?
Define an interface or type for the props and annotate the parameter. Use React's types for children, events, and refs.
interface ButtonProps { label: string; onClick: (event: React.MouseEvent<HTMLButtonElement>) => void; disabled?: boolean; } function Button({ label, onClick, disabled = false }: ButtonProps) { return <button onClick={onClick} disabled={disabled}>{label}</button>; }15. How do you debug type errors that are hard to read?
Read the error from the last line upward, because the root cause is usually at the end. Hover over types in the editor, break big types into named pieces to see where they differ, and use temporary assignments such as const x: Expected = actual to localize the mismatch. Avoid silencing errors with any or @ts-ignore; if you must, prefer @ts-expect-error with a comment, which fails when the error is fixed.
Interview Tips
- Show you know the difference between compile-time guarantees and runtime behavior.
- Have an opinion on strictness settings and be ready to defend it with an example bug it prevents.
- Mention tooling you have used: ESLint with typescript-eslint, tsc in CI, and your editor's type checks.