File types · Explainer

The TypeScript file (.ts, .mts, .cts)

A TypeScript file is a plain-text program written in TypeScript: JavaScript with type annotations that a compiler checks before the code runs. This guide explains what's inside one, how to compile or run it, the errors people hit most, how to tell it apart from a .ts video file, and has free sample TypeScript files to download for testing.

At a glance

Full name
TypeScript source file
Extensions
.ts; .mts (ES module), .cts (CommonJS), .d.ts (declarations only); .tsx with JSX
MIME type
None registered. Servers send text/plain, application/typescript or, wrongly, video/mp2t
Kind
Plain text (source code), UTF-8
Owner
Microsoft; open source under the Apache 2.0 licence. There is no separate standard: the compiler and its documentation define the language
First released
October 2012, by Microsoft (designed by Anders Hejlsberg)
Current version
TypeScript 7.0 (July 2026), the first with the compiler rewritten in Go
Runs with
tsc to compile to JavaScript; Node.js 22.18+ and 23.6+, Deno and Bun run it directly
Comments
// line and /* block */, as in JavaScript
Magic number
None. A .ts video file starts with the byte 47 instead

The basics

What is a TypeScript file?

A .ts file holds source code in TypeScript, a language Microsoft created as a superset of JavaScript: every JavaScript program is also valid TypeScript, and TypeScript adds a way to write down the types of values. A compiler reads those types and reports mistakes, like passing text where a number is expected, before the program ever runs. The file is plain text, so any text editor can open it.

Browsers can't run TypeScript. The types have to be removed first, either by compiling the file to a JavaScript file with tsc or a bundler, or by a runtime that strips them as it loads the file, as Node.js, Deno and Bun do. Either way, what finally runs is JavaScript.

  • Types are for the tools, not the running program. They are checked at compile time and erased. At run time, a TypeScript program behaves exactly like the JavaScript left behind.
  • Running is not checking. Node.js, Deno, Bun, esbuild and Vite remove types without checking them. Only the TypeScript compiler (tsc, or your editor using it) reports type errors.
  • .ts has a second meaning. It's also the extension of MPEG transport stream video, used by TV broadcasts and streaming. How to tell them apart is explained below.

Anatomy

What's inside a TypeScript file

A TypeScript file is JavaScript with extra syntax that describes types: what kind of value each variable, parameter and function result holds. Here is a short module, part by part. Everything that isn't plain JavaScript disappears before the code runs.

account.ts
import type { User } from "./user.ts";
import { formatName } from "./format.ts";

// One of three allowed values
type Role = "admin" | "editor" | "viewer";

interface Account {
  user: User;
  role: Role;
  lastLogin?: Date;
}

export function greet(account: Account): string {
  const name: string = formatName(account.user);
  return account.lastLogin
    ? `Welcome back, ${name}`
    : `Welcome, ${name}`;
}

export function first<T>(items: readonly T[]): T | undefined {
  return items[0];
}

const roles = ["admin", "editor"] as const satisfies readonly Role[];
  1. 1import type { User } from "./user.ts";

    A type-only import

    Brings in a type, not a value, so it can be removed completely. Node.js needs the type keyword here, or it looks for a value called User at run time and fails.

  2. 2import { formatName } from "./format.ts";

    A value import

    An ordinary ES module import. Writing the .ts extension is what Node.js, Deno and Bun expect; for tsc it needs a setting, explained below.

  3. 3type Role = "admin" | "editor" | "viewer";

    A type alias with a union

    Role may only be one of three strings. A typo such as "admim" is a compile error instead of a bug found later.

  4. 4interface Account { … }

    An interface

    Describes the shape of an object: which properties it has and their types. Interfaces produce no JavaScript at all.

  5. 5lastLogin?: Date;

    An optional property

    The ? means the property may be missing, so the compiler makes you check for it before use.

  6. 6greet(account: Account): string

    Parameter and return types

    The colon annotations say what goes in and what comes out. Calling greet with the wrong object, or using its result as a number, is caught before running.

  7. 7const name: string = …

    A variable annotation

    Optional most of the time: TypeScript infers that name is a string from what's assigned to it.

  8. 8first<T>(items: readonly T[]): T | undefined

    A generic function

    T stands for whatever type the caller passes, so first([1, 2]) returns a number and first(["a"]) a string.

  9. 9as const satisfies readonly Role[]

    `as const` and `satisfies`

    as const keeps the exact values instead of widening them to string[]; satisfies checks them against a type without changing it.

