Polyglot
Languages TypeScript stdlib
TypeScript § stdlib

Standard library

TypeScript does not have a standard library of its own — the runtime library is JavaScript’s, accessed through TypeScript’s lib.d.ts files describing the built-in globals. The conventional ECMAScript built-ins are: Object, Array, String, Number, Boolean, Date, RegExp, Math, JSON, Promise, Map, Set, WeakMap, WeakSet, Error and its subclasses, Symbol, Proxy, Reflect, and the Intl namespace for internationalisation. Browser environments add the DOM (document, window, Element, etc.) and Web APIs (fetch, Blob, URL, FormData, etc.). Node.js adds substantial APIs (fs, path, os, process, etc.). The combination — JavaScript’s substantial built-in globals plus the platform-specific surface — is the substance of TypeScript’s runtime library.

This tour points out the principal globals and APIs.

Object

The conventional object operations:

Object.keys(obj);                                 // ["a", "b", ...]
Object.values(obj);                               // [1, 2, ...]
Object.entries(obj);                              // [["a", 1], ...]

Object.assign(target, source1, source2);          // shallow merge
Object.freeze(obj);                               // shallow immutable
Object.isFrozen(obj);
Object.fromEntries(entries);                      // [["a", 1]] → { a: 1 }

Object.create(proto);                             // create with prototype
Object.getPrototypeOf(obj);
Object.setPrototypeOf(obj, proto);

Object.defineProperty(obj, "key", { value, writable, enumerable, configurable });
Object.getOwnPropertyDescriptor(obj, "key");

Object.hasOwn(obj, "key");                        // ES2022; preferred over hasOwnProperty

The Object.fromEntries and Object.entries admit substantial transformation patterns:

const transformed = Object.fromEntries(
    Object.entries(obj).map(([k, v]) => [k, transform(v)]),
);

const filtered = Object.fromEntries(
    Object.entries(obj).filter(([k, v]) => v !== null),
);

Array

The principal array operations are treated in Loops and Data structures.

The static methods:

Array.from(iterable);                             // from iterable
Array.from({ length: 10 }, (_, i) => i);         // [0, 1, ..., 9]
Array.from("abc");                                // ["a", "b", "c"]

Array.of(1, 2, 3);                                // [1, 2, 3]
Array.isArray(value);

// Modern (ES2023):
arr.toSorted((a, b) => a - b);                    // non-mutating sort
arr.toReversed();                                 // non-mutating reverse
arr.toSpliced(1, 1);                              // non-mutating splice
arr.with(1, 99);                                  // non-mutating set at index

The to* non-mutating variants admit immutable updates without spread.

String

The principal string operations are treated in Strings.

The static methods:

String.raw`literal\nwith\tno escapes`;            // raw string from template
String.fromCharCode(65);                          // "A"
String.fromCodePoint(0x1F600);                    // "😀"

Number

Number.MAX_SAFE_INTEGER;                          // 2^53 - 1
Number.MIN_SAFE_INTEGER;
Number.EPSILON;                                   // smallest distinguishable difference
Number.MAX_VALUE;
Number.MIN_VALUE;
Number.POSITIVE_INFINITY;
Number.NEGATIVE_INFINITY;
Number.NaN;

Number.isInteger(value);
Number.isSafeInteger(value);
Number.isFinite(value);
Number.isNaN(value);                              // strict; preferred over global isNaN

Number.parseInt("42", 10);
Number.parseFloat("3.14");

const n = 3.14159;
n.toFixed(2);                                     // "3.14"
n.toPrecision(4);                                 // "3.142"
n.toExponential(2);                               // "3.14e+0"
n.toString(16);                                   // base-16 string

Math

Math.PI;
Math.E;
Math.LN2;
Math.LN10;
Math.LOG2E;
Math.LOG10E;
Math.SQRT2;

Math.abs(-5);                                     // 5
Math.ceil(3.1);                                   // 4
Math.floor(3.9);                                  // 3
Math.round(3.5);                                  // 4
Math.trunc(3.9);                                  // 3 (toward zero)
Math.sign(-5);                                    // -1

