我希望能够将对象属性分配给给定键和值作为输入的值,但仍然能够确定值的类型。这有点难以解释,所以这段代码应该可以揭示问题:
type JWT = { id: string, token: string, expire: Date };
const obj: JWT = { id: 'abc123', token: 'tk01', expire: new Date(2018, 2, 14) };
function print(key: keyof JWT) {
switch (key) {
case 'id':
case 'token':
console.log(obj[key].toUpperCase());
break;
case 'expire':
console.log(obj[key].toISOString());
break;
}
}
function onChange(key: keyof JWT, value: any) {
switch (key) {
case 'id':
case 'token':
obj[key] = value + ' (assigned)';
break;
case 'expire':
obj[key] = value;
break;
}
}
print('id');
print('expire');
onChange('id', 'def456');
onChange('expire', new Date(2018, 3, 14));
print('id');
print('expire');
onChange('expire', 1337); // should fail here at compile time
print('expire'); // actually fails here at run time
我尝试将 value: any
更改为 value: valueof JWT
但这没有用。
理想情况下, onChange('expire', 1337)
会失败,因为 1337
不是 Date 类型。
如何将 value: any
更改为给定键的值?
原文由 styfle 发布,翻译遵循 CC BY-SA 4.0 许可协议
更新:看起来问题标题吸引了人们寻找所有可能的属性值类型的联合,类似于
keyof
为您提供所有可能的属性键类型的联合的方式。让我们先帮助那些人。您可以制作一个ValueOf
类似于keyof
,方法是使用keyof T
作为键的 索引访问类型,如下所示:这给了你
对于上述问题,您可以使用比
keyof T
更窄的单个键来仅提取您关心的值类型:为了确保键/值对在函数中正确“匹配”,您应该使用 泛型 以及索引访问类型,如下所示:
这个想法是
key
参数允许编译器推断通用K
参数。然后它要求value
匹配JWT[K]
,您需要的索引访问类型。