Under the hood

How a .ts file becomes running code

There are two ways to get from TypeScript to running code, and most projects use both: a fast tool that only removes types, and the compiler to check them.

ToolChecks types?What it doesCommand
TypeScript compilerYesChecks, then writes .js files (plus .d.ts and .map files if asked)npx tsc (or npx tsc --noEmit to check only)
Node.js 22.18+, 23.6+NoRuns the file directly, replacing the types with spacesnode app.ts
tsxNoRuns any TypeScript, including enums and JSX, on Node.js; reads tsconfig.jsonnpx tsx app.ts
DenoNot by defaultRuns it directlydeno run app.ts (deno check to check)
BunNoRuns it directlybun app.ts
esbuild, Vite and other bundlersNoRemove types while bundling for the browsernpx esbuild app.ts --bundle

Node.js runs TypeScript by type stripping: it replaces the type syntax with whitespace and runs what's left. Because every line and column stays where it was, error messages point at the right place without a source map. It was enabled by default in Node.js 23.6.0 and backported to 22.18.0, and declared stable in 25.2.0 and 24.12.0. The same node app.ts command works on Windows, macOS and Linux. Here is the anatomy example after stripping, made with Node.js's own stripTypeScriptTypes(): the types have become spaces, and lines that held only types are now blank.

account.ts, types stripped

import { formatName } from "./format.ts";

// One of three allowed values








export function greet(account         )         {
  const name         = formatName(account.user);
  return account.lastLogin
    ? `Welcome back, ${name}`
    : `Welcome, ${name}`;
}

export function first   (items              )                {
  return items[0];
}

const roles = ["admin", "editor"]                                   ;

Stripping only works for TypeScript syntax that can simply be deleted. Node.js refuses features that would need new JavaScript generated: enum, namespace blocks containing code, parameter properties (constructor(private x: number)) and import x = require(). It also ignores tsconfig.json, requires file extensions in imports, and won't run TypeScript inside node_modules. The Node.js documentation recommends these compiler settings, so tsc flags anything Node.js can't run:

tsconfig.json (for Node.js type stripping)
{
  "compilerOptions": {
    "noEmit": true,
    "target": "esnext",
    "module": "nodenext",
    "rewriteRelativeImportExtensions": true,
    "erasableSyntaxOnly": true,
    "verbatimModuleSyntax": true
  }
}

Extensions

.ts vs .mts vs .cts vs .d.ts vs .tsx

The extension tells the compiler and runtimes how to treat the file, the same way .mjs and .cjs do for JavaScript:

ExtensionWhat it isCompiles to
.tsTypeScript. ES module or CommonJS depending on the nearest package.json "type" field, as for .js.js
.mtsAlways an ES module (import/export).mjs
.ctsAlways CommonJS (require/module.exports).cjs
.d.tsA declaration file: types only, no code. Describes JavaScript that lives elsewhere, such as a libraryNothing; it's read, never run
.d.mts, .d.ctsDeclarations for .mjs and .cjs filesNothing
.tsxTypeScript with JSX tags, used for React components. See the TSX file.js, or .jsx with "jsx": "preserve"

Declaration files are how editors know the types of plain JavaScript packages. tsc --declaration writes them next to compiled output, and packages without their own are often covered by a separate @types/… package, such as @types/node.

Project files

tsconfig.json: the file that sets up a project

A tsconfig.json in a folder marks the root of a TypeScript project. Running tsc with no file names compiles everything it includes, with its settings. Editors read it too, so the errors you see while typing match the build.

tsconfig.json
{
  "compilerOptions": {
    "target": "es2022",
    "module": "nodenext",
    "strict": true,
    "outDir": "dist",
    "declaration": true,
    "sourceMap": true
  },
  "include": ["src"]
}
  • target: which JavaScript version to output. Newer syntax is rewritten for older targets.
  • module: which module system to output and how imports are resolved. nodenext follows Node.js's own rules.
  • strict: turns on the stricter checks, such as reporting values that might be null.
  • outDir, declaration, sourceMap: where the .js goes, and whether to also write .d.ts declaration files and source maps.
  • noEmit: check only, write nothing. Common when another tool does the building.

