new Function 得到的都是匿名函数,怎么得到一个具名函数对象?
背景
Vue 支持动态组件编译,使用原生组件定义方式创建对象:
// 动态创建一个 Vue 组件
const MyComponent = Vue.component('componentId', {
template: templateStr,
data: eval(dataStr),
methods: methodObj,
}
);
这个 methods
怎么动态生成呢?
JS 的 new Function
方案:可以使用 new Function
创建一个函数,但是它是一个匿名函数,为了让 Vue 能够使用这些函数,必须创建对应的具名函数,怎么实现呢?
在匿名函数的方法体中,返回一个具名函数,然后再调用一次这个匿名函数。
例如,一个弹框组件,提供一个 onClose
方法,动态生成:
const closeFuncDef = 'function onClose() {\n' +
' this.isShow = false;\n' +
' this.close();\n' +
' },';
再定义一个 methods
对象,传入这个字符串配置创建的方法对象:
// 定义一个匿名函数,它返回一个具名函数
const anonymousFuncDef = new Function(`return ${closeFuncDef}`);
// 调用这个匿名函数,得到那个具名函数对象
const withNameFuncDef = anonymousFuncDef();
// 设置这个函数属性的值为那个具名函数
methods = {
onClose: withNameFuncDef
}
这样就能被 Vue 动态编译并使用了。
函数对象如何反序列化并解析
正向思路是 methods
函数属性都通过读取文件获取字符串后,再解析出来,那么问题来了,JSON.parse
没法解析函数对象,怎么办呢?
另外 Vue.component
方式创建组件,怎么传递自定义的样式,以及 mounted/created
挂载事件呢?能不能支持复杂组件的定义呢?
要支持定制化前端文件,还差一点。