vue2+ts项目中实现自动注册import的函数的失败经历

背景

当我们在用vue2+ts的时候,如果我们需要在template里面使用某一个函数,就必须要先从其他文件中引入这个函数,然后在class中再注册一下,例如下面的代码: 这种写法有些组员提出来不是十分的优雅,我也觉得如果要是能直接使用那就更好了,就更加的方便了。所以这篇文章记录了我为了实现这个功能所做出的尝试,最后的结果是失败了,只是在过程中学到了一些mixin、装饰器和webpack插件的一些知识,为自己做一下记录,如果大家能够帮助我实现,那就太好了,我就可以去组里吹一波了。

装饰器

首先我想到的方法是利用装饰器。什么是装饰器?以我的理解,装饰器如果类比生活中例子,就比如你新买了一台车,他是针织的座椅,但是你不喜欢,你买了一个真皮的座椅套套在了外面。你并没有改变原来的座椅任何一点,但是这个座椅变成你喜欢的样子了。就像我在上面背景中展示的代码,@Component就是vue-property-decorator这个库里面的其中一个装饰器,把这个装饰器写在class上面,class里面的代码你就可以按照这个库规定的方式去写了,你就可以即使用vue又可以使用ts了。于是乎,我想要实现这个class中免注册的功能就总共分为两部分。

第一部分就是我需要知道我import进来了哪些函数,第二部分是把这些函数在我自己写的decorator中怎么注册到vue上。两个听着都非常不靠谱,但我也作死的往下走走看。先放下第一个,主攻第二个。想实现第二部分,我首先需要清楚怎么用装饰器。js的装饰器分为:类装饰器、方法装饰器、属性装饰器、还有访问符装饰器和参数装饰器。
当使用多个装饰器的时候,他们的运行顺序是 属性装饰器 -> 访问符装饰器 -> 方法装饰器 -> 参数装饰器 -> 类装饰器 具体的每一个用法在这个链接中www.tslang.cn/docs/handbo…

vue-property-decorator中,@Component这个装饰器,他是一个类装饰器,那我们就仅说一下类装饰器。类装饰器就是一个函数,它的第一个参数就是他下面这个类的构造器,举个例子 我们通过target.prototype就能获取到vue的实例,因为我们的class是继承了Vue的。@Component装饰器将将我们写在class下面的函数还有data等一系列vue的代码,注册到vue的实例上面,下面截图是源码的一部分 源码的链接

这样在template里面就可以用了,那我们也可以在我们自定义的这个类装饰器里面,将我们import进来的这些函数挂在这个vue的实例里面就可以了,但是如何在自定义的装饰器里面获取到import的函数,我一直没有找到方法。

mixin

苦于无法找到方法解决装饰器中获取import值,而且在每个@Component装饰器下面还要写一个自定义的装饰器,这也要一些工作量,所以我就在想能不能想一个办法在全局写一次就可以了。这时就想到了用mixin。
mixin可以让我们在全局混入一个created生命周期函数,这样在每个vue文件都会先执行一下这个mixin的函数,那我们在这个函数中注册import进来的函数就可以了。此处需要注意一点就是,当一个组件有created函数时,又有mixin的created函数时,先执行mixin的,然后再执行本身的created函数。

require.context

接下来想办法解决知道引入了哪些函数,我思来想去想出一个不成熟的办法。我们一般会把公共工具函数放在utils这个文件夹下面,而一些自定义的局部工具函数,放在当前文件夹下面再建立一个自定义名字的文件夹。然后利用require.context方法,因为require.context是webpack的一个api,可以让我们得到一个文件夹下面所有export出来的函数,例如下面的代码 但是这样虽然能够获取所有的export出来的函数,然后把他们注册到vue上,但是这是获取了所有,我只想要我import了哪些函数,所以核心问题还是如何获取到import引入的值。所以require.context更加适合当我们需要把整个文件夹下面的文件全部导入时,利用require.context进行动态的批量导入。

webpack plugin

webpack的插件提供了一些钩子函数,比如JavascriptParser Hooks,我们再利用normalModuleFactory可以进一步使用import这个钩子,这样就可以在所有import的地方触发这个钩子了。写法如下 但这个功能也还是不适合解决我的问题,因为还是全局的,而且数据处理起来非常的困难。webpack插件还是更加适合处理类似去除多余console.log等问题。

结尾

尝试了几种方法,但因为水平不够,还是无法实现import后直接在vue中注册好所需的函数。作者是第一次写文,也算是求助帖,下面的留言区可以吐槽可以喷,但要是能给出解决方案更加感激。书写此文,一是寻求大佬帮助,二是因为折腾了好几天,不写出来感觉几天啥也没干一样,所以鼓足勇气,作死发文。