Ich möchte einen Untertyp aus einer Schnittstelle in Typoskript wie unten extrahieren
interface components {
schemas: {
a: {
b?: Array<{
c?: {
d?: string;
};
}>;
};
}
// I want to export
export type custom = components["schemas"]["a"]["b"][number]["c"]
Ich bekomme jedoch einen Fehler beim [number]
SagenType '{ c?: { d?: string | undefined; } | undefined; }[] | undefined' has no matching index signature for type 'number'.ts(2537)
Wie erreichen wir das?
Lösung des Problems
Hier ist, was ich herausgefunden habe:
type Increment<A extends number[]> = [...A, 0];
type DeepRequired<T, D extends number = -1, R extends number[] = []> =
T extends object? R["length"] extends D? T: {
[K in keyof T]-?: DeepRequired<T[K], D, Increment<R>>;
}: T;
Betrachten wir DeepRequired
ohne die zusätzlichen Bits:
type DeepRequired<T> = T extends object? {
[K in keyof T]-?: DeepRequired<T[K]>;
}: T;
Dieser Typ ist im Kern einfach; es durchläuft einfach das gesamte Objekt und macht alle erforderlichen Eigenschaften.
Das funktioniert ohne Fehler:
type T = DeepRequired<components>["schemas"]["a"]["b"][number]["c"];
Aber Sie werden feststellen T
, dass auch die Eigenschaft „d" von erforderlich ist, was möglicherweise nicht das gewünschte Ergebnis ist. Deshalb ist es viel komplizierter; es begrenzt die Tiefe, in der es Eigenschaften erforderlich macht.
Zurück zu unserem ursprünglichen Snippet, ein Utility-Typ Increment
wird erstellt, um die Tiefe zu erhöhen, in der wir uns befinden, und die neuen Parameter für DeepRequired
enthalten die angegebene Tiefe (optional) und die aktuelle Tiefe, in der sie sich befindet.
Bevor es alle erforderlichen Eigenschaften ausführt, prüft es, ob es die angegebene Tiefe überschreitet, und wenn ja, stoppt es.
Das funktioniert jetzt wie erwartet:
type T = DeepRequired<components, 5>["schemas"]["a"]["b"][number]["c"];
Spielplatz
Keine Kommentare:
Kommentar veröffentlichen