Math.max(1, 2, 3);                                // 3
Math.min(1, 2, 3);                                // 1
Math.max(...arr);                                 // for an array

Math.pow(2, 10);                                  // 1024
Math.sqrt(16);                                    // 4
Math.cbrt(27);                                    // 3
Math.log(Math.E);                                 // 1
Math.log2(8);                                     // 3
Math.log10(100);                                  // 2
Math.exp(1);                                      // E

Math.sin(angle);
Math.cos(angle);
Math.tan(angle);
Math.asin(value);
Math.atan2(y, x);

Math.random();                                    // [0, 1)
const r = Math.floor(Math.random() * (max - min + 1)) + min;  // integer in [min, max]

Math.hypot(3, 4);                                 // 5
Math.clz32(1);                                    // 31 (count leading zeros)

For cryptographically secure randomness, use crypto.getRandomValues (browser) or crypto.randomBytes (Node.js).

Date

const now = new Date();
const specific = new Date("2026-01-15T10:00:00Z");
const fromMs = new Date(1736937600000);
const fromComponents = new Date(2026, 0, 15, 10, 0, 0);  // month is 0-indexed!

now.getFullYear();
now.getMonth();                                   // 0-11
now.getDate();                                    // 1-31
now.getDay();                                     // 0-6 (Sun=0)
now.getHours();
now.getMinutes();
now.getSeconds();
now.getMilliseconds();
now.getTime();                                    // ms since epoch

now.toISOString();
now.toJSON();                                     // same as toISOString
now.toLocaleDateString();
now.toLocaleTimeString();
now.toLocaleString("ja-JP");

Date.now();                                       // current ms
Date.parse("2026-01-15");                        // ms
Date.UTC(2026, 0, 15);                           // ms (UTC components)

The Date is conventional but pitfall-laden (mutable, 0-indexed months, timezone surprises). The substantive alternative is the Temporal API (TC39 Stage 3 as of 2026); @js-temporal/polyfill admits early use. Otherwise, date-fns, dayjs, or Luxon are conventional.

JSON

JSON.stringify(value);                            // serialise
JSON.stringify(value, null, 2);                   // pretty-print

JSON.parse(text);                                 // parse
JSON.parse(text, (key, value) => /* reviver */);  // with reviver

For custom serialisation, a value’s toJSON method is called by JSON.stringify:

class User {
    constructor(public name: string, public age: number, private password: string) {}

    toJSON() {
        return { name: this.name, age: this.age };  // omit password
    }
}

const u = new User("Alice", 30, "secret");
JSON.stringify(u);                                // {"name":"Alice","age":30}

Promise

Treated in Async and concurrency.

Promise.resolve(value);                           // already-fulfilled
Promise.reject(error);                            // already-rejected

Promise.all([p1, p2, p3]);                        // all fulfil; reject on first error
Promise.allSettled([p1, p2, p3]);                 // never rejects
Promise.race([p1, p2, p3]);                       // first to settle
Promise.any([p1, p2, p3]);                        // first to fulfil

Map, Set, WeakMap, WeakSet

Treated in Data structures.

Error and subclasses

class Error {
    name: string;
    message: string;
    stack?: string;
    cause?: unknown;                               // ES2022
}

// Built-in subclasses:
TypeError                                         // wrong type
RangeError                                        // value out of range
ReferenceError                                    // undeclared variable
SyntaxError                                       // parse error
URIError                                          // bad URI

// AggregateError (ES2021):
new AggregateError([err1, err2], "multiple errors");

Treated in Error handling.

Symbol

The Symbol type admits unique, opaque keys:

const s = Symbol();
const named = Symbol("description");

const id = Symbol.for("global");                  // global registry
Symbol.keyFor(id);                                // "global"

// Well-known symbols (used by the engine):
Symbol.iterator;                                  // for [Symbol.iterator]()
Symbol.asyncIterator;
Symbol.toPrimitive;
Symbol.toStringTag;

class MyClass {
    [Symbol.iterator]() { /* ... */ }
}

Symbols are conventional for non-string property keys, particularly for protocol-style methods.

Proxy and Reflect

Proxy admits intercepting object operations:

