Empresas
Empregos
  • Sobre nós
  • Soluções
    • Publicação de vagas
      Publique sua vaga e receba candidatos qualificados em 48h.
    • Avaliações de candidatos
      Mais de 500 testes técnicos e psicológicos, mais anti-fraude.
    • Headhunting
      Busca executiva personalizada do início ao fim.
    • Folha de Pagamento + EOR
      Dispersão de folha e EOR em mais de 15 países da LATAM.
  • Preços
  • Empregos

0

179
Visualizações
How to restrict array items using union type with TypeScript?

There is some event type: For example,

interface Event {
  type: 'a' | 'b' | 'c';
  value: string;
}

interface App {
  elements: Event[];
}

It's not bad, but I could do the following thing:

const app: App = {
  elements: [
    { type: 'a', value: '1' },
    { type: 'a', value: '2' },
  ],
}

But I need that elements array contains objects with uniq type (only one item with type 'a', only one item with type 'b', etc). How could I do it in TypeScript? Thanks in advance!

about 4 years ago · Juan Pablo Isaza
2 Respostas
Responde à pergunta

0

You might be able to adapt this answer to your situation (your union would be of distinct SomeEvent types, which you can generate from your existing type). It's complicated and I couldn't do it in the time I gave it, but it may be possible.

It would simpler, though, to use an object instead of an array, keyed by the type: elements: {a: { value: "1" } }. (If you need to get an array from it at some point, you can always use Object.values(theApp.elements) to get it, but you can easily loop through objects, not just arrays.)

interface SomeEvent {
  type: 'a' | 'b' | 'c';
  value: string;
}

interface App {
  elements: Partial<{
    [key in SomeEvent["type"]]: Omit<SomeEvent, "type"> & { type: key};
  }>
}

That uses the type as an object key, and requires the object assigned to it to have the same value as typd. (I used the name SomeEvent instead of Event to avoid confusing with DOM events.)

Then this works:

const app1: App = {
  elements: {
    a: { type: 'a', value: '1' },
    b: { type: 'b', value: '2' },
  },
};

but this has an error as desired:

const app2: App = {
  elements: {
    a: { type: 'a', value: '1' },
    a: { type: 'a', value: '2' }, // An object literal cannot have multiple properties with the same name in strict mode.
  },
};

Playground link

about 4 years ago · Juan Pablo Isaza Relatório

0

one way can be to create an interface for Event with different type a, b or c

you can create an interface that will say your elements property can have one instance of each type

interface EventFilter {
  elements: [EventA?, EventB?, EventC?];
}

The limitation of this solution is that element should be added in the order defined in EventFilter

interface Event {
  type: 'a' | 'b' | 'c';
  value: string;
}

interface EventA extends Event {
  type: 'a';
}

interface EventB extends Event {
  type: 'b';
}

interface EventC extends Event {
  type: 'c';
}

interface EventFilter {
  elements: [EventA?, EventB?, EventC?];
}

const app: EventFilter = {
  elements: [ 
    { type: 'a', value: '1' },
    { type: 'b', value: '1' } 
  ],
}

unfortunately, you will have to list all authorised combine to be able to have a flexible array with element in any order

interface EventFilter {
  elements: [EventA?, EventB?, EventC?] | [EventA?, EventC?, EventB?] 
            | [EventB?, EventA?, EventC?] | [EventB?, EventC?, EventA?]
            | [EventC?, EventA?, EventB?] | [EventC?, EventB?, EventA?];
}

const app: EventFilter = {
  elements: [ 
    { type: 'c', value: '1' },
    { type: 'a', value: '1' },
  ],
}
about 4 years ago · Juan Pablo Isaza Relatório
Responde à pergunta
Encontrar trabalhos remotos

Descubra a nova forma de encontrar um emprego!

melhores empregos
Principais categorias de trabalho
Empresas
Postar vaga Preços Comercial
Jurídico
Termos e Condições Política de privacidade
© 2026 PeakU Inc. All Rights Reserved.
Andres GPT
Recomende algumas ofertas para mim
Preciso de ajuda