Convert Slack Events API JSON to TypeScript

Use json to typescript to model the Slack Events API envelope. Discriminated union over event subtypes with shared metadata fields.

Real-World API Schemas

Detailed Explanation

The Slack Events Envelope

Slack wraps every event in a fixed outer envelope (token, team_id, event) and discriminates the inner event object by a type literal — message, reaction_added, app_mention, and many more.

Example JSON

{
  "token": "xxxx",
  "team_id": "T01ABCD",
  "api_app_id": "A09EFGH",
  "type": "event_callback",
  "event_id": "Ev08JKLMN",
  "event_time": 1717000000,
  "event": {
    "type": "message",
    "channel": "C03ABCDEF",
    "user": "U02XYZ123",
    "text": "Hello world",
    "ts": "1717000000.000200"
  }
}

Generated TypeScript

interface MessageEvent {
  type: "message";
  channel: string;
  user: string;
  text: string;
  ts: string;            // Slack timestamps are strings, not numbers
  thread_ts?: string;
}

interface ReactionAddedEvent {
  type: "reaction_added";
  user: string;
  reaction: string;
  item: { type: "message"; channel: string; ts: string };
  event_ts: string;
}

interface AppMentionEvent {
  type: "app_mention";
  user: string;
  text: string;
  ts: string;
  channel: string;
}

type SlackEvent = MessageEvent | ReactionAddedEvent | AppMentionEvent;

interface EventCallback {
  token: string;
  team_id: string;
  api_app_id: string;
  type: "event_callback";
  event_id: string;
  event_time: number;
  event: SlackEvent;
}

Slack-Specific Conversion Rules

  • ts is always a string like "1717000000.000200", never a number. The fractional part is the message ID within a second.
  • The outer type is "event_callback" for normal events and "url_verification" during setup — model both as a discriminated union at the top level.
  • thread_ts only appears in threaded messages, so mark it optional rather than nullable.
  • The event discriminator has dozens of variants. Generate types only for the ones your bot actually subscribes to and add a fallback { type: string } for unknown events.

A typed Slack event union turns your event handler into a switch with exhaustive checking, which is far safer than the loose event.text access common in tutorials.

Use Case

Building a Slack bot in Next.js where the webhook handler must dispatch on event subtype with no chance of accessing fields that do not exist on a particular event variant.

Try It — JSON to TypeScript

Open full tool