Generi c возвращаемый тип при преобразовании объекта - PullRequest
1 голос
/ 27 мая 2020

У меня есть функция, которая принимает объект и возвращает новый с дополнительными свойствами. И я не могу понять, почему эта общая c типизация не работает.

const obj = { name: 'hello', id: 1 };

const transformObj = <T extends { name: string }>({ name, ...rest }: T): T & { newName: string } => ({
    name,
    newName: name + '1',
    ...rest,
});

Ссылка на игровую площадку

Она возвращает эту ошибку

Type '{ name: string; newName: string; } & Pick<T, Exclude<keyof T, "name">>' is not assignable to type 'T & { newName: string; }'. Type '{ name: string; newName: string; } & Pick<T, Exclude<keyof T, "name">>' is not assignable to type 'T'. '{ name: string; newName: string; } & Pick<T, Exclude<keyof T, "name">>' is assignable to the constraint of type 'T', but 'T' could be instantiated with a different subtype of constraint '{ name: string; }'.

1 Ответ

1 голос
/ 27 мая 2020

Вот почему это не работает так, как написано. Обратите внимание на { newName: number } в obj. Этот объект действительно соответствует ограничению <T extends { name: string }>, но попытка пересечь его с { newName: string } создает противоречие.

const obj = { name: 'hello', /**/ newName: 10 /**/, id: 1 };

Это дает вам нужный тип, удаляя "newName" из keyof rest с помощью деструктурирование, а затем добавление его обратно как string.

const transformObj = <T extends { name: string, newName?: unknown }>({ name, newName, ...rest }: T): typeof rest & { name: string, newName: string } => ({
    ...rest,    
    name,
    newName: name + '1',
});
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...