const handler: ProxyHandler<{ value: number }> = {
    get(target, key, receiver) {
        console.log(`getting ${String(key)}`);
        return Reflect.get(target, key, receiver);
    },
    set(target, key, value, receiver) {
        console.log(`setting ${String(key)} = ${value}`);
        return Reflect.set(target, key, value, receiver);
    },
};

const p = new Proxy({ value: 0 }, handler);
p.value = 10;                                     // logs "setting value = 10"
console.log(p.value);                             // logs "getting value", returns 10

Reflect provides functional equivalents to operators:

Reflect.get(obj, "key");                          // obj["key"]
Reflect.set(obj, "key", value);                   // obj["key"] = value
Reflect.has(obj, "key");                          // "key" in obj
Reflect.deleteProperty(obj, "key");               // delete obj["key"]
Reflect.ownKeys(obj);                             // all own keys (incl. symbols)
Reflect.getPrototypeOf(obj);
Reflect.setPrototypeOf(obj, proto);
Reflect.construct(Constructor, args);
Reflect.apply(fn, this, args);

The conventional uses are metaprogramming, validation, ORM-style proxies, and observable state.

Intl

The Intl namespace admits internationalisation:

new Intl.NumberFormat("en-US").format(1234567);   // "1,234,567"
new Intl.NumberFormat("ja-JP", { style: "currency", currency: "JPY" }).format(1234567);

new Intl.DateTimeFormat("en-US", {
    year: "numeric", month: "long", day: "numeric"
}).format(new Date());

new Intl.RelativeTimeFormat("en", { numeric: "auto" }).format(-1, "day");  // "yesterday"

new Intl.ListFormat("en", { style: "long" }).format(["a", "b", "c"]);  // "a, b, and c"

new Intl.Collator("de-DE").compare("ä", "z");    // locale-aware comparison

new Intl.Segmenter("en", { granularity: "word" }).segment("Hello, world!");

crypto

Web Crypto API (browser and modern Node.js):

const buf = new Uint8Array(16);
crypto.getRandomValues(buf);

const id = crypto.randomUUID();                   // UUIDv4

// Hashing:
const data = new TextEncoder().encode("hello");
const hash = await crypto.subtle.digest("SHA-256", data);
const hex = Array.from(new Uint8Array(hash))
    .map(b => b.toString(16).padStart(2, "0")).join("");

// Encryption (substantive; conventional libraries are layered above):
const key = await crypto.subtle.generateKey(
    { name: "AES-GCM", length: 256 },
    true,
    ["encrypt", "decrypt"],
);

DOM APIs (browser)

The principal browser globals:

document                                          // the document
window                                            // the window
console                                           // logging

document.querySelector(".class");
document.querySelectorAll("p");
document.getElementById("id");
document.createElement("div");

document.body.appendChild(element);
element.classList.add("active");
element.setAttribute("data-id", "123");
element.addEventListener("click", e => /* ... */);

Web APIs

Modern browsers and Node.js (since 18+) admit substantial Web APIs:

// Fetch:
const response = await fetch(url);
const data = await response.json();

// URL:
const u = new URL("https://example.com/path?q=1");
u.searchParams.set("q", "2");

// FormData:
const fd = new FormData();
fd.append("name", "Alice");
fd.append("file", fileBlob);

// Blob:
const blob = new Blob(["hello"], { type: "text/plain" });

// FileReader (browser):
const reader = new FileReader();
reader.onload = () => console.log(reader.result);
reader.readAsText(file);

// AbortController:
const ctrl = new AbortController();
fetch(url, { signal: ctrl.signal });
ctrl.abort();

Node.js APIs

For Node.js targets, common modules:

import { readFile, writeFile, readdir } from "node:fs/promises";
import { join, basename, extname } from "node:path";
import { homedir, platform, cpus } from "node:os";
import { argv, env, exit, cwd } from "node:process";
import { Buffer } from "node:buffer";
import { createServer } from "node:http";
import { connect } from "node:net";
import { spawn, exec } from "node:child_process";
import { Worker } from "node:worker_threads";
import { createHash } from "node:crypto";

The node: prefix admits explicit Node.js built-in imports; conventional in modern code.

