最新消息:雨落星辰是一个专注网站SEO优化、网站SEO诊断、搜索引擎研究、网络营销推广、网站策划运营及站长类的自媒体原创博客

javascript - Get properties of class in typescript - Stack Overflow

programmeradmin7浏览0评论

I've the following class:

export class Test {

        private _rowsCount: string;
        public get RowsCount(): string {
            return this._rowsCount;
        };
        public set RowsCount(value: string) {
            this._rowsCount = value;
        };

        private _rowsCount2: string;
        public get RowsCount2(): string {
            return this._rowsCount2;
        };
        public set RowsCount2(value: string) {
            this._rowsCount2 = value;
        };
    }

I need to iterate over the properties in a specific class, I tried the following:

Object.keys(this).forEach((key)=> {
    console.log(key);
});

But the problem that this iterate just over the private fields, I tried also the following I got all the methods and properties:

    for (var property in this) {
        if (this.hasOwnProperty(property)) {
            console.log(property);                
        }
    }

Does anyone have a solution?

Thanks!

I've the following class:

export class Test {

        private _rowsCount: string;
        public get RowsCount(): string {
            return this._rowsCount;
        };
        public set RowsCount(value: string) {
            this._rowsCount = value;
        };

        private _rowsCount2: string;
        public get RowsCount2(): string {
            return this._rowsCount2;
        };
        public set RowsCount2(value: string) {
            this._rowsCount2 = value;
        };
    }

I need to iterate over the properties in a specific class, I tried the following:

Object.keys(this).forEach((key)=> {
    console.log(key);
});

But the problem that this iterate just over the private fields, I tried also the following I got all the methods and properties:

    for (var property in this) {
        if (this.hasOwnProperty(property)) {
            console.log(property);                
        }
    }

Does anyone have a solution?

Thanks!

Share Improve this question asked Jan 31, 2017 at 14:02 Ramzy AbourafehRamzy Abourafeh 1,1957 gold badges18 silver badges35 bronze badges 6
  • 1 The for/in loop gave you all of them, that's not what you're after? What are you trying to get? – Nitzan Tomer Commented Jan 31, 2017 at 14:12
  • The for/in gave also the methods and the constructor if exist!, and I don't want those, I need just the public properties! – Ramzy Abourafeh Commented Feb 1, 2017 at 9:14
  • By "properties" you mean getters/setters only? Or members as well? You need to be more precise about what you're asking as it isn't clear at all. – Nitzan Tomer Commented Feb 1, 2017 at 9:22
  • I need to get only the getters/setters. – Ramzy Abourafeh Commented Feb 1, 2017 at 9:24
  • Possible duplicate of Get functions (methods) of a class – Bruno Grieder Commented Feb 1, 2017 at 11:01
 |  Show 1 more ment

2 Answers 2

Reset to default 11

If you need to only get the getters/setters, then you'll need to do something like:

class Test {
    ...

    public static getGetters(): string[] {
        return Object.keys(this.prototype).filter(name => {
            return typeof Object.getOwnPropertyDescriptor(this.prototype, name)["get"] === "function"
        });
    }

    public static getSetters(): string[] {
        return Object.keys(this.prototype).filter(name => {
            return typeof Object.getOwnPropertyDescriptor(this.prototype, name)["set"] === "function"
        });
    }
}

Test.getGetters(); // ["RowsCount", "RowsCount2"]
Test.getSetters(); // ["RowsCount", "RowsCount2"]

(code in playground)


You can put the static methods in a base class, and then when you extend it the subclass will have those static methods as well:

class Base {
    public static getGetters(): string[] {
        return Object.keys(this.prototype).filter(name => {
            return typeof Object.getOwnPropertyDescriptor(this.prototype, name)["get"] === "function"
        });
    }

    public static getSetters(): string[] {
        return Object.keys(this.prototype).filter(name => {
            return typeof Object.getOwnPropertyDescriptor(this.prototype, name)["set"] === "function"
        });
    }
}

class Test extends Base {
   ...
}

Test.getGetters(); // work the same

(code in playground)

If you want these methods to be instance methods then you can do this:

class Base {
    public getGetters(): string[] {
        return Object.keys(this.constructor.prototype).filter(name => {
            return typeof Object.getOwnPropertyDescriptor(this.constructor.prototype, name)["get"] === "function"
        });
    }

    public getSetters(): string[] {
        return Object.keys(this.constructor.prototype).filter(name => {
            return typeof Object.getOwnPropertyDescriptor(this.constructor.prototype, name)["set"] === "function"
        });
    }
}

The change is that instead of using this.prototype you're using this.constructor.prototype.
Then you simply:

let a = new Test();
a.getGetters(); // ["RowsCount", "RowsCount2"]

(code in playground)


Edit

Based on a ment by @Twois, who pointed out that it won't work when targetting es6, here's a version that will work:

class Base {
    public static getGetters(): string[] {
        return Reflect.ownKeys(this.prototype).filter(name => {
            return typeof Reflect.getOwnPropertyDescriptor(this.prototype, name)["get"] === "function";
        }) as string[];
    }

    public static getSetters(): string[] {
        return Reflect.ownKeys(this.prototype).filter(name => {
            return typeof Reflect.getOwnPropertyDescriptor(this.prototype, name)["set"] === "function";
        }) as string[];
    }
}

The main difference: using Reflect.ownKeys(this.prototype) instead of Object.keys(this.prototype).

What you can do is for the class you want to use it extend the class above and make the properties public for this reason;

   class TestExposed extend Test {
      public _rowsCount: string;
      public _rowsCount2: string; 
   }

And in your Test class make the private protected:

class Test {
    protected _rowsCount: string;
    public get RowsCount(): string {
        return this._rowsCount;
    };
    public set RowsCount(value: string) {
        this._rowsCount = value;
    };

    protected _rowsCount2: string;
    public get RowsCount2(): string {
        return this._rowsCount2;
    };
    public set RowsCount2(value: string) {
        this._rowsCount2 = value;
    };
}

Then you should be able to iterate over the properties in an external class;

But if you want to have the values; Why not make a function that exposes the values by returning them in an array or log them as a string;

发布评论

评论列表(0)

  1. 暂无评论