TypeScript 7 changed some defaults

In TypeScript 7.0, strict is on and module is esnext unless you say otherwise, types defaults to an empty list (add "types": ["node"] to use Node.js's types), and options deprecated in 6.0, such as target: es5, baseUrl and moduleResolution: node10, are now errors. Running tsc file.ts in a folder that has a tsconfig.json is also an error unless you add --ignoreConfig.

Related formats

TypeScript vs JavaScript files

TypeScript (.ts)JavaScript (.js)
Type annotationsYes, checked by tscNo (JSDoc comments can carry types)
Runs in a browserNo, compile it firstYes
Runs in Node.jsYes, in 22.18+ and 23.6+ (erasable syntax only)Yes
Build stepUsually, for browsers and librariesOptional
Mistakes foundWhile you type, and at compile timeWhen the code runs
Registered MIME typeNonetext/javascript
Published to npm asCompiled .js plus .d.ts declarations.js

Converting is one-way and easy in one direction: rename a .js file to .ts and it's already TypeScript, with types to add over time. Going back means compiling it, which removes the types.

History

TypeScript versions

VersionReleasedNotable for
0.8October 2012The first public release, a preview
1.0April 2014The first stable release
4.1November 2020The react-jsx setting for React's new JSX transform
5.0March 2023Standard ECMAScript decorators, the bundler module resolution
5.8February 2025--erasableSyntaxOnly, for code that Node.js can run by stripping types
6.0March 2026strict on by default; the last compiler written in TypeScript itself
7.0July 2026The compiler rewritten in Go: Microsoft reports full builds 8 to 12 times faster

A .ts file doesn't say which TypeScript version it was written for. Code written for one version almost always compiles with the next; what changes between versions is mostly which mistakes the checker catches. TypeScript 7.0 ships without a programmatic API, so tools that embed the compiler can keep using the 6.0 one from the @typescript/typescript6 package for now.

Same extension

Is my .ts file TypeScript or a video?

.ts is also the extension of the MPEG transport stream, the video format of digital TV broadcasts, which is also used for recordings from TV tuners and for segments of streamed video. The two have nothing in common, and telling them apart takes a second:

TypeScriptMPEG transport stream
ContentReadable textBinary data
In a text editorCodeGarbage characters
First byteUsually /, i, e or another letter (a comment, import, export)Always 47 (hex), the sync byte
StructureLines of textPackets of exactly 188 bytes, each starting with 47
Typical sizeA few KBMegabytes to gigabytes
MIME typeNone registeredvideo/mp2t
Opens withA code editorVLC, mpv, ffmpeg and most video players

To check the first byte, run head -c 1 file.ts | od -An -tx1 on macOS or Linux, or Format-Hex file.ts | Select-Object -First 1 in PowerShell. A third, rarer .ts is a Qt Linguist translation file: XML that starts with <?xml and contains a <TS> element.

Why servers send TypeScript as video

Many web servers and libraries look up the type by extension, and their tables only know the video meaning: the mime-db list that many Node.js servers use maps .ts and .mts to video/mp2t. A browser opening such a link may try to play or download it. Serve TypeScript as text/plain (or application/typescript) if people should read it in the browser.

Troubleshooting

The TypeScript errors people hit most, and what they mean

Error messageUsual causeFix
Unknown file extension ".ts"Node.js older than 22.18 (or 23.6 in the 23 line), or type stripping switched off. In a CommonJS project the same problem shows as a SyntaxError at the first type annotationUpgrade Node.js, or run it with npx tsx file.ts
ERR_UNSUPPORTED_TYPESCRIPT_SYNTAX: TypeScript enum is not supported in strip-only modeAn enum, a parameter property or a namespace with code, which Node.js can't stripUse a union type or an as const object instead, or run it with tsx; erasableSyntaxOnly makes tsc flag these
The requested module './shapes.ts' does not provide an export named 'Shape'A type imported without import type, so Node.js looks for a valueWrite import type { Shape }; verbatimModuleSyntax makes tsc insist on it
ERR_MODULE_NOT_FOUND: Cannot find module './shapes'An import without a file extensionWrite the full name: ./shapes.ts
TS5097: An import path can only end with a '.ts' extension when 'allowImportingTsExtensions' is enabledtsc checking code written for Node.js-style importsSet rewriteRelativeImportExtensions (rewrites them to .js on output) or allowImportingTsExtensions with noEmit
TS2591: Cannot find name 'process'Node.js's types aren't loadednpm i -D @types/node and add "types": ["node"] to tsconfig.json
TS5112: tsconfig.json is present but will not be loaded if files are specified on commandlinetsc file.ts in a project folder, with TypeScript 7Run plain tsc, or add --ignoreConfig

A program with type errors can still run: node, tsx, Bun and bundlers never look at the types. The sample-type-error.ts file below shows this. Run tsc --noEmit before committing or in CI, so type errors stop a build instead of reaching users.

How to

How to open and edit a TypeScript file, and is it safe?

  • Edit it: VS Code has TypeScript support built in, with errors underlined as you type and fixes suggested. WebStorm, Zed, Neovim and most other code editors support it too, and any plain-text editor can open the file.
  • On Windows: double-clicking a .ts file may open a video player, because of the video meaning of the extension. Use Open with, or open it from your editor.
  • Try it without installing anything: paste it into the TypeScript Playground on typescriptlang.org, which shows the errors and the JavaScript output side by side.
  • Run it: install Node.js (22.18 or newer) and run node file.ts; or npx tsx file.ts for files that use enums or other non-erasable syntax.
  • Convert it to JavaScript: npx tsc file.ts writes file.js next to it. Online, the Playground's JS tab does the same.

Opening a .ts file in an editor only shows text; nothing runs. Running one with Node.js, Deno or Bun is different: it's a program with the same access to your files and network as any other you start. Unlike .js, Windows doesn't run .ts files with Windows Script Host when they're double-clicked. Types don't make code safe: they catch mistakes, not malicious intent. Read code you didn't write before you run it, and be as careful with npx commands and npm packages as with any software you install.

Free downloads

Sample TypeScript files to download

Free sample TypeScript files for testing compilers, runtimes, editors, linters, upload filters and MIME types. Except the one with a deliberate error, each passes tsc --noEmit in strict mode, and each runnable one runs with node (22.18+), tsx and Bun, with the same output.

sample-app.ts · 3.3 KBDownloadOpen
Loading…

What's inside sample-app.ts

The file is commented: open it in a text editor and each numbered comment marks one of these parts. Run it with node sample-app.ts to see its three lines of output.

  1. Comments 1 and 2: annotations and an interface

    Typed const and let variables, then a Product interface with a readonly property and an optional tags list.

  2. Comments 3 and 4: union and object types

    A Status that can only be "pending", "paid" or "shipped", and an Order type built from the others.

  3. Comments 5 to 7: functions

    Parameter and return types, a generic firstOrDefault<T>, and narrowing with typeof and === null, where TypeScript knows the exact type inside each branch.

  4. Comment 8: `as const` and `satisfies`

    A catalogue checked against Product without losing its exact values, with accented product names to show UTF-8 text.

  5. Comment 9: a class

    A Basket with both kinds of privacy: private (checked only by the compiler) and #totalCents (enforced by JavaScript at run time).

  6. Comments 10 and 11: async code and output

    A function returning Promise<Order>, then the output: Ada's Café: 2 × Thé vert, 1 × Crème brûlée = €12.25 and two more lines.

All sample TypeScript files

  • Commented sample program

    sample-app.ts · 3.3 KB (3,351 bytes)

    Types, interfaces, unions, generics, narrowing, satisfies, a class with private fields and async code, with numbered comments explaining each part. Uses only erasable syntax, so Node.js can run it directly.

    • Checking a runtime or bundler handles modern TypeScript
    • Teaching the building blocks of TypeScript
  • ES module that imports another (.mts)

    sample-main.mts · 1.1 KB (1,103 bytes)

    Imports a type with import type and values with an explicit .mts extension from sample-shapes.mts, and uses top-level await. Download both files to the same folder and run node sample-main.mts.

    • Testing module resolution and `.ts` extensions in imports
    • Checking `rewriteRelativeImportExtensions` output (`.mts` becomes `.mjs`)
  • Module that sample-main.mts imports

    sample-shapes.mts · 879 bytes

    Exports two types (a discriminated union of shapes) and two values. On its own it runs but prints nothing.

    • Testing import resolution
    • A minimal TypeScript ES module
  • Declaration file (.d.ts)

    sample-types.d.ts · 1.1 KB (1,144 bytes)

    Types only: a global variable, an overloaded function, a declare module for an untyped package and an addition to the browser's Window interface.

    • Testing tools that must treat `.d.ts` files differently
    • Showing what a declaration file looks like
  • File with one deliberate type error

    sample-type-error.ts · 1018 bytes

    Clearly labelled at the top. It runs with node and prints a wrong total, while tsc --noEmit rejects it with error TS2345. Shows that runtimes don't check types.

    • Checking a CI step or editor reports type errors
    • Demonstrating type stripping vs type checking
  • 100 KB TypeScript file (CRLF)

    sample-100kb.ts · 100 KB (102,400 bytes)

    A typed table of the Roman numerals 1 to 3,999 and a parser that checks every one, saved with Windows (CRLF) line endings and padded with comments to exactly 102,400 bytes.

    • Upload and size-limit tests
    • Line-ending handling in tools and diffs

Ways to test with them

  • Type stripping vs checking: run sample-type-error.ts with node, then with tsc --noEmit. The first prints a result; the second must fail with TS2345.
  • MIME types: put sample-app.ts online and check the Content-Type your server sends. If it's video/mp2t, browsers may try to play it instead of showing the code.
  • Module resolution: download sample-main.mts and sample-shapes.mts together and run them with Node.js, tsx, Deno and Bun, or compile them with tsc --rewriteRelativeImportExtensions --module nodenext.
  • Upload filters and limits: some filters treat .ts as video. sample-100kb.ts is exactly 102,400 bytes, for testing a limit at the boundary.

Free to use for testing, teaching and demos, commercially or not, with no attribution needed. A link back to this page is always appreciated.

Put it online

Have a TypeScript file? Give it a link.

Drop a .ts file on 99helpers and it gets its own address in seconds. Opening the link shows the code as plain text in the browser, and it never runs, which is what you want for sharing source code.

Questions

TypeScript files, frequently asked

What is a .ts file?

Usually a TypeScript source file: JavaScript with type annotations, as plain text. It can also be an MPEG transport stream video, which is binary; open it in a text editor and you'll see which.

How do I run a .ts file?

With Node.js 22.18 or newer, run node file.ts. For files that use enums or other syntax Node.js can't strip, use npx tsx file.ts. Deno (deno run file.ts) and Bun (bun file.ts) run it directly too.

How do I convert a .ts file to .js?

Run npx tsc file.ts to write file.js next to it, or set up a tsconfig.json and run tsc for a whole project. Bundlers such as esbuild and Vite do the same while building.

Can a browser run TypeScript?

No. Browsers only run JavaScript, so TypeScript is compiled or bundled first. Opened directly, a .ts file shows as text, or is downloaded.

What's the difference between .ts and .d.ts?

A .ts file contains code that runs. A .d.ts declaration file contains only types that describe code living elsewhere, usually a JavaScript library, and produces no output.

What's the difference between .ts and .mts?

.mts is always an ES module and compiles to .mjs. A .ts file is an ES module or CommonJS depending on the nearest package.json, and compiles to .js. .cts is always CommonJS.

Does Node.js check types when it runs TypeScript?

No. It replaces the types with whitespace and runs the rest. Run tsc --noEmit to find type errors.

What is the MIME type of a TypeScript file?

None is registered. text/plain and application/typescript are common; video/mp2t belongs to the video format and makes browsers treat the file as video.

Is TypeScript a different language from JavaScript?

It's JavaScript with extra syntax for types. Any JavaScript file is valid TypeScript, and removing the types from TypeScript leaves JavaScript.

Related formats

Other file types explained

Keep going

Related

Sources

Last reviewed 27 October 2026.