我有一个带有代理的类,如下所示:
export class Row<T extends ModelItems> {
private _row: T = <T>{}
public constructor(rowItems?: T) {
if (rowItems) { this._row = rowItems }
return new Proxy(this, {
get: function (target, prop) {
return (<any>target)[prop] || target._row[prop] || ''
}
/* set(): snipped */
}
}
当我这样做时:
interface User {
id: number
first: string
last: string
username: string
}
let row = new Row<User>({/* My object */})
如何获取它,以便在输入 row
时获得在 User
界面中定义的项目列表。现在所有建议的都是对象根中的实际方法/属性。
我已经尝试过这个:
export interface Row<T extends ModelItems> {
[key: string]: T
}
然而,除了告诉我我的方法没有正确定义之外,这似乎没有任何帮助
最佳答案
看起来您想要 Row<T>
的实例也成为T
本身;是对的吗? TypeScript 不会让你做类似 class Row<T> implements T
的事情,它本身也不会轻易推断出这一点。相反,您可以执行如下操作:
export class _Row<T> {
// ... your definition above
}
// Row type alias
export type Row<T extends ModelItems> = _Row<T> & T;
// Row value alias
export const Row = _Row as {
new <T>(rowItems?: T): Row<T>
prototype: _Row<{}>
}
这在运行时的行为或多或少相同,但现在 TypeScript 将理解 Row<T>
的实例具有 T
的所有属性有:
declare const u: User;
let row = new Row(u); // inferred as Row<User>
row.username // string
<小时/>
如果您试图表示不同的东西,例如 Row<T>
其行为类似于具有 T
的所有键的东西但对于可能为空字符串的属性,您可以替换 // Row type alias
用这个代替:
// Row type alias
export type Row<T extends ModelItems> = _Row<T> &
{[K in keyof T]: T[K] | ''};
并验证它的行为是否符合您的预期:
declare const u: User;
let row = new Row(u); // inferred as Row<User>
row.id // number || ''
<小时/>
希望有帮助;祝你好运!
关于javascript - 如何使用代理定义属性,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/47955506/