浅谈vue中.vue文件解析流程


Posted in Javascript onApril 24, 2018

我们平时写的 .vue 文件称为 SFC(Single File Components),本文介绍将 SFC 解析为 descriptor 这一过程在 vue 中是如何执行的。

vue 提供了一个 compiler.parseComponent(file, [options]) 方法,来将 .vue 文件解析成一个 descriptor:

// an object format describing a single-file component.
declare type SFCDescriptor = {
  template: ?SFCBlock;
  script: ?SFCBlock;
  styles: Array<SFCBlock>;
  customBlocks: Array<SFCBlock>;
};

文件入口

解析 sfc 文件的入口在 src/sfc/parser.js 中,该文件 export 了 parseComponent 方法, parseComponent 方法用来对单文件组件进行编译。

接下来我们看看 parseComponent 方法都做了哪些事情。

parseComponent 方法

function start(tag, attrs, unary, start, end,){
}

function end(tag, start, end){
}

parseHTML(content, {
  start,
  end
})

parseComponent 方法中定义了 start``end 两个函数,之后调用了 parseHTML 方法来对 .vue 文件内容践行编译。

那么这个 parseHTML 方法是做啥的呢?

parseHTML 方法

该方法看名字就知道是一个 html-parser,可以简单理解为,解析到每个起始标签时,调用 option 中的 start;每个标签结束时,调用 option 中的 end。

对应到这里,就是分别调用 parseComponent 方法中定义的 start 和 end 函数。

在 parseComponent 中维护一个 depth 变量,在 start 中将 depth++ ,在 end 中 depth-- 。那么,每个 depth === 0 的标签就是我们需要获取的信息,包含 template、script、style 以及一些自定义标签。

start

每当遇到一个起始标签时,执行 start 函数。

1、记录下 currentBlock。

每个 currentBlock 包含以下内容:

declare type SFCBlock = {
  type: string;
  content: string;
  start?: number;
  end?: number;
  lang?: string;
  src?: string;
  scoped?: boolean;
  module?: string | boolean;
};

2、根据 tag 名称,将 currentBlock 对象在返回结果对象中。

返回结果对象定义为 sfc,如果tag不是 script,style,template 中的任一个,就放在 sfc.customBlocks 中。如果是style,就放在 sfc.styles 中。script 和 template 则直接放在 sfc 下。

if (isSpecialTag(tag)) {
  checkAttrs(currentBlock, attrs)
  if (tag === 'style') {
    sfc.styles.push(currentBlock)
  } else {
    sfc[tag] = currentBlock
  }
} else { // custom blocks
  sfc.customBlocks.push(currentBlock)
}

end

每当遇到一个结束标签时,执行 end 函数。

1、如果当前是第一层标签(depth === 1),并且 currentBlock 变量存在,那么取出这部分text,放在 currentBlock.content 中。

if (depth === 1 && currentBlock) {
 currentBlock.end = start
 let text = deindent(content.slice(currentBlock.start, currentBlock.end))
 // pad content so that linters and pre-processors can output correct
 // line numbers in errors and warnings
 if (currentBlock.type !== 'template' && options.pad) {
  text = padContent(currentBlock, options.pad) + text
 }
 currentBlock.content = text
 currentBlock = null
}

2、depth-- 。

得到 descriptor

在将 .vue 整个遍历一遍后,得到的 sfc 对象即为我们需要的结果。

生成 .js ?

compiler.parseComponent(file, [options]) 得到的只是一个组件的 SFCDescriptor ,最终编译成.js 文件是交给 vue-loader 等库来做的。

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持三水点靠木。

