我可以在Typescript中使用`keyof`来静态描述我想要返回的此类型的属性吗?

时间:2017-06-05 21:33:06

标签: typescript

想象一下,我有一个查询类和执行方法,如下所示:

class Query {
    name: string;
    sql: string;
} 

function execute(query: Query): any{
    let retVal = {};
    retVal[query.name] = true;
    return retVal;
}

q = new Query();
q.name = "thisIsMyQueryName";
let result = execute(q); // Returns: {thisIsMyQueryName: true}
// `typeof result` is still `any` of course, but I'd like it to be:
// {thisIsMyQueryName: boolean}

在这种情况下,我返回的对象具有基于我传入其中的类的实例的形状。显然,由于查询的“名称”在运行时可能会有所不同,因此我无法告诉编译器,因此它知道返回的对象将具有名为“thisIsMyQueryName”的属性。

然而,我认为我可以采取一些措施来使其更加静态地进行分析。我们有很多这些“查询”对象,当我们在代码中实例化它们时,我们知道它们的名字。我正在试验key of的不同咒语,我有一些很有希望的事情,但我对此并不满意。

能够做到这一点是理想的:

let q = {
   sql: "",
   queryName: {
       thisIsMyQueryName: ""
   }
}
let result = execute(q); // Returns: {thisIsMyQueryName: true}
// typeof result == {thisIsMyQueryName: boolean}

同样,我意识到我刚写的内容是不可能的,但我认为必须有一种方法以某种方式描述这些各种实例,编译器将知道返回类型具有名为{{1的属性}}

有什么想法吗?

1 个答案:

答案 0 :(得分:1)

您可以通过.queryName类型参数并在该参数上使用keyof来执行此操作:

class Query<TName> {
    queryName: TName
    sql: string;
} 
type Result<TName> = {
    [P in keyof TName]: boolean
}

function execute<TName>(query: Query<TName>): Result<TName> {
    return { [Object.keys(query.queryName)[0]]: true };
}

const q = {
    sql: "",
    queryName: {
        thisIsMyQueryName: ""
    }
};

const result = execute(q);
const b = result.thisIsMyQueryName; // boolean

Live demo

但是,您无法证明实现该功能。