[英]TypeScript type for object whose values match its keys
Is it possible to define a TypeScript type for an object where the key values are the literal key names themselves?是否可以为 object 定义 TypeScript 类型,其中键值是文字键名本身? For example:
例如:
declare const $: SpecialGenericType
$.prop // typed as the literal value "prop"
const values = [
$.a,
$.b,
$.c
] as const
// values has the type (and value) ["a", "b", "c"]
The $
object could be implemented using a Proxy, but I'm not sure how to implement the SpecialGenericType
. $
object 可以使用代理来实现,但我不确定如何实现SpecialGenericType
。 The type would need to allow any string as a key, but the values would need to be typed as the string literal of its key name (so Record<string, string>
does not work in this case).该类型需要允许任何字符串作为键,但值需要作为键名的字符串文字输入(因此
Record<string, string>
在这种情况下不起作用)。 For example, values
above would have the tuple type ["a", "b", "c"]
.例如,上面的
values
将具有元组类型["a", "b", "c"]
。
What you're looking for is not currently possible in TypeScript.您正在寻找的内容目前在 TypeScript 中是不可能的。 It works if you have some finite union of string literal keys, but not for all of
string
.如果您有一些有限的字符串文字键联合,它会起作用,但不适用于所有
string
。 There is an open suggestion at microsoft/TypeScript#22509 asking for this exact thing (called Thing
instead of SpecialGenericType
in the description), but there hasn't been any movement.在microsoft/TypeScript#22509有一个公开的建议,要求提供这个确切的东西(在描述中称为
Thing
而不是SpecialGenericType
),但没有任何动静。 The chief language architect said首席语言架构师说
This really is a request to add compiler support for ECMAScript proxy objects, ie compiler knowledge of the relationship between property access operations and the
get
andset
proxy methods.这确实是一个为 ECMAScript 代理对象添加编译器支持的请求,即编译器了解属性访问操作与
get
和set
代理方法之间的关系。 It is simply not possible to model that with our current type system features (because nothing allows you to capture the literal type corresponding to the property name in a property access).model 根本不可能使用我们当前的类型系统功能(因为没有任何东西可以让您在属性访问中捕获与属性名称对应的文字类型)。
You might want to go to that issue and give it a or describe why you think your use case is compelling, but I doubt that it will be implemented anytime soon.您可能希望 go 解决该问题并给出或描述您认为您的用例具有吸引力的原因,但我怀疑它是否会很快实施。 Oh well, at least there's something like a definitive answer to this question, even if it is "no".
哦,好吧,至少这个问题有一个明确的答案,即使它是“否”。 Good luck!
祝你好运!
If I understand correctly, this is what you'd like:如果我理解正确,这就是您想要的:
type SpecialGenericType<T extends object> = {
[K in keyof T]: K
};
function proxify<T extends object>(source: T) {
const proxy = new Proxy(source, {
get: (_, property) => {
return property
}
});
return proxy as SpecialGenericType<T>;
}
const $ = proxify({
prop: {},
a: 'some',
b: 'random',
c: 'values',
} as const)
$.prop // typed as the literal value "prop"
const values = [
$.a,
$.b,
$.c
] as const
// values has the type (and value) ["a", "b", "c"];
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.