如何通过Babel在JavaScript类注解中保留类属性列表?
如何通过Babel在注解中获取类的属性列表?
可以做到,类的实例属性(比如示例中的property = "hello")在原生JavaScript运行时不会直接暴露在类本身,需要借助Babel插件在编译阶段收集属性信息,并传递给装饰器(注解)使用。
具体实现步骤
配置Babel基础插件
先安装处理装饰器和类属性的必要依赖:npm install @babel/core @babel/plugin-proposal-decorators @babel/plugin-proposal-class-properties --save-dev然后在
babel.config.json中启用插件:{ "plugins": [ ["@babel/plugin-proposal-decorators", { "legacy": true }], ["@babel/plugin-proposal-class-properties", { "loose": true }] ] }这里启用
legacy模式是为了兼容常见的装饰器使用方式,loose模式让类属性编译后更易被收集。编写自定义Babel插件收集类属性
这个插件会在编译时遍历类的属性节点,收集属性名后注入到装饰器的参数中:// your-custom-plugin.js module.exports = function() { return { visitor: { ClassDeclaration(path) { const classProps = []; // 遍历类体,收集所有实例属性名 path.node.body.body.forEach(node => { if (node.type === 'ClassProperty') { classProps.push(node.key.name); } }); // 找到类上的装饰器,注入属性列表 const decorators = path.node.decorators; if (decorators?.length) { decorators.forEach(decorator => { if (decorator.expression.type === 'CallExpression') { // 给装饰器调用添加属性列表参数 decorator.expression.arguments.push({ type: 'ArrayExpression', elements: classProps.map(name => ({ type: 'StringLiteral', value: name })) }); } }); } } } }; };将自定义插件加入Babel配置:
{ "plugins": [ "./your-custom-plugin.js", ["@babel/plugin-proposal-decorators", { "legacy": true }], ["@babel/plugin-proposal-class-properties", { "loose": true }] ] }修改装饰器接收属性列表
现在装饰器可以拿到额外传入的属性列表参数:const anno = function () { return function (Class, descriptor, properties) { console.log('类的属性列表:', properties); // 输出: ["property"] return Class; } }; @anno() class App { property = "hello"; }
注意事项
- 装饰器的参数顺序会受Babel装饰器模式影响,
legacy模式和新规范模式的参数结构不同,需要根据实际测试调整。 - 若要收集静态属性,只需在插件中判断
node.static属性即可。
内容的提问来源于stack exchange,提问作者dooxe
相关产品推荐
相关产品推荐

