如何获取 public fields/properties 名称的数组?

How to get array of public fields/properties names?

说我有打字稿class:

class Person
{
    constructor(public readonly firstName: string, public readonly lastName: string, public readonly id: number)
    {

    }
}

我想使用一些通用函数列出给定 class 的所有 public 属性。

所以假设的 getAllPublicProps<...> 会像这样使用:

const allPublicProps: (keyof Person)[] = getAllPublicProps<Person>() ;

和 return 等价于 ['firstName'、'lastName'、'id'].

的字符串数组

在不知道您的确切用例的情况下,很难给您一个具体的答案。 但我会尝试:)

由于 TypeScript 的类型注释仅在编译时可用,运行 时不可用,因此编译时的属性之间不再存在真正的区别。例如:

class Person {
    private secret = '123';
    constructor(
        public readonly firstName: string,
        public readonly lastName: string,
        public readonly id: number
    ) { }
}

将编译为

var Person = (function () {
    function Person(firstName, lastName, id) {
        this.firstName = firstName;
        this.lastName = lastName;
        this.id = id;
        this.secret = '123';
    }
    return Person;
}());

此外,虽然 type PersonProperties = keyof Person 会为您提供所有 public 属性的字符串文字类型,但您不能使用此类型来过滤任何内容,因为它只是一个注解。所以你只能使用 PersonProperties 作为函数签名。

我猜你可以使用 Reflect,但这将包括对 public 属性进行硬编码。此外,Angular 的编译器正在滥用 TS 编译器来编写在编译期间可用的元数据。我现在不知道是否有任何与框架无关的库可以做同样的事情。

如果你能接受一些丑陋的东西,比如实例化 class 并接受它不会理解私有属性和 public 属性之间的区别(除非你以某种方式对其进行编码),这是有可能的).

假设您有 class

class Person {
  constructor(public readonly firstName: string, 
              public readonly lastName: string,
              public readonly id: number,
              private readonly _secret: number) {}
}

你可以写一个util方法

class Util {
  static getProperties(obj: any): string[] {
    const result = [];
    for (let property in obj) {
      if (obj.hasOwnProperty(property) && !property.startsWith('_')) {
        result.push(property);
      }
    }
    return result;
  }
}

并使用它

const allProperties = Util.getProperties(new Person());