TypeScript and Haskell: Unions & Singletons

Gabriel Garcia · December 14, 2024

I like TypeScript's type system. In particular, I like the combination of Union Types (aka anonymous Sum Types) and Literal Types (aka Singleton Types).

Those features allow us to achieve API precision, while also minding conciseness:

// Not very precise
type Result = {
  ok: boolean;
  error?: string;
  userRole?: string;
  avatarSize?: number;
};

// Much more precise
type Result =
  | { ok: false; error: string }
  | { ok: true; userRole: "ADMIN" | "GUEST"; avatarSize: 96 | 128 | 512 };

Let's compare that to Haskell without any language extensions:

data Result =
  ResultError { resultError :: String }
  | ResultOk { resultUserRole :: UserRole, resultAvatarSize :: AvatarSize }

data UserRole = UserRoleAdmin | UserRoleGuest

data AvatarSize = AvatarSize96 | AvatarSize128 | AvatarSize512