Uma união discriminada (também chamada tagged union) conecta um grupo de tipos por meio de um campo discriminador comum (status, kind...), cujo valor é um literal distinto por membro. Ao fazer switch no discriminador, o TypeScript estreita para o membro correspondente — o padrão de união mais prático na modelagem de negócios.
Grupo
Restrição e Asserções de Tipos
Tipo
Tipo
Modo strict
Não necessário
ℹ️ Info O editor transpila TypeScript para JavaScript e o executa (sem verificação de tipos); veja a Saída de cada exemplo para o resultado da verificação.
📝 Sintaxe
type Result<T> =
| { status: "loading" }
| { status: "success"; data: T }
| { status: "error"; message: string };
function handle<T>(res: Result<T>) {
switch (res.status) {
case "loading": /* res: sem data */ break;
case "success": res.data; break; // estreitado para o membro success
case "error": res.message; break;
}
}
⚙️ Parâmetros
discriminant
O discriminador: cada membro deve declará-lo, com um tipo literal distinto por membro (por exemplo, "loading" / "success" / "error")
Retorno:Sem valor de retorno — uniões discriminadas são um recurso de modelagem no nível de tipo; o estreitamento é disparado por comparações switch/if no discriminador e ocorre em tempo de compilação.
▶ Exemplo
Edite o código abaixo e clique em Testar para ver o resultado transpilado:
Saída:
loading…
got 3 items
error: timeout
(Saída de execução após a transpilação; res.data passa na verificação de tipos no ramo success graças ao estreitamento pelo discriminador — garantido estaticamente pelo tsc, em tempo de execução existem apenas os valores)
ℹ️ Info O nome do discriminador fica a seu critério — type, kind, status, state e tag são comuns; o que importa é um valor literal distinto por membro, para que o TS possa identificá-lo de forma única.
⚠️ Atenção O discriminador precisa ser um campo obrigatório de tipo literal. Escrever string em vez de um literal como "success", ou torná-lo opcional, destrói o poder de discriminação e o estreitamento deixa de funcionar.
💡 Dica Uniões discriminadas combinam perfeitamente com a verificação de exaustividade: depois que todos os valores do discriminador são cobertos pelo switch, adicionar um membro faz o compilador apontar cada ramo esquecido (use assertNever — veja a entrada exhaustive-checks).
P Qual é a diferença entre uma união discriminada e uma união simples?
R Uma união simples só estreita por meio de verificações genéricas como typeof/in; uma união discriminada adiciona um discriminador literal, de modo que um único switch leva exatamente a um membro, e permite a verificação de exaustividade. Modele um discriminador sempre que puder.
P O discriminador pode estar aninhado dentro de um objeto?
R Sim — o TS estreita com discriminadores aninhados (e até elementos de array), por exemplo res.meta.state. Mas o aninhamento profundo prejudica a legibilidade; a convenção é um discriminador no nível superior.
P Um enum numérico pode servir como valor discriminador?
R Sim. Membros de enum (incluindo numéricos) são tipos literais, de modo que valores de enum distintos por membro formam uma união discriminada válida; enums de string são mais legíveis que os numéricos ao depurar.
Equipe Técnica Web-Tutorial
Uma plataforma de tutoriais mantida por diversos desenvolvedores. Cada tutorial é escrito e revisado por profissionais da área correspondente. Trabalhamos para manter nosso conteúdo preciso e confiável — se encontrar algum problema, avise-nos.