Skip to content

Commit f0a66c5

Browse files
committed
refactor: cache v-once and purely static trees separately
1 parent 267ada0 commit f0a66c5

File tree

3 files changed

+24
-11
lines changed

3 files changed

+24
-11
lines changed

src/compiler/codegen/index.js

+9-3
Original file line numberDiff line numberDiff line change
@@ -86,10 +86,16 @@ export function genElement (el: ASTElement, state: CodegenState): string {
8686
}
8787

8888
// hoist static sub-trees out
89-
function genStatic (el: ASTElement, state: CodegenState): string {
89+
function genStatic (el: ASTElement, state: CodegenState, once: ?boolean): string {
9090
el.staticProcessed = true
9191
state.staticRenderFns.push(`with(this){return ${genElement(el, state)}}`)
92-
return `_m(${state.staticRenderFns.length - 1}${el.staticInFor ? ',true' : ''})`
92+
return `_m(${
93+
state.staticRenderFns.length - 1
94+
},${
95+
el.staticInFor ? 'true' : 'false'
96+
},${
97+
once ? 'true' : 'false'
98+
})`
9399
}
94100

95101
// v-once
@@ -115,7 +121,7 @@ function genOnce (el: ASTElement, state: CodegenState): string {
115121
}
116122
return `_o(${genElement(el, state)},${state.onceId++},${key})`
117123
} else {
118-
return genStatic(el, state)
124+
return genStatic(el, state, true)
119125
}
120126
}
121127

src/core/instance/render-helpers/render-static.js

+13-6
Original file line numberDiff line numberDiff line change
@@ -7,12 +7,19 @@ import { cloneVNode, cloneVNodes } from 'core/vdom/vnode'
77
*/
88
export function renderStatic (
99
index: number,
10-
isInFor?: boolean
10+
isInFor: boolean,
11+
isOnce: boolean
1112
): VNode | Array<VNode> {
12-
// static trees can be rendered once and cached on the contructor options
13-
// so every instance shares the same cached trees
14-
const options = this.$options
15-
const cached = options.cached || (options.cached = [])
13+
// render fns generated by compiler < 2.5.4 does not provide v-once
14+
// information to runtime so be conservative
15+
const isOldVersion = arguments.length < 3
16+
// if a static tree is generated by v-once, it is cached on the instance;
17+
// otherwise it is purely static and can be cached on the shared options
18+
// across all instances.
19+
const renderFns = this.$options.staticRenderFns
20+
const cached = isOldVersion || isOnce
21+
? (this._staticTrees || (this._staticTrees = []))
22+
: (renderFns.cached || (renderFns.cached = []))
1623
let tree = cached[index]
1724
// if has already-rendered static tree and not inside v-for,
1825
// we can reuse the same tree by doing a shallow clone.
@@ -22,7 +29,7 @@ export function renderStatic (
2229
: cloneVNode(tree)
2330
}
2431
// otherwise, render a fresh tree.
25-
tree = cached[index] = options.staticRenderFns[index].call(this._renderProxy, null, this)
32+
tree = cached[index] = renderFns[index].call(this._renderProxy, null, this)
2633
markStatic(tree, `__static__${index}`, false)
2734
return tree
2835
}

test/unit/modules/compiler/codegen.spec.js

+2-2
Original file line numberDiff line numberDiff line change
@@ -478,7 +478,7 @@ describe('codegen', () => {
478478
// have "inline-template'"
479479
assertCodegen(
480480
'<my-component inline-template><p><span>hello world</span></p></my-component>',
481-
`with(this){return _c('my-component',{inlineTemplate:{render:function(){with(this){return _m(0)}},staticRenderFns:[function(){with(this){return _c('p',[_c('span',[_v("hello world")])])}}]}})}`
481+
`with(this){return _c('my-component',{inlineTemplate:{render:function(){with(this){return _m(0,false,false)}},staticRenderFns:[function(){with(this){return _c('p',[_c('span',[_v("hello world")])])}}]}})}`
482482
)
483483
// "have inline-template attrs, but not having exactly one child element
484484
assertCodegen(
@@ -498,7 +498,7 @@ describe('codegen', () => {
498498
it('generate static trees inside v-for', () => {
499499
assertCodegen(
500500
`<div><div v-for="i in 10"><p><span></span></p></div></div>`,
501-
`with(this){return _c('div',_l((10),function(i){return _c('div',[_m(0,true)])}))}`,
501+
`with(this){return _c('div',_l((10),function(i){return _c('div',[_m(0,true,false)])}))}`,
502502
[`with(this){return _c('p',[_c('span')])}`]
503503
)
504504
})

0 commit comments

Comments
 (0)