在前面知道,在完全版本的 Vue 中,比运行时版本多了一个编译器。
const { render, staticRenderFns } = compileToFunctions(template, {
outputSourceRange: process.env.NODE_ENV !== 'production',
shouldDecodeNewlines,
shouldDecodeNewlinesForHref,
delimiters: options.delimiters,
comments: options.comments
}, this)
// 挂在渲染函数
options.render = render
options.staticRenderFns = staticRenderFns
compileToFunctions 是什么?
顺着方法我们找到了 src/complier/index.js
/* @flow */
import { parse } from './parser/index'
import { optimize } from './optimizer'
import { generate } from './codegen/index'
import { createCompilerCreator } from './create-compiler'
// `createCompilerCreator` allows creating compilers that use alternative
// parser/optimizer/codegen, e.g the SSR optimizing compiler.
// Here we just export a default compiler using the default parts.
export const createCompiler = createCompilerCreator(function baseCompile (
template: string,
options: CompilerOptions
): CompiledResult {
const ast = parse(template.trim(), options)
if (options.optimize !== false) {
optimize(ast, options)
}
const code = generate(ast, options)
return {
ast,
render: code.render,
staticRenderFns: code.staticRenderFns
}
})
这个代码将模板的编译分为三个步骤:
- const ast = parse(...): 将末班对象编译成 ast
- optimize() 优化器,将编译成的模板进行优化
- generate(...) 代码生成器
最终返回了一个具有 ast,render, staticRenderFns 三个属性的对象
分析具体的三步都干了些什么?
想像一下我们在 HTML 中曾经有过这么个用法:
Vue.component('todo-item', {
template: '<li>这是个待办项</li>'
})