Overview

TypeScript is the default for static typing in JavaScript projects as of 2026. Its tooling, community, ecosystem support, and hiring pool dwarf Flow’s. Use Flow only if you maintain a Meta-stack codebase (React Native, Relay) that already runs Flow with active tooling investment. For any new project, the answer is TypeScript. See typescript for project setup conventions.

When TypeScript wins

TypeScript is the right pick for virtually all new JavaScript and Node.js projects.

  • Ecosystem breadth: every major library ships @types/* or first-party declarations. Flow type stubs for third-party libraries are sparse and often outdated.
  • Tooling depth: the TypeScript Language Server (tsserver) powers VS Code, Neovim, JetBrains, and every major editor. Autocomplete, go-to-definition, and refactoring across large codebases work reliably.
  • Build pipeline: swc-vs-babel and esbuild both strip TypeScript annotations without type-checking, making builds fast. Vite, Bun, and Next.js all treat TypeScript as first-class input.
  • Community: the TypeScript tag on Stack Overflow has 50x more answers than Flow. Hiring TypeScript engineers is straightforward; Flow engineers are a niche pool.
  • Strict mode: strict: true in tsconfig.json turns on null checking, exact optional properties, and unchecked indexed access. Flow’s strict mode exists but is less battle-tested in large codebases.
  • Incremental adoption: rename a .js file to .ts and add types one file at a time. The compiler accepts // @ts-ignore and any as escape hatches during migration.

When Flow wins

Flow’s advantage is narrow and shrinking. Stay on Flow when all of the following are true.

  • The codebase already runs Flow with a recent version (0.230+) and the team actively maintains type coverage.
  • The project uses Relay or React Native with Meta’s internal toolchain, where Flow’s type system is tuned for those patterns.
  • Migration cost is genuinely prohibitive: a monorepo with millions of Flow-annotated lines and no automated codemod budget is a real constraint.

Outside that window, Flow is a maintenance liability. Meta continues to ship it but the external community has largely moved on. New contributors will not know it.

Trade-offs at a glance

DimensionTypeScriptFlow
Ecosystem coverageNear-universal @types and native typesSparse; many libraries untyped
Editor supportFirst-class in all major editorsDecent in VS Code via extension; inconsistent elsewhere
Build speedStrip-only with SWC or esbuildflow-remove-types or Babel plugin
Community sizeVery largeSmall; Meta-focused
Strict null checksstrict: truestrict mode; less adoption
Learning resourcesAbundantLimited
Framework integrationReact, Vue, Angular, Next.js, Astro, allReact and React Native primarily
HiringLarge poolNiche
Active external devYes (Microsoft-led)Minimal outside Meta
Migration toolingflowToTs, ts-migrate, manualN/A (you migrate away from it)

Migration cost

Flow to TypeScript is the common direction and is supported by codemods.

  • flow-to-ts: converts Flow annotations to TypeScript syntax. Handles most constructs; expect 10 to 20 percent of files needing manual cleanup, especially around opaque types, variance annotations, and $ObjMap.
  • ts-migrate from Airbnb: inserts any where type inference fails and gets the project compiling fast. Plan a second pass to tighten types after the build passes.
  • Timeline: a 50 kloc Flow codebase typically migrates in one to three sprints depending on Flow coverage depth and library dependency sprawl.
  • The hardest part is third-party types: libraries that had Flow stubs but no @types need type declarations written or sourced from DefinitelyTyped.

TypeScript-to-Flow migration has no documented tooling and would be a regression. Do not do it.

Recommendation

  • New project: TypeScript. No caveats.
  • Existing Flow project, active and healthy: stay on it; do not rewrite for its own sake. Migrate opportunistically when a module undergoes significant change.
  • Existing Flow project showing type rot (stale stubs, contributors unfamiliar with Flow): migrate. Budget one sprint per 20 kloc of annotated code.
  • Mixed codebase: TypeScript files and Flow files do not coexist in the same module graph. Migrate module by module with a clear boundary.