TYPESCRIPT

TypeScript keyof Operator: Syntax, Use Cases, and Examples

The keyof operator in TypeScript lets you extract the names of properties from a type or interface. It returns a union of the property keys, which you can use to create safer, more flexible types. It’s especially useful when working with generics, utility types, and type transformations that rely on knowing the shape of an object.


What Is keyof?

keyof takes an object type and produces a union of its property names as string or number literals.

Example

type User = {
  id: number;
  name: string;
  email: string;
};

type UserKeys = keyof User;
// Result: "id" | "name" | "email"

You can use this union in other types—like Pick, Record, or constrained generics—to ensure only valid keys are referenced.


Using keyof on Objects

You can extract keys from object values at runtime by combining typeof with keyof.

const user = {
  id: 1,
  name: "Alice",
  email: "alice@example.com"
};

type Keys = keyof typeof user;
// Result: "id" | "name" | "email"

This is useful when you're writing generic functions that should only access known keys.


Working with Interfaces

When used with interfaces, keyof produces a union of all declared property names.

interface Product {
  title: string;
  price: number;
  inStock: boolean;
}

type ProductKeys = keyof Product;
// "title" | "price" | "inStock"

This makes it easier to dynamically operate on or restrict parts of an interface.


Generic Constraints with extends keyof

You can create safe, reusable functions by restricting generic type parameters to valid keys.

function getValue<T, K extends keyof T>(obj: T, key: K): T[K] {
  return obj[key];
}

const book = { title: "1984", author: "Orwell" };
const title = getValue(book, "title"); // OK

If you try an invalid key, TypeScript will catch it at compile time. This pattern is key in building safe APIs and helper utilities.


Index Signatures and Keyof

If a type uses an index signature, keyof may return string, number, or a union of both—depending on the index.

type Collection = {
  [id: number]: string;
};

type CollectionKey = keyof Collection;
// Result: number

This is common in types that represent maps, arrays, or dictionaries.


Casting Values as Keys

You can use as keyof to assert that a runtime value is a valid key of a type.

function logField<T>(obj: T, field: string) {
  const key = field as keyof T;
  console.log(obj[key]);
}

This is helpful when working with dynamic field names, but use it with caution—it bypasses full type safety.


Combining keyof with typeof

This combination is useful for extracting property names from a constant or config object.

const settings = {
  darkMode: true,
  volume: 70,
  notifications: false
};

type SettingsKeys = keyof typeof settings;
// "darkMode" | "volume" | "notifications"

You’ll often see this pattern in dynamic forms or config-driven UI.


Using keyof with Enums

When used with enums, keyof returns a union of the enum's key names—not their values.

enum Status {
  Active = "active",
  Inactive = "inactive"
}

type StatusKeys = keyof typeof Status;
// "Active" | "Inactive"

type StatusValues = typeof Status[StatusKeys];
// "active" | "inactive"

This lets you iterate or validate against enum keys and values as needed.


Mapped Types with keyof

You can use keyof inside mapped types to transform object properties.

type Original = {
  id: number;
  name: string;
};

type Nullable<T> = {
  [K in keyof T]: T[K] | null;
};

type NullableOriginal = Nullable<Original>;
// { id: number | null; name: string | null }

This is the foundation of many utility types like Partial, Readonly, and Pick.


Type Guards Using keyof

You can build generic type guards that check for key presence at runtime.

function hasKey<T>(obj: T, key: keyof T): boolean {
  return key in obj;
}

This is a flexible way to work with dynamic objects while staying within type boundaries.


Picking or Omitting Keys Dynamically

Use keyof with Exclude, Pick, or Omit to include or exclude properties programmatically.

type Person = {
  name: string;
  age: number;
  password: string;
};

type PublicKeys = Exclude<keyof Person, "password">;
type PublicInfo = Pick<Person, PublicKeys>;

This is perfect for hiding sensitive fields in APIs or UI layers.


Accessing Nested Keys

While keyof only extracts top-level keys, you can combine it with property access to go deeper.

type Nested = {
  user: {
    id: number;
    name: string;
  };
};

type UserKeys = keyof Nested["user"];
// "id" | "name"

This is handy when working with deeply nested config or data types.


Building UI Forms with keyof

In UI frameworks like React, keyof helps create type-safe bindings between form fields and their data models.

type FormFields = {
  username: string;
  email: string;
};

function renderField<K extends keyof FormFields>(field: K, value: FormFields[K]) {
  return `<input name="${field}" value="${value}" />`;
}

This ensures every rendered field matches an actual property in your model.


Using keyof with Record

You can pair keyof with Record to define objects with controlled keys and consistent value types.

type Permissions = "read" | "write" | "delete";
type RolePermissions = Record<Permissions, boolean>;

const admin: RolePermissions = {
  read: true,
  write: true,
  delete: true
};

You can also generate the Permissions type from keyof SomeType for more dynamic use.


Summary

The keyof operator is a core building block in TypeScript’s type system. It gives you access to the keys of an object or interface, allowing you to write more reusable, flexible, and type-safe code.

Use it for filtering keys, building utility types, accessing dynamic properties, or constraining generic parameters. Combined with typeof, Record, Pick, and conditional types, keyof unlocks advanced capabilities that make your TypeScript code cleaner and more robust.

Learn TypeScript for Free
Start learning now
button icon
To advance beyond this tutorial and learn TypeScript by doing, try the interactive experience of Mimo. Whether you're starting from scratch or brushing up your coding skills, Mimo helps you take your coding journey above and beyond.

Sign up or download Mimo from the App Store or Google Play to enhance your programming skills and prepare for a career in tech.

You can code, too.

© 2025 Mimo GmbH

Reach your coding goals faster