vue源码分析(九) 编译之解析(parse)整体流程
Robin 10/9/2018 vue源码分析面试
# 1. 概述
上一章 —— vue源码分析(八) 编译之整体流程 (opens new window) 我们分析了模板编译的入口以及整体逻辑,遗留了三个问题没有分析即编译生成 AST
树、AST
树优化、将 AST
编译成渲染函数,,本章节我们主要分析第一个问题——编译生成 AST
树。
# 2. 案例
在分析之前我们以一个案例开始,代码如下:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>parse</title>
<script src="./vue.js"></script>
</head>
<body>
<div id="app">{{ fullName }}</div>
<script>
new Vue({
el: '#app',
template: `
<ul :class="classObject" class="list" v-show="isShow">
<li v-for="(l, i) in list" :key="i" @click="clickItem(index)">{{ i }}:{{ l }}</li>
</ul>
`,
data: {
isShow: true,
list: ['Vue', 'React', 'Angular'],
classObject: {
active: true,
'text-danger': false
}
},
methods: {
clickItem(index) {
console.log(index)
}
}
})
</script>
</body>
</html>
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
# 3.整体流程
parse
的定义,下面代码为精简后的伪代码。
源码目录:src/compiler/parser/index.js
/**
* Convert HTML string to AST.
*/
export function parse (
template: string,
options: CompilerOptions
): ASTElement | void {
// ...
getFnsAndConfigFromOptions(options)
function warnOnce (msg, range) {
// ...
}
function closeElement (element) {
// ...
}
function trimEndingWhitespace (el) {
// remove trailing whitespace node
// ...
}
function checkRootConstraints (el) {
// ...
}
parseHTML(template, {
// options ...
start (tag, attrs, unary, start, end) {
// ...
let element: ASTElement = createASTElement(tag, attrs, currentParent)
// ...
processElement(element)
treeManagement()
// ...
},
end (tag, start, end) {
// ...
treeManagement()
closeElement(element)
},
chars (text: string, start: number, end: number) {
// ...
handleText()
createChildrenASTOfText()
},
comment (text: string, start, end) {
// ...
createChildrenASTOfComment()
}
})
return root
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
这段代码主要做了两件事:
(1)、parseHTML
: 函数的作用就是用来做词法分析的
(2)、parse
: 函数的作用则是在词法分析的基础上做句法分析从而生成一棵 AST
# 4. parseHTML
说明:关于 parseHTML
我们会在下一章 (opens new window)做详细分析。
# 5. parse
说明:关于 parse
我们会在第十一章 (opens new window)做详细分析。