【问题标题】:Inheriting parent class attributes in Mixin在 Mixin 中继承父类属性
【发布时间】:2020-10-29 18:25:38
【问题描述】:

我正在尝试从 mixin 中的继承类访问属性

class BaseItem{
     public id:string;
     constructor(id:string) {
        this.id =id;  
     }
} 

abstract class ConfigMixin<K extends BaseItem>{
        public saveConfig() {
            const repo = getRepository(Entity);
            repo.update(
                { 
                    id: this.id // Typescript error
                },
                {
                    ...this.getConfig(),
                },
            );
        }
}

class BaseDevice extends BaseItem{
     constructor(id:string) {
        super(id);   
     }
} 
export interface BaseDevice extends ConfigMixin<BaseDevice> {}
applyMixins(BaseDevice , [ConfigMixin]);

但是我收到以下错误: TS2339:“ORCASmartLightConfig”类型上不存在属性“id”。

【问题讨论】:

    标签: typescript inheritance mixins typescript-generics


    【解决方案1】:

    我可以想到两种方法:

    1. 坚持 mixin 的严格封装。 Mixin 是自立的,不知道它们将被混合到哪里。这意味着一个 mixin 不应该知道它已经被混合到一个类中有一个id 字段:
    // The first approach sticks to the strict encapsulation of mixins
    export abstract class ConfigMixin {
      // Your mixin will receive all the things it needs as parameters
      // so every time you call saveConfig you need to pass the id
      public saveConfig(id: string) {
        console.log(id);
      }
    }
    
    // The base class
    class BaseItem {
      constructor(public id: string) {}
    }
    
    // An implementation of subclass of BaseItem
    export class BaseDevice extends BaseItem {}
    
    // Here we tell TypeScript that BaseDevice has ConfigMixin mixed in
    export interface BaseDevice extends ConfigMixin {}
    
    // And finally we apply the ConfigMixin
    applyMixins(BaseDevice, [ConfigMixin]);
    

    Link to TypeScript playground

    1. Trick TypeScript!在这种情况下,生成的代码更类似于您的原始方法,但它有一个缺点:
    // The second approach makes use of an abstract class field
    export abstract class ConfigMixin {
      public abstract id: string;
    
      public saveConfig() {
        console.log(this.id);
      }
    }
    
    // The base class
    class BaseItem {
      constructor(public id: string) {}
    }
    
    // An implementation of subclass of BaseItem
    export class BaseDevice extends BaseItem {}
    
    // Here we tell TypeScript that BaseDevice has ConfigMixin mixed in
    export interface BaseDevice extends ConfigMixin {}
    
    // NOW THE DRAWBACK
    //
    // Unfortunately with this approach TypeScript will not complain when
    // you are trying to mixin ConfigMixin with a class that does not have id
    export class SomeDevice {}
    export interface SomeDevice extends ConfigMixin {}
    
    // And finally we apply the ConfigMixin
    applyMixins(BaseDevice, [ConfigMixin]);
    applyMixins(SomeDevice, [ConfigMixin]);
    

    Link to TypeScript playground

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2012-05-03
      • 2020-11-08
      • 1970-01-01
      • 2021-01-25
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多