test: add transform tests to `v-html` / `v-text` tests (#49)
Co-authored-by: 三咲智子 Kevin Deng <sxzz@sxzz.moe>
This commit is contained in:
parent
28b11f5cf7
commit
c87512f592
|
@ -1,5 +1,19 @@
|
||||||
// Vitest Snapshot v1, https://vitest.dev/guide/snapshot.html
|
// Vitest Snapshot v1, https://vitest.dev/guide/snapshot.html
|
||||||
|
|
||||||
|
exports[`v-html > should convert v-html to innerHTML 1`] = `
|
||||||
|
"import { template as _template, children as _children, effect as _effect, setHtml as _setHtml } from 'vue/vapor';
|
||||||
|
|
||||||
|
export function render(_ctx) {
|
||||||
|
const t0 = _template("<div></div>")
|
||||||
|
const n0 = t0()
|
||||||
|
const { 0: [n1],} = _children(n0)
|
||||||
|
_effect(() => {
|
||||||
|
_setHtml(n1, undefined, _ctx.code)
|
||||||
|
})
|
||||||
|
return n0
|
||||||
|
}"
|
||||||
|
`;
|
||||||
|
|
||||||
exports[`v-html > should raise error and ignore children when v-html is present 1`] = `
|
exports[`v-html > should raise error and ignore children when v-html is present 1`] = `
|
||||||
"import { template as _template, children as _children, effect as _effect, setHtml as _setHtml } from 'vue/vapor';
|
"import { template as _template, children as _children, effect as _effect, setHtml as _setHtml } from 'vue/vapor';
|
||||||
|
|
||||||
|
@ -25,17 +39,3 @@ export function render(_ctx) {
|
||||||
return n0
|
return n0
|
||||||
}"
|
}"
|
||||||
`;
|
`;
|
||||||
|
|
||||||
exports[`v-html > simple expression 1`] = `
|
|
||||||
"import { template as _template, children as _children, effect as _effect, setHtml as _setHtml } from 'vue/vapor';
|
|
||||||
|
|
||||||
export function render(_ctx) {
|
|
||||||
const t0 = _template("<div></div>")
|
|
||||||
const n0 = t0()
|
|
||||||
const { 0: [n1],} = _children(n0)
|
|
||||||
_effect(() => {
|
|
||||||
_setHtml(n1, undefined, _ctx.code)
|
|
||||||
})
|
|
||||||
return n0
|
|
||||||
}"
|
|
||||||
`;
|
|
||||||
|
|
|
@ -1,18 +1,6 @@
|
||||||
// Vitest Snapshot v1, https://vitest.dev/guide/snapshot.html
|
// Vitest Snapshot v1, https://vitest.dev/guide/snapshot.html
|
||||||
|
|
||||||
exports[`v-text > no expression 1`] = `
|
exports[`v-text > should convert v-text to textContent 1`] = `
|
||||||
"import { template as _template, children as _children, setText as _setText } from 'vue/vapor';
|
|
||||||
|
|
||||||
export function render(_ctx) {
|
|
||||||
const t0 = _template("<div></div>")
|
|
||||||
const n0 = t0()
|
|
||||||
const { 0: [n1],} = _children(n0)
|
|
||||||
_setText(n1, undefined, "")
|
|
||||||
return n0
|
|
||||||
}"
|
|
||||||
`;
|
|
||||||
|
|
||||||
exports[`v-text > simple expression 1`] = `
|
|
||||||
"import { template as _template, children as _children, effect as _effect, setText as _setText } from 'vue/vapor';
|
"import { template as _template, children as _children, effect as _effect, setText as _setText } from 'vue/vapor';
|
||||||
|
|
||||||
export function render(_ctx) {
|
export function render(_ctx) {
|
||||||
|
@ -25,3 +13,29 @@ export function render(_ctx) {
|
||||||
return n0
|
return n0
|
||||||
}"
|
}"
|
||||||
`;
|
`;
|
||||||
|
|
||||||
|
exports[`v-text > should raise error and ignore children when v-text is present 1`] = `
|
||||||
|
"import { template as _template, children as _children, effect as _effect, setText as _setText } from 'vue/vapor';
|
||||||
|
|
||||||
|
export function render(_ctx) {
|
||||||
|
const t0 = _template("<div></div>")
|
||||||
|
const n0 = t0()
|
||||||
|
const { 0: [n1],} = _children(n0)
|
||||||
|
_effect(() => {
|
||||||
|
_setText(n1, undefined, _ctx.test)
|
||||||
|
})
|
||||||
|
return n0
|
||||||
|
}"
|
||||||
|
`;
|
||||||
|
|
||||||
|
exports[`v-text > should raise error if has no expression 1`] = `
|
||||||
|
"import { template as _template, children as _children, setText as _setText } from 'vue/vapor';
|
||||||
|
|
||||||
|
export function render(_ctx) {
|
||||||
|
const t0 = _template("<div></div>")
|
||||||
|
const n0 = t0()
|
||||||
|
const { 0: [n1],} = _children(n0)
|
||||||
|
_setText(n1, undefined, "")
|
||||||
|
return n0
|
||||||
|
}"
|
||||||
|
`;
|
||||||
|
|
|
@ -1,39 +1,119 @@
|
||||||
import { type RootNode, BindingTypes, DOMErrorCodes } from '@vue/compiler-dom'
|
import {
|
||||||
import { type CompilerOptions, compile as _compile } from '../../src'
|
BindingTypes,
|
||||||
|
DOMErrorCodes,
|
||||||
|
NodeTypes,
|
||||||
|
parse,
|
||||||
|
} from '@vue/compiler-dom'
|
||||||
|
import {
|
||||||
|
type CompilerOptions,
|
||||||
|
compile as _compile,
|
||||||
|
RootIRNode,
|
||||||
|
transform,
|
||||||
|
generate,
|
||||||
|
IRNodeTypes,
|
||||||
|
} from '../../src'
|
||||||
|
import { getBaseTransformPreset } from '../../src/compile'
|
||||||
|
|
||||||
function compile(template: string | RootNode, options: CompilerOptions = {}) {
|
function compileWithVHtml(
|
||||||
let { code } = _compile(template, {
|
template: string,
|
||||||
...options,
|
options: CompilerOptions = {},
|
||||||
mode: 'module',
|
): {
|
||||||
|
ir: RootIRNode
|
||||||
|
code: string
|
||||||
|
} {
|
||||||
|
const ast = parse(template, { prefixIdentifiers: true, ...options })
|
||||||
|
const [nodeTransforms, directiveTransforms] = getBaseTransformPreset(true)
|
||||||
|
const ir = transform(ast, {
|
||||||
|
nodeTransforms,
|
||||||
|
directiveTransforms,
|
||||||
prefixIdentifiers: true,
|
prefixIdentifiers: true,
|
||||||
|
...options,
|
||||||
})
|
})
|
||||||
return code
|
const { code } = generate(ir, { prefixIdentifiers: true, ...options })
|
||||||
|
return { ir, code }
|
||||||
}
|
}
|
||||||
|
|
||||||
describe('v-html', () => {
|
describe('v-html', () => {
|
||||||
test('simple expression', () => {
|
test('should convert v-html to innerHTML', () => {
|
||||||
const code = compile(`<div v-html="code"></div>`, {
|
const { code, ir } = compileWithVHtml(`<div v-html="code"></div>`, {
|
||||||
bindingMetadata: {
|
bindingMetadata: {
|
||||||
code: BindingTypes.SETUP_REF,
|
code: BindingTypes.SETUP_REF,
|
||||||
},
|
},
|
||||||
})
|
})
|
||||||
|
|
||||||
|
expect(ir.vaporHelpers).contains('setHtml')
|
||||||
|
expect(ir.helpers.size).toBe(0)
|
||||||
|
|
||||||
|
expect(ir.operation).toEqual([])
|
||||||
|
expect(ir.effect).toMatchObject([
|
||||||
|
{
|
||||||
|
expressions: [
|
||||||
|
{
|
||||||
|
type: NodeTypes.SIMPLE_EXPRESSION,
|
||||||
|
content: 'code',
|
||||||
|
isStatic: false,
|
||||||
|
},
|
||||||
|
],
|
||||||
|
operations: [
|
||||||
|
{
|
||||||
|
type: IRNodeTypes.SET_HTML,
|
||||||
|
element: 1,
|
||||||
|
value: {
|
||||||
|
type: NodeTypes.SIMPLE_EXPRESSION,
|
||||||
|
content: 'code',
|
||||||
|
isStatic: false,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
],
|
||||||
|
},
|
||||||
|
])
|
||||||
|
|
||||||
expect(code).matchSnapshot()
|
expect(code).matchSnapshot()
|
||||||
})
|
})
|
||||||
|
|
||||||
test('should raise error and ignore children when v-html is present', () => {
|
test('should raise error and ignore children when v-html is present', () => {
|
||||||
const onError = vi.fn()
|
const onError = vi.fn()
|
||||||
const code = compile(`<div v-html="test">hello</div>`, {
|
const { code, ir } = compileWithVHtml(`<div v-html="test">hello</div>`, {
|
||||||
onError,
|
onError,
|
||||||
})
|
})
|
||||||
expect(code).matchSnapshot()
|
|
||||||
|
expect(ir.vaporHelpers).contains('setHtml')
|
||||||
|
expect(ir.helpers.size).toBe(0)
|
||||||
|
|
||||||
|
expect(ir.operation).toEqual([])
|
||||||
|
expect(ir.effect).toMatchObject([
|
||||||
|
{
|
||||||
|
expressions: [
|
||||||
|
{
|
||||||
|
type: NodeTypes.SIMPLE_EXPRESSION,
|
||||||
|
content: 'test',
|
||||||
|
isStatic: false,
|
||||||
|
},
|
||||||
|
],
|
||||||
|
operations: [
|
||||||
|
{
|
||||||
|
type: IRNodeTypes.SET_HTML,
|
||||||
|
element: 1,
|
||||||
|
value: {
|
||||||
|
type: NodeTypes.SIMPLE_EXPRESSION,
|
||||||
|
content: 'test',
|
||||||
|
isStatic: false,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
],
|
||||||
|
},
|
||||||
|
])
|
||||||
|
|
||||||
expect(onError.mock.calls).toMatchObject([
|
expect(onError.mock.calls).toMatchObject([
|
||||||
[{ code: DOMErrorCodes.X_V_HTML_WITH_CHILDREN }],
|
[{ code: DOMErrorCodes.X_V_HTML_WITH_CHILDREN }],
|
||||||
])
|
])
|
||||||
|
|
||||||
|
expect(code).matchSnapshot()
|
||||||
})
|
})
|
||||||
|
|
||||||
test('should raise error if has no expression', () => {
|
test('should raise error if has no expression', () => {
|
||||||
const onError = vi.fn()
|
const onError = vi.fn()
|
||||||
const code = compile(`<div v-html></div>`, {
|
const { code } = compileWithVHtml(`<div v-html></div>`, {
|
||||||
onError,
|
onError,
|
||||||
})
|
})
|
||||||
expect(code).matchSnapshot()
|
expect(code).matchSnapshot()
|
||||||
|
|
|
@ -1,28 +1,120 @@
|
||||||
import { type RootNode, BindingTypes, DOMErrorCodes } from '@vue/compiler-dom'
|
import {
|
||||||
import { type CompilerOptions, compile as _compile } from '../../src'
|
BindingTypes,
|
||||||
|
DOMErrorCodes,
|
||||||
|
NodeTypes,
|
||||||
|
parse,
|
||||||
|
} from '@vue/compiler-dom'
|
||||||
|
import {
|
||||||
|
type CompilerOptions,
|
||||||
|
compile as _compile,
|
||||||
|
RootIRNode,
|
||||||
|
transform,
|
||||||
|
generate,
|
||||||
|
IRNodeTypes,
|
||||||
|
} from '../../src'
|
||||||
|
import { getBaseTransformPreset } from '../../src/compile'
|
||||||
|
|
||||||
function compile(template: string | RootNode, options: CompilerOptions = {}) {
|
function compileWithVText(
|
||||||
let { code } = _compile(template, {
|
template: string,
|
||||||
...options,
|
options: CompilerOptions = {},
|
||||||
mode: 'module',
|
): {
|
||||||
|
ir: RootIRNode
|
||||||
|
code: string
|
||||||
|
} {
|
||||||
|
const ast = parse(template, { prefixIdentifiers: true, ...options })
|
||||||
|
const [nodeTransforms, directiveTransforms] = getBaseTransformPreset(true)
|
||||||
|
const ir = transform(ast, {
|
||||||
|
nodeTransforms,
|
||||||
|
directiveTransforms,
|
||||||
prefixIdentifiers: true,
|
prefixIdentifiers: true,
|
||||||
|
...options,
|
||||||
})
|
})
|
||||||
return code
|
const { code } = generate(ir, { prefixIdentifiers: true, ...options })
|
||||||
|
return { ir, code }
|
||||||
}
|
}
|
||||||
|
|
||||||
describe('v-text', () => {
|
describe('v-text', () => {
|
||||||
test('simple expression', () => {
|
test('should convert v-text to textContent', () => {
|
||||||
const code = compile(`<div v-text="str"></div>`, {
|
const { code, ir } = compileWithVText(`<div v-text="str"></div>`, {
|
||||||
bindingMetadata: {
|
bindingMetadata: {
|
||||||
str: BindingTypes.SETUP_REF,
|
str: BindingTypes.SETUP_REF,
|
||||||
},
|
},
|
||||||
})
|
})
|
||||||
|
|
||||||
|
expect(ir.vaporHelpers).contains('setText')
|
||||||
|
expect(ir.helpers.size).toBe(0)
|
||||||
|
|
||||||
|
expect(ir.operation).toEqual([])
|
||||||
|
|
||||||
|
expect(ir.effect).toMatchObject([
|
||||||
|
{
|
||||||
|
expressions: [
|
||||||
|
{
|
||||||
|
type: NodeTypes.SIMPLE_EXPRESSION,
|
||||||
|
content: 'str',
|
||||||
|
isStatic: false,
|
||||||
|
},
|
||||||
|
],
|
||||||
|
operations: [
|
||||||
|
{
|
||||||
|
type: IRNodeTypes.SET_TEXT,
|
||||||
|
element: 1,
|
||||||
|
value: {
|
||||||
|
type: NodeTypes.SIMPLE_EXPRESSION,
|
||||||
|
content: 'str',
|
||||||
|
isStatic: false,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
],
|
||||||
|
},
|
||||||
|
])
|
||||||
|
|
||||||
expect(code).matchSnapshot()
|
expect(code).matchSnapshot()
|
||||||
})
|
})
|
||||||
|
|
||||||
test('no expression', () => {
|
test('should raise error and ignore children when v-text is present', () => {
|
||||||
const onError = vi.fn()
|
const onError = vi.fn()
|
||||||
const code = compile(`<div v-text></div>`, { onError })
|
const { code, ir } = compileWithVText(`<div v-text="test">hello</div>`, {
|
||||||
|
onError,
|
||||||
|
})
|
||||||
|
expect(onError.mock.calls).toMatchObject([
|
||||||
|
[{ code: DOMErrorCodes.X_V_TEXT_WITH_CHILDREN }],
|
||||||
|
])
|
||||||
|
|
||||||
|
// children should have been removed
|
||||||
|
expect(ir.template).toMatchObject([{ template: '<div></div>' }])
|
||||||
|
|
||||||
|
expect(ir.effect).toMatchObject([
|
||||||
|
{
|
||||||
|
expressions: [
|
||||||
|
{
|
||||||
|
type: NodeTypes.SIMPLE_EXPRESSION,
|
||||||
|
content: 'test',
|
||||||
|
isStatic: false,
|
||||||
|
},
|
||||||
|
],
|
||||||
|
operations: [
|
||||||
|
{
|
||||||
|
type: IRNodeTypes.SET_TEXT,
|
||||||
|
element: 1,
|
||||||
|
value: {
|
||||||
|
type: NodeTypes.SIMPLE_EXPRESSION,
|
||||||
|
content: 'test',
|
||||||
|
isStatic: false,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
],
|
||||||
|
},
|
||||||
|
])
|
||||||
|
|
||||||
|
expect(code).matchSnapshot()
|
||||||
|
// children should have been removed
|
||||||
|
expect(code).contains('template("<div></div>")')
|
||||||
|
})
|
||||||
|
|
||||||
|
test('should raise error if has no expression', () => {
|
||||||
|
const onError = vi.fn()
|
||||||
|
const { code } = compileWithVText(`<div v-text></div>`, { onError })
|
||||||
expect(code).matchSnapshot()
|
expect(code).matchSnapshot()
|
||||||
expect(onError.mock.calls).toMatchObject([
|
expect(onError.mock.calls).toMatchObject([
|
||||||
[{ code: DOMErrorCodes.X_V_TEXT_NO_EXPRESSION }],
|
[{ code: DOMErrorCodes.X_V_TEXT_NO_EXPRESSION }],
|
||||||
|
|
|
@ -13,7 +13,7 @@ export const transformVText: DirectiveTransform = (dir, node, context) => {
|
||||||
context.options.onError(
|
context.options.onError(
|
||||||
createDOMCompilerError(DOMErrorCodes.X_V_TEXT_WITH_CHILDREN, loc),
|
createDOMCompilerError(DOMErrorCodes.X_V_TEXT_WITH_CHILDREN, loc),
|
||||||
)
|
)
|
||||||
node.children.length = 0
|
context.childrenTemplate.length = 0
|
||||||
}
|
}
|
||||||
|
|
||||||
context.registerEffect(
|
context.registerEffect(
|
||||||
|
|
Loading…
Reference in New Issue