装饰器Decorator应用

203 阅读1分钟

前言

Decorator 是 ES7 的一个新语法,简单地说:他们是修改其他函数的功能的函数。他们有助于让我们的代码更简短,他可以通过 @方法名称 对一些对象进行装饰然后返回一个被包装过的对象,很像我们使用的callback函数一样。

Decorator 因为目前正在提案中,所以使用需要经过bebal编译,因此在vue以及react项目中可以直接使用。

vue中的使用

打印日志装饰器
  1. 定义装饰器函数
export const function log (target, name, descriptor) {
  const old = descriptor.value
	descriptor.value = function (...arg) {
		arg.map((item,index)=>console.log(`${name}函数的第${index+1}个参数:${item}`))
		const data = old.apply(this, arg)
		console.log(`${name}函数的返回值为:${data}`)
		return data
	}
}

  1. .vue文件中引入装饰器并使用
import { log } from './decorator.js'
export default {
  methods:{
    @log
    add (num1, num2) {
      return num1 + num2
    }
  }
}

运行add函数后控制台显示为

1.png

装饰器不止可以打印日志,还可以拦截修改入参出参

修改入参以及携带参数装饰器
export const formatTime = function  (type) {
	return (target, name, descriptor) => {
		const old = descriptor.value
		descriptor.value = async function (...arg) {
			for(let key in arg) {
				if(arg[key] instanceof Date) {
					arg[key] = transitionTimestamp(arg[key], type)
				}
			}
			return old.apply(this, arg)
		}
	}
}

function transitionTimestamp (val, type) {
    if (!val) return ''
    if (!type) type = 'YYYY-MM-DD HH:mm:SS'

    const date = new Date(val)
    const year = date.getFullYear()
    const month = date.getMonth() + 1 < 10 ? '0' + (date.getMonth() + 1) : date.getMonth() + 1
    const day = date.getDate() < 10 ? '0' + date.getDate() : date.getDate()
    const hour = date.getHours() * 1 < 10 ? '0' + date.getHours() : date.getHours()
    const minute = date.getMinutes() * 1 < 10 ? '0' + date.getMinutes() : date.getMinutes()
    const second = date.getSeconds() * 1 < 10 ? '0' + date.getSeconds() : date.getSeconds()

    switch (type) {
      case 'YYYY-MM-DD' :
        return year + '-' + month + '-' + day
      case 'YYYY-MM-DD HH:mm:SS' :
        return year + '-' + month + '-' + day + ' ' + hour + ':' + minute + ':' + second
			case 'YYYY-MM-DD HH:mm' :
				return year + '-' + month + '-' + day + ' ' + hour + ':' + minute
			case 'MM-DD HH:mm' :
				return month + '-' + day + ' ' + hour + ':' + minute
			case 'HH:mm:SS' :
				return hour + ':' + minute + ':' + second
			case 'HH:mm' :
				return hour + ':' + minute
			case 'MM-DD' :
				return month + '月' + day + ' '
			default :
				return year + '-' + month + '-' + day + ' ' + hour + ':' + minute
    }
  }

.vue文件中使用

import { formatTime } from './decorator.js'
export default {
  methods:{
    @formatTime('YYYY-MM-DD')
    test (time, str) {
      console.log(time) // 2021-11-17
      console.log(str) // string
    }
  }
}
this.test(new Date(), 'string') 

可以看到我们入参时候的new Date() 标准时间已经被格式化为 'YYYY-MM-DD' 时间格式了

多个装饰器配合使用,注意装饰器使用顺序
import { log, formatTime } from './decorator.js'
export default {
  methods:{
    @formatTime('YYYY-MM-DD')
    @log
    test (time, str) {
      console.log(time) // 2021-11-17
      console.log(str) // string
    }
  }
}
this.test(new Date(), 'string') 

控制台结果

2.png

装饰器还可以做许多事情,代码也非常简洁容易理解.

core-decorators.js 提供了一些常用的装饰器方法,可以参考源码有助于理解装饰器

github.com/jayphelps/c…