前段时间参与了川神的源码共读活动,一直也没能产出文章,十分遗憾,现在这篇文章就姑且当作川神文章:据说 99% 的人不知道 vue-devtools 还能直接打开对应组件文件?本文原理揭秘的补充吧
疑惑
既然是补充,那么内容肯定是简短有力,不知道大家在用这个工具的时候,有没有疑惑一个点:
- 我们并没有进行过多的配置,装上之后进入
开发环境,就能看到我们的组件信息。经过简单的配置也能链接到对应的文件。
那么他是怎么做到的呢,就看下文吧。
vue-loader
现在应该大家在使用vue进行开发的过程中很少有人不使用vue-loader吧?大家了解过一个.vue文件被vue-loader处理过之后是什么样子没有?
我这里举个🌰,创建一个abc.vue文件
这样的一段vue模版语法在经过vue-loader处理后,会分成三部分。
render和options部分
这里主要是定义了render函数和用户传入的options对象,render函数里的_h和_c是vue渲染的runtime函数,其实就跟createReactElement是一个意思,忽略就好。继续往下看。
normalized
这里主要是把不同的输入类型都统统转成下面的形式,如果没猜错的话这个转换也会在vue的源码本体里好多地方使用,或者在其他需要渲染的插件里使用。
{
exports: scriptExports,
options: options
}
导出
这里拿到转换后的内容就把它导出嘛,跟我们这次的目的相关度比较高的就是component.options.__file = 'src/abc.vue'这一行了,很显然,这里是把文件的路径放到了运行时的构造函数属性里,其实这里的component根据我们函数即组件的思想来说就是一个组件的构造函数了。后面只需要给他一个runtime的context就能渲染出来视图,不过很显然这个跟我们现在讨论的话题无关。
Vue本体
为啥上面已经找到了文件路径挂在的位置之后我们还要去vue的本体代码去看呢?
-
不知道大家注意过没,最关键的点,vue-dveools是可以显示一整个组件组成的树结构的。 上面不是已经找到组件构造函数了嘛。这个不能生成树结构吗?
-
上面的是组件
构造函数,现在我们要看的是runtime也就是组件实例对象,其实在vue中叫组件实例context更合适
如何找到对应组件名
首先,我们知道一般XXX.vue文件的导出组件名称叫XXX,因此其实组件名根据文件名解析就可以得出。 在vue-loader里没看到其他和组件名相关的,我们来到vue源码文件里搜索__file就得到下面的方法
看到这个
match变量,其实大家都明白了,就是从文件路径里抠出来的。
那他是什么时候抠呢?
在组件的
init生命周期里看到了这么一行代码
很显然,这里是拿到__name挂到了vm也就是构造函数实例的上下文下。
这个config.performance 和 mark又是啥?
performance其实是一个是否记录性能的flag一般在开发环境会默认开启,生产环境默认关闭。真正和我们的插件联动的其实是这个mark
可以看到,当window上被挂了performance属性的时候,mark就不会为空了。
对于浏览器插件来说,给window上挂一个属性并不难。
总结
突然就总结了?是不是感觉还没讲完,其实已经完了,我们已经找到了__file和__name是如何被一个一个地挂到组件的渲染上下文中。如果感兴趣的话可以生成一个vue的模版项目,然后像下面一样操作打印一下,找一找这两个属性隐藏在了哪里,解锁vue的你没见过的新面纱吧!
tips
插两个广告哈:
- 第一个就是感谢川神组织的源码共读,感兴趣的可以加他微信了解
ruochuan12 - 第二个就是电商前端团队大力招人啊,感兴趣的加我微信
zs15931442916或者在下面评论