Open-Source Wikis

/

TypeScript

/

Systems

/

Build mode (`tsc -b`)

microsoft/TypeScript

Build mode (tsc -b)

The orchestrator that compiles a graph of project references in topological order, sharing state across projects and writing per-project .tsbuildinfo files.

Source

File Role
src/compiler/tsbuild.ts Public types — BuildOptions, UpToDateStatus, BuildOrder, etc.
src/compiler/tsbuildPublic.ts The Solution Builder — 4,000+ lines

Purpose

Project references (references in tsconfig.json) let large codebases split into smaller compilations that import each other. tsc -b (build mode) is the driver:

  • Parses the root tsconfig.json's references and recursively follows them.
  • Computes a topological build order.
  • For each project, decides whether it's UpToDate, OutOfDateWithSelf, OutOfDateWithUpstream, etc.
  • Compiles only what's stale.
  • Writes one .tsbuildinfo per project.
  • Optionally runs in --watch (continuous build) or --clean (delete outputs) mode.

Key abstractions

Symbol Role
createSolutionBuilder(host, rootNames, options) Public factory
SolutionBuilder The orchestrator instance with build, clean, buildReferences, buildAllProjects
BuildOrder The topologically sorted project list (or a circular-reference error)
UpToDateStatus (and UpToDateStatusType) Per-project state: Unbuildable, UpToDate, OutOfDateWithSelf, OutOfDateWithUpstream, OutOfDateBuildInfo, OutOfDateOptions, OutOfDateRoots, OutOfDateBuildInfoWithErrors, UpstreamOutOfDate, UpstreamBlocked, …
getUpToDateStatusOfProject The fast pre-check that reads .tsbuildinfo and decides whether to skip a project
BuildResultFlags What happened to a project this build (None, Success, DeclarationOutputUnchanged, …)

How it works

graph TD
    Root["tsc -b ./project"] --> Parse["parse tsconfig + follow references"]
    Parse --> Order["topological sort → BuildOrder"]
    Order --> Loop["for each project in order"]
    Loop --> Check["getUpToDateStatusOfProject"]
    Check --> Decision{"up to date?"}
    Decision -->|yes| Skip
    Decision -->|no| Build["createProgram + emit"]
    Build --> Info["write .tsbuildinfo"]
    Skip --> Loop
    Info --> Loop
    Loop --> Done["all projects processed"]

getUpToDateStatusOfProject is where the savings live. Without ever loading the source files, it:

  1. Reads the project's .tsbuildinfo.
  2. Compares stored options against the current CompilerOptions.
  3. Stats the configured root files and compares timestamps with the recorded set.
  4. Recursively checks each upstream project's status.

If the status is UpToDate, the project is skipped entirely. Otherwise, a full Program is built (with oldProgram set to the previous incremental state) and emitted.

Watch mode

createSolutionBuilderWithWatch keeps the orchestrator alive, watches each project's files and tsconfigs, and triggers per-project rebuilds in topological order when relevant changes arrive. This is what backs tsc -b --watch.

Diagnostics

Build-mode diagnostics include the standard Program ones plus solution-level errors:

  • TS6377: Cannot write file because it would overwrite input file — output paths overlap.
  • TS6379: Composite projects may not disable declaration emit--composite requires --declaration.
  • TS6378: Project references may not form a circular graph — cycle in references.

Integration points

  • Invoked by tsc -b via executeCommandLine.ts.
  • Reuses Program from program.ts for each project.
  • Reuses BuilderProgram from builder.ts for incremental signatures.
  • Reuses watch primitives for tsc -b --watch.

Entry points for modification

See systems/program and systems/watch-and-builder for the underlying primitives.

Built by Factory AutoWiki from public repository content. It is a generated preview for codebase exploration, not source-maintained documentation.

Build mode (`tsc -b`) – TypeScript wiki | Factory