digitando - Há uma maneira de "extrair" o tipo de uma propriedade de interface do TypeScript?
Vamos supor que haja um arquivo de tipagem para a biblioteca X que inclui algumas interfaces.
interface I1 {
x: any;
}
interface I2 {
y: {
a: I1,
b: I1,
c: I1
}
z: any
}
Para trabalhar com esta biblioteca, preciso passar um objeto que seja exatamente do mesmo tipo que I2.y. Posso, é claro, criar uma interface idêntica nos meus arquivos de origem:
interface MyInterface {
a: I1,
b: I1,
c: I1
}
let myVar: MyInterface;
mas então eu fico com o ônus de mantê-lo atualizado com o da biblioteca, além disso, ele pode ser muito grande e resultar em muita duplicação de código.
Portanto, existe alguma maneira de "extrair" o tipo desta propriedade específica da interface? Algo semelhante a let myVar: typeof I2.y (o que não funciona e resulta no erro "Cannot find name I2").
Editar: depois de brincar um pouco no TS Playground, percebi que o código a seguir consegue exatamente o que eu quero:
declare var x: I2;
let y: typeof x.y;
No entanto, isso requer que uma variável redundante x seja declarada. Estou procurando uma maneira de conseguir isso sem essa declaração.
Resposta #1
Não era possível antes, mas felizmente agora é, desde a versão 2.1 do TypeScript. Ela foi lançada em 7 de dezembro de 2016 e introduz tipos de acesso indexado, também chamados de tipos de consulta.
A sintaxe se parece com o acesso a elementos, mas é escrita no lugar dos tipos. Então, no seu caso:
interface I1 {
x: any;
}
interface I2 {
y: {
a: I1,
b: I1,
c: I1
}
z: any
}
let myVar: I2['y']; // indexed access type
Agora myVar tem o tipo de I2.y.
Confira no TypeScript Playground.
Resposta #2
Para expandir a resposta aceita, você também pode atribuir o tipo usando a palavra-chave type e usá-lo em outros lugares.
// Some obscure library
interface A {
prop: {
name: string;
age: number;
}
}
// Your helper type
type A_Prop = A['prop']
// Usage
const myThing: A_prop = { name: 'June', age: 29 };
Resposta #3
Apenas um exemplo de extração de um tipo literal do tipo de objeto união:
type Config = {
key: "start_time",
value: number,
} | {
key: "currency",
value: string,
}
export type ConfigKey = Config["key"];
// "start_time"|"currency"
Resposta #4
keyof Colors retornará uma lista de todas as chaves "white" | "black". Quando essa lista de chaves é passada para a interface Colors, o tipo será todos os valores das chaves fornecidas, "#fff" | #000.
interface Colors {
white: "#fff"
black: "#000"
}
type ColorValues = Colors[keyof Colors]
// ColorValues = "#fff" | "#000"
