Hvordan dyp-flate et grensesnitt i Typescript?


for eksempel:

interface a {
  name: string 
  nested: {
    lastName: string 
    nested: {
      age: number
    }
  }
}

Jeg vil at det skal bli:

interface b {
  name: string 
  lastName: string 
  age: number
}

grensesnittverdier vil være dynamiske, så jeg trenger sannsynligvis en slags rekursiv løsning på dette

Jeg endte bare opp med endelige løsninger

Svar #1

Her er en løsning som bruker kartlagte og betingede typer: FlattenPairs konstruerer en union av par som ['name', string] | ['lastName', string] | ['age', number], deretter konverterer Flatten dette til en objekttype. Jeg antok at de nestede egenskapene ikke nødvendigvis alle heter nested (og nødvendigvis ikke har forutsigbare egenskapsnavn), så typen Primitive er nødvendig som basissak for rekursjonen.

type Primitive = string | number | boolean
type FlattenPairs<T> = {[K in keyof T]: T[K] extends Primitive ? [K, T[K]] : FlattenPairs<T[K]>}[keyof T] & [PropertyKey, Primitive]
type Flatten<T> = {[P in FlattenPairs<T> as P[0]]: P[1]}

Eksempel :

interface TestInterface {
  name: string 
  nested: {
    lastName: string 
    nested: {
      age: number
    }
  }
}

// {age: number, lastName: string, name: string}
type Test = Flatten<TestInterface>

Lekeromlenke

Hjelpertypen FlattenPairs kan skrives på en litt enklere måte hvis de nestede egenskapsnavnene er kjent:

type FlattenPairs<T> = {[K in keyof T]: K extends 'nested' ? FlattenPairs<T[K]> : [K, T[K]]}[keyof T]

Lekeromlenke

Relaterte artikler