Javascript 相关文章推荐
用jQuery打造TabPanel效果代码
May 22 Javascript
js/jQuery对象互转(快速操作dom元素)
Feb 04 Javascript
js的.innerHTML = &quot;&quot;IE9下显示有错误的解决方法
Sep 16 Javascript
判断字符串的长度(优化版)中文占两个字符
Oct 30 Javascript
Google 地图API Map()构造器详解
Aug 06 Javascript
微信小程序 实战小程序实例
Oct 08 Javascript
BootStrap实现手机端轮播图左右滑动事件
Oct 13 Javascript
基于canvas的二维码邀请函生成插件
Feb 14 Javascript
详解vue2.0脚手架的webpack 配置文件分析
May 27 Javascript
angular4 JavaScript内存溢出问题
Mar 06 Javascript
vue 中几种传值方法(3种)
Nov 12 Javascript
vue+element UI实现树形表格
Dec 29 Vue.js
vue-cli2.9.3 详细教程
Apr 23 #Javascript
vue.js数据绑定操作详解
Apr 23 #Javascript
jQuery+ajax实现动态添加表格tr td功能示例
Apr 23 #jQuery
再谈Angular4 脏值检测(性能优化)
Apr 23 #Javascript
微信小程序之swiper轮播图中的图片自适应高度的方法
Apr 23 #Javascript
vue.js中实现登录控制的方法示例
Apr 23 #Javascript
JS中获取 DOM 元素的绝对位置实例详解
Apr 23 #Javascript
You might like
关于php fread()使用技巧
2010/01/22 PHP
php文件打包 下载之使用PHP自带的ZipArchive压缩文件并下载打包好的文件
2012/06/13 PHP
PHP获取当前日期所在星期(月份)的开始日期与结束日期(实现代码)
2013/06/18 PHP
使用PHP和HTML5 FormData实现无刷新文件上传教程
2014/09/06 PHP
WordPres对前端页面调试时的两个PHP函数使用小技巧
2015/12/22 PHP
niceTitle 基于jquery的超链接提示插件
2010/05/31 Javascript
让人蛋疼的JavaScript语法特性
2014/09/30 Javascript
jQuery处理json数据返回数组和输出的方法
2015/03/11 Javascript
HTML5+setCutomValidity()函数验证表单实例分享
2015/04/24 Javascript
详解js图片轮播效果实现原理
2015/12/17 Javascript
你所未知的3种Node.js代码优化方式
2016/02/25 Javascript
举例讲解如何判断JavaScript中对象的类型
2016/04/22 Javascript
详解JavaScript模块化开发
2016/12/04 Javascript
jQuery File Upload文件上传插件使用详解
2016/12/06 Javascript
微信小程序 视图容器组件的详解及实例代码
2017/01/19 Javascript
JavaScript和JQuery获取DIV值的方法示例
2017/03/07 Javascript
原生js中ajax访问的实例详解
2017/09/19 Javascript
vue+vuex+axios+echarts画一个动态更新的中国地图的方法
2017/12/19 Javascript
JavaScript实现封闭区域布尔运算的示例代码
2018/06/25 Javascript
微信小程序基于高德地图API实现天气组件(动态效果)
2020/10/22 Javascript
Python 文件和输入输出小结
2013/10/09 Python
python threading模块操作多线程介绍
2015/04/08 Python
Python爬虫框架Scrapy实例代码
2018/03/04 Python
python logging日志模块以及多进程日志详解
2018/04/18 Python
解决pycharm工程启动卡住没反应的问题
2019/01/19 Python
Python中三元表达式的几种写法介绍
2019/03/04 Python
Python实现UDP程序通信过程图解
2020/05/15 Python
Python扫描端口的实现
2021/01/25 Python
Python如何实现单例模式
2016/06/03 面试题
本科生职业生涯规划书范文
2014/01/21 职场文书
广告宣传策划方案
2014/05/21 职场文书
纪念九一八事变83周年国旗下讲话稿
2014/09/15 职场文书
2016年度师德标兵先进事迹材料
2016/02/26 职场文书
辞职报告(范文三篇)
2019/08/27 职场文书
Python类方法总结讲解
2021/07/26 Python
移除Selenium中window.navigator.webdriver值
2022/06/10 Python