Vue框架TypeScript装饰器

栏目: 编程语言 · 发布时间: 5年前

内容简介:关键词装饰器是一种特殊类型的声明,它能够被附加到本篇先从项目的宏观角度来总结一下Decorator如何组织。

关键词 装饰器 Decorator 元编程

装饰器是一种特殊类型的声明,它能够被附加到 类声明,方法, 访问符,属性或参数 上。 装饰器使用 @expression这种形式, expression求值 后必须为一个函数,它会在 运行时被调用 ,被装饰的声明信息做为参数传入。

本篇先从项目的宏观角度来总结一下Decorator如何组织。

目录

  • 主要的Decorator依赖
    • vue-class-component
    • vuex-class
    • vue-property-decorator
    • core-decorators
  • 自定义Decorator示例
  • 哪些功能适合用Decorator实现
  • Decorator实现小Tips
  • See also

主要的Decorator依赖

vue-cli3 默认支持Decorator, 年初重写了一个design库主要依赖官方和社区提供的Decorator来实现的组件。 Decorator可以非侵入的装饰类、方法、属性,解耦业务逻辑和辅助功能逻辑。以下是主要的三方Decorator组件:

vue-class-component

get computedMsg () {return 'computed ' + this.msg}
mounted () {this.greet()}

vuex-class

让Vuex和Vue之间的绑定更清晰和可拓展

  • @State
  • @Getter
  • @Action
  • @Mutation

vue-property-decorator

这个组件完全依赖于vue-class-component.它具备以下几个属性:

  • @Component (完全继承于vue-class-component)

  • @Prop:父子组件之间值的传递

  • @Emit:子组件向父组件传递

  • @Model:双向绑定

  • @Watch:观察的表达式变动

  • @Provice:在组件嵌套层级过深时。父组件不便于向子组件传递数据。就把数据通过Provide传递下去。

  • @Inject:然后子组件通过Inject来获取

  • Mixins (在vue-class-component中定义);

core-decorators

  • @readonly
  • @autobind : TSX 回调函数中的 this,类的方法默认是不会绑定 this 的,可以使用autobind装饰器
  • @override

总结一下主要就分成这三类:

  • 修饰类的:@Component、@autobind;
  • 修饰方法的:@Emit、@Watch、@readonly、@override;
  • 修饰属性的:@Prop、@readonly;

以上引用方法等详系内容可查看官方文档。下面自定义部分来实现一个记录日志功能的装饰器。

自定义Decorator示例

  • @Logger,Logger日志装饰器通常是修饰方法,Decorater则是在 运行时就被触发了 ,日志记录是在 方法被调用时触发 ,示例中通过自动发布事件实现调用时触发。为增加日志记录的灵活性,需要通过暴露钩子函数的方式来改变日志记录的内容。

期望的日志格式

{
    "logId":"", // 事件Id
    "input":"", // 方法输入的内容
    "output":"", // 方法输出的内容
    "custom":"" // 自定义的日志内容
}
复制代码

实现

export function Logger(logId?: string, hander?: Function) {
    const loggerInfo =Object.seal({logId:logId, input:'',output:'', custom: ''});
    const channelName = '__logger';
    const msgChannel = postal.channel(channelName);
    msgChannel.subscribe(logId, logData => {
        // 根据业务逻辑来处理日志
        console.log(logData);
    });

    return function (target: any,
        key: string,
        descriptor: TypedPropertyDescriptor<any>): TypedPropertyDescriptor<any> {
            const oldValue = descriptor.value
            descriptor.value = function () {
                const args: Array<any> = [];
                for (let index in arguments) {
                args.push(arguments[index]);
                }
                loggerInfo.input = `${key}(${args.join(',')})`;
                // 执行原方法
                const value = oldValue.apply(this, arguments);
                loggerInfo.output = value;
                hander && (loggerInfo.custom = hander(loggerInfo.input, loggerInfo.output) || '');
                // 被调用时,会自动发出一个事件
                msgChannel.publish(logId, loggerInfo);
            }
            return descriptor
    }
}
复制代码

使用

@Logger('event_get_detial1')
getDetial(id?: string, category?: string) {
    return "详细内容";
}
// 或者
@Logger('event_get_detial2', (input, output) => {
        return '我是自定义内容';
})
getDetial2(id?: string, category?: string) {
    return "详细内容";
}
...
<button @click="getDetial2('1000', 'a')">获取详情</button>
复制代码

效果: {logId: "event_get_detial2", input: "getDetial(1000,a)", output: "详细内容", custom: "我是自定义内容"} , 每次点击按钮都会触发一次。

TODO: 这里还需要对输入参数和输出参数中的引用数据类型做处理。

同时还需要掌握: 装饰器工厂、装饰器组合、装饰器求值、参数装饰器、元数据

哪些功能适合用Decorator实现

  • 官网和社区提供的这些Decorator, 可以作为自己框架的底层设计。
  • 日志功能全局都得用,调用方法基本一致,是最适合使用装饰器来实现,并且每个项目的日志记录各有差异,最适合自定义这部分。

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持 码农网

查看所有标签

猜你喜欢:

本站部分资源来源于网络,本站转载出于传递更多信息之目的,版权归原作者或者来源机构所有,如转载稿涉及版权问题,请联系我们

鸟哥的Linux私房菜 基础学习篇(第二版)

鸟哥的Linux私房菜 基础学习篇(第二版)

鸟哥 / 人民邮电出版社 / 2007-9 / 65.00元

《鸟哥的Linux私房菜基础学习篇(第二版)》全面而详细地介绍了Linux操作系统。全书分为5个部分:第一部分着重说明Linux的起源及功能,如何规划和安装Linux主机;第二部分介绍Linux的文件系统、文件、目录与磁盘的管理;第三部分介绍文字模式接口shell和管理系统的好帮手shell脚本,另外还介绍了文字编辑器vi和vim的使用方法;第四部分介绍了对于系统安全非常重要的Linux账号的管理......一起来看看 《鸟哥的Linux私房菜 基础学习篇(第二版)》 这本书的介绍吧!

HTML 编码/解码
HTML 编码/解码

HTML 编码/解码

Markdown 在线编辑器
Markdown 在线编辑器

Markdown 在线编辑器

UNIX 时间戳转换
UNIX 时间戳转换

UNIX 时间戳转换