Is it possible to create dynamic getters/setters in typescript?

Viewed 15376

I'm new in typescript, and I'm trying to rewrite our application from es2016 to TypeScript. My task is to have a class with data property and make each element from data object available as class property.

I get stuck on this JavaScript code:

for(let key in this.data) {
  Object.defineProperty(this, key, {
    get: function(value:any) { return this.data[key]; },
    set: function(value:any) {
      if (this.data[key] !== value) {
        this.data[key] = value;
        this.updatedKeys.push(key);
      }
    },
  });
}

It is pretty easy to use getter/setters for typescript, but i get confused if i can create them dynamically?

interface IData {
  id: number;
  [propName: string]: any;
}

class Model  {
  
  protected updatedKeys:string[] = [];
  
  baseUrl:string = null;
  data:IData;
  fields:IData;
  
  constructor(data:IData={id:null}, fields:IData={id:null}) {
    super();
    this.data = data;
    this.fields = fields;
    
    for(let key in this.data) {
      Object.defineProperty(this, key, {
        get: function(value:any) { return this.data[key]; },
        set: function(value:any) {
          if (this.data[key] !== value) {
            this.data[key] = value;
            this.updatedKeys.push(key);
          }
        },
      });
    }
  }
}

tsc -t ES2016 --lib "es2016","dom" models.ts

will give this error:

models.ts(33,40): error TS2345: Argument of type '{ get: (value: any) => any; set: (value: any) => void; }' is not assignable to parameter of type 'PropertyDescriptor & ThisType<any>'.
  Type '{ get: (value: any) => any; set: (value: any) => void; }' is not assignable to type 'PropertyDescriptor'.
    Types of property 'get' are incompatible.
      Type '(value: any) => any' is not assignable to type '() => any'.

And I don't know how to get rid of this problem.

2 Answers
Related