The Node.js ecosystem also has a standard library of conventional npm packages:

  • zod, valibot — schema validation.
  • date-fns, dayjs — date manipulation.
  • undici — HTTP client (faster than fetch in some cases).
  • pino — fast structured logging.

Common patterns

Object transformation

const lowercased = Object.fromEntries(
    Object.entries(obj).map(([k, v]) => [k.toLowerCase(), v]),
);

const filtered = Object.fromEntries(
    Object.entries(obj).filter(([_, v]) => v !== null),
);

Date arithmetic

const now = new Date();
const tomorrow = new Date(now.getTime() + 24 * 60 * 60 * 1000);
const inAnHour = new Date(now.getTime() + 60 * 60 * 1000);

// Better: use Temporal or date-fns:
import { addDays } from "date-fns";
const tomorrow2 = addDays(now, 1);

Number formatting

const n = 1234567.89;

n.toFixed(2);                                     // "1234567.89"
n.toLocaleString();                               // "1,234,567.89" (locale-dependent)
new Intl.NumberFormat("en-US").format(n);         // "1,234,567.89"
new Intl.NumberFormat("de-DE").format(n);         // "1.234.567,89"
new Intl.NumberFormat("en-US", {
    style: "currency", currency: "USD"
}).format(n);                                     // "$1,234,567.89"

Conditional access

const value = obj?.deep?.path?.value ?? defaultValue;
const length = arr?.length ?? 0;
const result = fn?.(arg);

JSON with reviver

const data = JSON.parse(text, (key, value) => {
    if (key === "createdAt" && typeof value === "string") {
        return new Date(value);
    }
    return value;
});

Frozen configuration

const config = Object.freeze({
    host: "localhost",
    port: 8080,
});

// Better, with type-level freeze:
const config = {
    host: "localhost",
    port: 8080,
} as const;

Hashable map keys via Symbol

const idKey = Symbol("id");

class User {
    [idKey]: string;
    constructor(id: string) { this[idKey] = id; }
}

Deep clone

const clone = structuredClone(value);             // ES2022; deep clone

// Or for JSON-compatible data:
const clone2 = JSON.parse(JSON.stringify(value));

The structuredClone is the conventional contemporary form; admits Date, Map, Set, ArrayBuffer, etc.

Counting via Map

function count<T>(items: T[]): Map<T, number> {
    const counts = new Map<T, number>();
    for (const item of items) {
        counts.set(item, (counts.get(item) ?? 0) + 1);
    }
    return counts;
}

Async resource management (TS 5.2+)

class Resource implements AsyncDisposable {
    async [Symbol.asyncDispose]() { /* cleanup */ }
}

{
    await using r = new Resource();
    // use r
}                                                 // automatic cleanup

TextEncoder/TextDecoder

const encoder = new TextEncoder();
const bytes = encoder.encode("hello");           // Uint8Array

const decoder = new TextDecoder();
const text = decoder.decode(bytes);              // "hello"

The mechanism admits substantial conversion between text and bytes; conventional in Web APIs.

A note on the conventional discipline

The contemporary TypeScript standard-library advice:

  • Use the JavaScript built-ins — they cover most needs.
  • Use Object.entries / fromEntries for typed-object transformations.
  • Use Array.from and the to* non-mutating methods.
  • Use Number.isFinite / isInteger / isNaN over the global versions.
  • Use Math.random for non-cryptographic randomness; crypto.getRandomValues for cryptography.
  • Use Intl.* for internationalisation.
  • Use JSON.stringify with a space argument for pretty-printing.
  • Use structuredClone for deep cloning.
  • Use URL for URL manipulation.
  • Use Promise.all / allSettled for concurrent operations.
  • Use crypto.randomUUID for unique identifiers.
  • Use Temporal / date-fns over raw Date for substantial date manipulation.
  • Use Node.js built-ins via node:* prefix.

The combination — JavaScript’s built-in objects, the platform-specific APIs (DOM, Node.js), the third-party ecosystem (npm) — is the substance of TypeScript’s runtime library. The discipline lean on the standard built-ins and reach for libraries when substantial functionality is needed; the breadth of the platform admits substantial out-of-the-box capability.