Open webfansplz opened 3 years ago
In template transform, use compileTemplate to compile the raw template into render function code(在模板转换中,使用compileTemplate将原始模板编译为render函数)
export interface TemplateCompiler {
compile(template: string, options: CompilerOptions): CodegenResult
parse(template: string, options: ParserOptions): RootNode
}
export interface SFCTemplateCompileOptions {
source: string
filename: string
id: string
scoped?: boolean
isProd?: boolean
ssr?: boolean
ssrCssVars?: string[]
inMap?: RawSourceMap
compiler?: TemplateCompiler
compilerOptions?: CompilerOptions
preprocessLang?: string
preprocessOptions?: any
/**
* 在某些情况下,compiler-sfc可能不在项目根目录内
* 比如:link或者globally installed
* 在这种情况下,可以传递自定义的"require"来正确解析预处理器
*/
preprocessCustomRequire?: (id: string) => any
/**
* Configure what tags/attributes to transform into asset url imports,
* or disable the transform altogether with `false`.
*/
transformAssetUrls?: AssetURLOptions | AssetURLTagConfig | boolean
}
export interface SFCTemplateCompileResults {
code: string
ast?: RootNode
preamble?: string
source: string
tips: string[]
errors: (string | CompilerError)[]
map?: RawSourceMap
}
export function compileTemplate(
options: SFCTemplateCompileOptions
): SFCTemplateCompileResults {
// 预处理语言, SFCTemplateCompileOptions的preprocessCustomRequire
const { preprocessLang, preprocessCustomRequire } = options
/**
* 在es模块浏览器构建||或者全局的情况下,存在preprocessLang且没有传递自定义的方法来正确解析。
* 模板预处理需要一个cusotomRequire配置返回浏览器,然后预处理器render一个字符串来转换
*/
if (
(__ESM_BROWSER__ || __GLOBAL__) &&
preprocessLang &&
!preprocessCustomRequire
) {
throw new Error(
`[@vue/compiler-sfc] Template preprocessing in the browser build must ` +
`provide the \`preprocessCustomRequire\` option to return the in-browser ` +
`version of the preprocessor in the shape of { render(): string }.`
)
}
const preprocessor = preprocessLang
? preprocessCustomRequire
? preprocessCustomRequire(preprocessLang)
: require('consolidate')[preprocessLang as keyof typeof consolidate]
: false
if (preprocessor) {
try {
return doCompileTemplate({
...options,
source: preprocess(options, preprocessor)
})
} catch (e) {
return {
code: `export default function render() {}`,
source: options.source,
tips: [],
errors: [e]
}
}
} else if (preprocessLang) {
return {
code: `export default function render() {}`,
source: options.source,
tips: [
`Component ${
options.filename
} uses lang ${preprocessLang} for template. Please install the language preprocessor.`
],
errors: [
`Component ${
options.filename
} uses lang ${preprocessLang} for template, however it is not installed.`
]
}
} else {
return doCompileTemplate(options)
}
}
function doCompileTemplate({
filename,
id,
scoped,
inMap,
source,
ssr = false,
ssrCssVars,
isProd = false,
compiler = ssr ? (CompilerSSR as TemplateCompiler) : CompilerDOM,
compilerOptions = {},
transformAssetUrls
}: SFCTemplateCompileOptions): SFCTemplateCompileResults {
const errors: CompilerError[] = []
let nodeTransforms: NodeTransform[] = []
if (isObject(transformAssetUrls)) {
const assetOptions = normalizeOptions(transformAssetUrls)
nodeTransforms = [
createAssetUrlTransformWithOptions(assetOptions),
createSrcsetTransformWithOptions(assetOptions)
]
} else if (transformAssetUrls !== false) {
nodeTransforms = [transformAssetUrl, transformSrcset]
}
if (ssr && !ssrCssVars) {
warnOnce(
`compileTemplate is called with \`ssr: true\` but no ` +
`corresponding \`cssVars\` option.\`.`
)
}
if (!id) {
warnOnce(`compileTemplate now requires the \`id\` option.\`.`)
id = ''
}
const shortId = id.replace(/^data-v-/, '')
const longId = `data-v-${shortId}`
let { code, ast, preamble, map } = compiler.compile(source, {
mode: 'module',
prefixIdentifiers: true,
hoistStatic: true,
cacheHandlers: true,
ssrCssVars:
ssr && ssrCssVars && ssrCssVars.length
? genCssVarsFromList(ssrCssVars, shortId, isProd)
: '',
scopeId: scoped ? longId : undefined,
...compilerOptions,
nodeTransforms: nodeTransforms.concat(compilerOptions.nodeTransforms || []),
filename,
sourceMap: true,
onError: e => errors.push(e)
})
// inMap should be the map produced by ./parse.ts which is a simple line-only
// mapping. If it is present, we need to adjust the final map and errors to
// reflect the original line numbers.
if (inMap) {
if (map) {
map = mapLines(inMap, map)
}
if (errors.length) {
patchErrors(errors, source, inMap)
}
}
return { code, ast, preamble, source, errors, tips: [], map }
}
占坑:compileScript.ts
占坑:stylePluginScoped.ts
占坑:templateTransformAssetUrl.ts
compileStyle.ts模块
在样式转换中,使用“compileStyle”来编译原始CSS以处理“
Share your knowledge and repository sources from Github . ♥️
subject
vue-next/compiler-sfc
2020/11/23 - 2020/11/29 ~