我找到了一种实现多种遗产的解决方案(实际上是级联的),但值得一看。
假设您有一个 Base 类,其中包含一些属性和方法:
class Base {
tableName = 'My table name';
hello(name) {
return `hello ${name}`;
}
}
你想要一个类来扩展 Base 但你也定义了一些你想要重用的属性。为此将执行以下功能:
type Constructor<T = {}> = new (...args: any[]) => T;
function UserFields<TBase extends Constructor>(Base: TBase) {
return class extends Base {
name: string;
email: string;
};
}
现在我们可以做一个扩展 Base 和扩展 UserFields 的类,打字稿语言服务将从这两个类中找到属性。它模拟了多重遗产,但它实际上是一个级联。
class User extends UserFields(Base) { }
const u = new User();
u.tableName = 'users'; // ok
u.name = 'John'; // ok
通过这种方式,您可以将 UserFields 函数与任何其他类一起使用。一个明显的例子是,如果您想在客户端将 User 对象公开为“干净”对象并具有可用字段,然后您有一个 UserDb 对象与数据库连接,并且任何其他服务器端方法都可以具有相同的字段也。我们只定义一次数据库字段!
另一件好事是您可以链接 mixin mixin1(mixin2....(Base)) 以在同一个类中拥有尽可能多的属性。
每个人都希望装饰器属性可以被打字稿看到,但同时也是一个很好的解决方案。