}"
`;
-exports[`compiler: v-skip > transform > on component 1`] = `
-"const _Vue = Vue
-
-return function render(_ctx, _cache) {
- with (_ctx) {
- const { withCtx: _withCtx, createCommentVNode: _createCommentVNode, resolveComponent: _resolveComponent, openBlock: _openBlock, createBlock: _createBlock } = _Vue
-
- const _component_Comp = _resolveComponent("Comp")
-
- return (_ctx.ok)
- ? _createCommentVNode("v-skip", true)
- : (_openBlock(), _createBlock(_component_Comp, { key: 1 }))
- }
-}"
-`;
-
-exports[`compiler: v-skip > transform > on component with default slot 1`] = `
-"const _Vue = Vue
-
-return function render(_ctx, _cache) {
- with (_ctx) {
- const { withCtx: _withCtx, resolveComponent: _resolveComponent, Fragment: _Fragment, openBlock: _openBlock, createElementBlock: _createElementBlock, createBlock: _createBlock } = _Vue
-
- const _component_Comp = _resolveComponent("Comp")
-
- return (_ctx.ok)
- ? (_openBlock(), _createElementBlock(_Fragment, { key: 0 }, ["foo"], 2112 /* STABLE_FRAGMENT, DEV_ROOT_FRAGMENT */))
- : (_openBlock(), _createBlock(_component_Comp, { key: 1 }, {
- default: _withCtx(() => ["foo"]),
- _: 1 /* STABLE */
- }))
- }
-}"
-`;
-
-exports[`compiler: v-skip > transform > on component with multiple implicit slot 1`] = `
-"const _Vue = Vue
-
-return function render(_ctx, _cache) {
- with (_ctx) {
- const { withCtx: _withCtx, createElementVNode: _createElementVNode, resolveComponent: _resolveComponent, Fragment: _Fragment, openBlock: _openBlock, createElementBlock: _createElementBlock, createBlock: _createBlock } = _Vue
-
- const _component_Comp = _resolveComponent("Comp")
-
- return (_ctx.ok)
- ? (_openBlock(), _createElementBlock(_Fragment, { key: 0 }, [
- _createElementVNode("span"),
- _createElementVNode("div")
- ], 64 /* STABLE_FRAGMENT */))
- : (_openBlock(), _createBlock(_component_Comp, { key: 1 }, {
- foo: _withCtx(() => ["foo"]),
- default: _withCtx(() => [
- _createElementVNode("span"),
- _createElementVNode("div")
- ]),
- _: 1 /* STABLE */
- }))
- }
-}"
-`;
-
-exports[`compiler: v-skip > transform > on component with multiple named slot 1`] = `
-"const _Vue = Vue
-
-return function render(_ctx, _cache) {
- with (_ctx) {
- const { withCtx: _withCtx, resolveComponent: _resolveComponent, Fragment: _Fragment, openBlock: _openBlock, createElementBlock: _createElementBlock, createBlock: _createBlock } = _Vue
-
- const _component_Comp = _resolveComponent("Comp")
-
- return (_ctx.ok)
- ? (_openBlock(), _createElementBlock(_Fragment, { key: 0 }, ["default"], 2112 /* STABLE_FRAGMENT, DEV_ROOT_FRAGMENT */))
- : (_openBlock(), _createBlock(_component_Comp, { key: 1 }, {
- default: _withCtx(() => ["default"]),
- foo: _withCtx(() => ["foo"]),
- _: 1 /* STABLE */
- }))
- }
-}"
-`;
-
-exports[`compiler: v-skip > transform > on dynamic component 1`] = `
-"const _Vue = Vue
-
-return function render(_ctx, _cache) {
- with (_ctx) {
- const { withCtx: _withCtx, renderSlot: _renderSlot, resolveDynamicComponent: _resolveDynamicComponent, openBlock: _openBlock, createBlock: _createBlock } = _Vue
-
- return (_ctx.ok)
- ? _renderSlot(_ctx.$slots, "default", { key: 0 })
- : (_openBlock(), _createBlock(_resolveDynamicComponent(_ctx.Comp), { key: 1 }, {
- default: _withCtx(() => [
- _renderSlot(_ctx.$slots, "default", { key: 0 })
- ]),
- _: 3 /* FORWARDED */
- }))
- }
-}"
-`;
-
exports[`compiler: v-skip > transform > v-else + v-skip 1`] = `
"const _Vue = Vue
export const RESOLVE_COMPONENT: unique symbol = Symbol(
__DEV__ ? `resolveComponent` : ``,
)
+export const RESOLVE_SKIP_COMPONENT: unique symbol = Symbol(
+ __DEV__ ? `resolveSkipComponent` : ``,
+)
export const RESOLVE_DYNAMIC_COMPONENT: unique symbol = Symbol(
__DEV__ ? `resolveDynamicComponent` : ``,
)
[CREATE_STATIC]: `createStaticVNode`,
[RESOLVE_COMPONENT]: `resolveComponent`,
[RESOLVE_DYNAMIC_COMPONENT]: `resolveDynamicComponent`,
+ [RESOLVE_SKIP_COMPONENT]: `resolveSkipComponent`,
[RESOLVE_DIRECTIVE]: `resolveDirective`,
[RESOLVE_FILTER]: `resolveFilter`,
[WITH_DIRECTIVES]: `withDirectives`,
type DirectiveNode,
type ElementNode,
ElementTypes,
+ type ExpressionNode,
type IfBranchNode,
NodeTypes,
type SimpleExpressionNode,
type SkipNode,
- type TemplateChildNode,
+ type VNodeCall,
createCallExpression,
createConditionalExpression,
createSimpleExpression,
import {
CREATE_COMMENT,
ErrorCodes,
- buildSlots,
+ RESOLVE_SKIP_COMPONENT,
+ WITH_MEMO,
createCompilerError,
findDir,
findProp,
export const transformSkip: NodeTransform = createStructuralDirectiveTransform(
'skip',
(node, dir, context) => {
- return processSkip(node, dir, context, skipNode => {
+ return processSkip(node, dir, context, (skipNode?: SkipNode) => {
return () => {
- const { consequent, alternate, test } = skipNode
- const consequentNode =
- consequent.type === NodeTypes.IF_BRANCH
- ? createCodegenNodeForBranch(consequent, 0, context)
- : consequent
+ const codegenNode = node.codegenNode!
+ if (node.tagType === ElementTypes.COMPONENT) {
+ if (codegenNode.type === NodeTypes.VNODE_CALL) {
+ codegenNode.tag = getVNodeTag(
+ context,
+ dir.exp!,
+ codegenNode.tag as string,
+ )
+ } else if (
+ codegenNode.type === NodeTypes.JS_CALL_EXPRESSION &&
+ codegenNode.callee === WITH_MEMO
+ ) {
+ const vnodeCall = codegenNode.arguments[1].returns as VNodeCall
+ vnodeCall.tag = getVNodeTag(
+ context,
+ dir.exp!,
+ vnodeCall.tag as string,
+ )
+ }
+ } else {
+ const { consequent, alternate, test } = skipNode!
+ const consequentNode =
+ consequent.type === NodeTypes.IF_BRANCH
+ ? createCodegenNodeForBranch(consequent, 0, context)
+ : consequent
- skipNode.codegenNode = createConditionalExpression(
- test,
- consequentNode,
- createCodegenNodeForBranch(alternate, 1, context),
- )
+ skipNode!.codegenNode = createConditionalExpression(
+ test,
+ consequentNode,
+ createCodegenNodeForBranch(alternate, 1, context),
+ )
+ }
}
})
},
node: ElementNode,
dir: DirectiveNode,
context: TransformContext,
- processCodegen?: (skipNode: SkipNode) => () => void,
+ processCodegen?: (skipNode?: SkipNode) => () => void,
): (() => void) | undefined {
const loc = dir.exp ? dir.exp.loc : node.loc
if (
validateBrowserExpression(dir.exp as SimpleExpressionNode, context)
}
- let children: TemplateChildNode[] = []
- // for components, extract default slot without props
- // if not found, throw an error
- if (node.tagType === ElementTypes.COMPONENT) {
- const { slots } = buildSlots(node, context, undefined, true)
- if (slots.type === NodeTypes.JS_OBJECT_EXPRESSION) {
- const prop = slots.properties.find(
- p =>
- p.type === NodeTypes.JS_PROPERTY &&
- p.key.type === NodeTypes.SIMPLE_EXPRESSION &&
- p.key.content === 'default' &&
- p.value.params === undefined,
- )
- if (prop) {
- children = prop.value.returns as TemplateChildNode[]
- } else {
- context.onError(
- createCompilerError(ErrorCodes.X_V_SKIP_UNEXPECTED_SLOT, loc),
- )
- }
- }
- }
- // for plain elements, take all children
- else {
- children = node.children
- }
+ let skipNode: SkipNode | undefined
+ if (node.tagType === ElementTypes.ELEMENT) {
+ const children = node.children
+ // if children is empty, create comment node
+ const consequent =
+ children.length !== 0
+ ? ({
+ type: NodeTypes.IF_BRANCH,
+ loc: node.loc,
+ condition: undefined,
+ children,
+ userKey: findProp(node, `key`),
+ } as IfBranchNode)
+ : createCallExpression(context.helper(CREATE_COMMENT), [
+ __DEV__ ? '"v-skip"' : '""',
+ 'true',
+ ])
- // if children is empty, create comment node
- const consequent =
- children.length !== 0
- ? ({
- type: NodeTypes.IF_BRANCH,
- loc: node.loc,
- condition: undefined,
- children,
- userKey: findProp(node, `key`),
- } as IfBranchNode)
- : createCallExpression(context.helper(CREATE_COMMENT), [
- __DEV__ ? '"v-skip"' : '""',
- 'true',
- ])
+ const alternate: IfBranchNode = {
+ type: NodeTypes.IF_BRANCH,
+ loc: node.loc,
+ condition: undefined,
+ children: [node],
+ userKey: findProp(node, `key`),
+ }
- const alternate: IfBranchNode = {
- type: NodeTypes.IF_BRANCH,
- loc: node.loc,
- condition: undefined,
- children: [node],
- userKey: findProp(node, `key`),
+ skipNode = {
+ type: NodeTypes.SKIP,
+ loc: cloneLoc(node.loc),
+ test: dir.exp,
+ consequent,
+ alternate,
+ newline: true,
+ }
+ context.replaceNode(skipNode)
}
- const skipNode: SkipNode = {
- type: NodeTypes.SKIP,
- loc: cloneLoc(node.loc),
- test: dir.exp,
- consequent,
- alternate,
- newline: true,
- }
- context.replaceNode(skipNode)
if (processCodegen) return processCodegen(skipNode)
}
+
+function getVNodeTag(
+ context: TransformContext,
+ exp: ExpressionNode,
+ tag: string,
+) {
+ return createCallExpression(context.helper(RESOLVE_SKIP_COMPONENT), [
+ exp,
+ tag,
+ ])
+}
test('on component', () => {
expect(compile(`<Comp v-skip="foo"/>`).code).toMatchInlineSnapshot(`
- "const { withCtx: _withCtx, createCommentVNode: _createCommentVNode, resolveComponent: _resolveComponent } = require("vue")
- const { ssrRenderComponent: _ssrRenderComponent } = require("vue/server-renderer")
+ "const { resolveComponent: _resolveComponent } = require("vue")
+ const { ssrRenderComponent: _ssrRenderComponent, ssrRenderSkipComponent: _ssrRenderSkipComponent } = require("vue/server-renderer")
return function ssrRender(_ctx, _push, _parent, _attrs) {
const _component_Comp = _resolveComponent("Comp")
- if (_ctx.foo) {
- _createCommentVNode("v-skip", true)
- } else {
- _push(_ssrRenderComponent(_component_Comp, _attrs, null, _parent))
- }
+ _push(_ssrRenderSkipComponent(_push, _ctx.foo, _component_Comp, _attrs, null, _parent))
}"
`)
})
test('on component with default slot', () => {
expect(compile(`<Comp v-skip="ok">foo</Comp>`).code).toMatchInlineSnapshot(`
- "const { withCtx: _withCtx, resolveComponent: _resolveComponent, createTextVNode: _createTextVNode } = require("vue")
- const { ssrRenderComponent: _ssrRenderComponent } = require("vue/server-renderer")
+ "const { resolveComponent: _resolveComponent, withCtx: _withCtx, createTextVNode: _createTextVNode } = require("vue")
+ const { ssrRenderComponent: _ssrRenderComponent, ssrRenderSkipComponent: _ssrRenderSkipComponent } = require("vue/server-renderer")
return function ssrRender(_ctx, _push, _parent, _attrs) {
const _component_Comp = _resolveComponent("Comp")
- if (_ctx.ok) {
- _push(\`<!--[-->foo<!--]-->\`)
- } else {
- _push(_ssrRenderComponent(_component_Comp, _attrs, {
- default: _withCtx((_, _push, _parent, _scopeId) => {
- if (_push) {
- _push(\`foo\`)
- } else {
- return [
- _createTextVNode("foo")
- ]
- }
- }),
- _: 1 /* STABLE */
- }, _parent))
- }
+ _push(_ssrRenderSkipComponent(_push, _ctx.ok, _component_Comp, _attrs, {
+ default: _withCtx((_, _push, _parent, _scopeId) => {
+ if (_push) {
+ _push(\`foo\`)
+ } else {
+ return [
+ _createTextVNode("foo")
+ ]
+ }
+ }),
+ _: 1 /* STABLE */
+ }, _parent))
}"
`)
})
</Comp>`,
).code,
).toMatchInlineSnapshot(`
- "const { withCtx: _withCtx, resolveComponent: _resolveComponent, createTextVNode: _createTextVNode } = require("vue")
- const { ssrRenderComponent: _ssrRenderComponent } = require("vue/server-renderer")
+ "const { resolveComponent: _resolveComponent, withCtx: _withCtx, createTextVNode: _createTextVNode } = require("vue")
+ const { ssrRenderComponent: _ssrRenderComponent, ssrRenderSkipComponent: _ssrRenderSkipComponent } = require("vue/server-renderer")
return function ssrRender(_ctx, _push, _parent, _attrs) {
const _component_Comp = _resolveComponent("Comp")
- if (_ctx.ok) {
- _push(\`<!--[-->default<!--]-->\`)
- } else {
- _push(_ssrRenderComponent(_component_Comp, _attrs, {
- default: _withCtx((_, _push, _parent, _scopeId) => {
- if (_push) {
- _push(\`default\`)
- } else {
- return [
- _createTextVNode("default")
- ]
- }
- }),
- foo: _withCtx((_, _push, _parent, _scopeId) => {
- if (_push) {
- _push(\`foo\`)
- } else {
- return [
- _createTextVNode("foo")
- ]
- }
- }),
- _: 1 /* STABLE */
- }, _parent))
- }
+ _push(_ssrRenderSkipComponent(_push, _ctx.ok, _component_Comp, _attrs, {
+ default: _withCtx((_, _push, _parent, _scopeId) => {
+ if (_push) {
+ _push(\`default\`)
+ } else {
+ return [
+ _createTextVNode("default")
+ ]
+ }
+ }),
+ foo: _withCtx((_, _push, _parent, _scopeId) => {
+ if (_push) {
+ _push(\`foo\`)
+ } else {
+ return [
+ _createTextVNode("foo")
+ ]
+ }
+ }),
+ _: 1 /* STABLE */
+ }, _parent))
}"
`)
})
</Comp>`,
).code,
).toMatchInlineSnapshot(`
- "const { withCtx: _withCtx, resolveComponent: _resolveComponent, createTextVNode: _createTextVNode, createVNode: _createVNode } = require("vue")
- const { ssrRenderComponent: _ssrRenderComponent } = require("vue/server-renderer")
+ "const { resolveComponent: _resolveComponent, withCtx: _withCtx, createTextVNode: _createTextVNode, createVNode: _createVNode } = require("vue")
+ const { ssrRenderComponent: _ssrRenderComponent, ssrRenderSkipComponent: _ssrRenderSkipComponent } = require("vue/server-renderer")
return function ssrRender(_ctx, _push, _parent, _attrs) {
const _component_Comp = _resolveComponent("Comp")
- if (_ctx.ok) {
- _push(\`<!--[--><span></span><div></div><!--]-->\`)
- } else {
- _push(_ssrRenderComponent(_component_Comp, _attrs, {
- foo: _withCtx((_, _push, _parent, _scopeId) => {
- if (_push) {
- _push(\`foo\`)
- } else {
- return [
- _createTextVNode("foo")
- ]
- }
- }),
- default: _withCtx((_, _push, _parent, _scopeId) => {
- if (_push) {
- _push(\`<span\${
- _scopeId
- }></span><div\${
- _scopeId
- }></div>\`)
- } else {
- return [
- _createVNode("span"),
- _createVNode("div")
- ]
- }
- }),
- _: 1 /* STABLE */
- }, _parent))
- }
+ _push(_ssrRenderSkipComponent(_push, _ctx.ok, _component_Comp, _attrs, {
+ foo: _withCtx((_, _push, _parent, _scopeId) => {
+ if (_push) {
+ _push(\`foo\`)
+ } else {
+ return [
+ _createTextVNode("foo")
+ ]
+ }
+ }),
+ default: _withCtx((_, _push, _parent, _scopeId) => {
+ if (_push) {
+ _push(\`<span\${
+ _scopeId
+ }></span><div\${
+ _scopeId
+ }></div>\`)
+ } else {
+ return [
+ _createVNode("span"),
+ _createVNode("div")
+ ]
+ }
+ }),
+ _: 1 /* STABLE */
+ }, _parent))
}"
`)
})
</component>`,
).code,
).toMatchInlineSnapshot(`
- "const { withCtx: _withCtx, resolveDynamicComponent: _resolveDynamicComponent, renderSlot: _renderSlot, createVNode: _createVNode } = require("vue")
- const { ssrRenderSlot: _ssrRenderSlot, ssrRenderVNode: _ssrRenderVNode } = require("vue/server-renderer")
+ "const { resolveDynamicComponent: _resolveDynamicComponent, withCtx: _withCtx, renderSlot: _renderSlot, createVNode: _createVNode } = require("vue")
+ const { ssrRenderSlot: _ssrRenderSlot, ssrRenderVNode: _ssrRenderVNode, ssrRenderSkipComponent: _ssrRenderSkipComponent } = require("vue/server-renderer")
return function ssrRender(_ctx, _push, _parent, _attrs) {
- if (_ctx.ok) {
- _ssrRenderSlot(_ctx.$slots, "default", {}, null, _push, _parent, _scopeId)
- } else {
- _ssrRenderVNode(_push, _createVNode(_resolveDynamicComponent(_ctx.Comp), _attrs, {
- default: _withCtx((_, _push, _parent, _scopeId) => {
- if (_push) {
- _ssrRenderSlot(_ctx.$slots, "default", {}, null, _push, _parent, _scopeId)
- } else {
- return [
- _renderSlot(_ctx.$slots, "default")
- ]
- }
- }),
- _: 3 /* FORWARDED */
- }), _parent)
- }
+ _ssrRenderSkipComponent(_push, _ctx.ok, _push, _createVNode(_resolveDynamicComponent(_ctx.Comp), _attrs, {
+ default: _withCtx((_, _push, _parent, _scopeId) => {
+ if (_push) {
+ _ssrRenderSlot(_ctx.$slots, "default", {}, null, _push, _parent, _scopeId)
+ } else {
+ return [
+ _renderSlot(_ctx.$slots, "default")
+ ]
+ }
+ }),
+ _: 3 /* FORWARDED */
+ }), _parent)
}"
`)
})
<Comp v-skip="ok"><span/></Comp>
`).code,
).toMatchInlineSnapshot(`
- "const { withCtx: _withCtx, resolveComponent: _resolveComponent, createVNode: _createVNode } = require("vue")
- const { ssrRenderComponent: _ssrRenderComponent } = require("vue/server-renderer")
+ "const { resolveComponent: _resolveComponent, withCtx: _withCtx, createVNode: _createVNode } = require("vue")
+ const { ssrRenderComponent: _ssrRenderComponent, ssrRenderSkipComponent: _ssrRenderSkipComponent } = require("vue/server-renderer")
- return function ssrRender(_ctx, _push, _parent, _attrs) {
- const _component_Comp = _resolveComponent("Comp")
+ return function ssrRender(_ctx, _push, _parent, _attrs) {
+ const _component_Comp = _resolveComponent("Comp")
- _push(\`<!--[--><div></div>\`)
- if (_ctx.ok) {
- _push(\`<span></span>\`)
- } else {
- _push(_ssrRenderComponent(_component_Comp, null, {
- default: _withCtx((_, _push, _parent, _scopeId) => {
- if (_push) {
- _push(\`<span\${_scopeId}></span>\`)
- } else {
- return [
- _createVNode("span")
- ]
- }
- }),
- _: 1 /* STABLE */
- }, _parent))
- }
- _push(\`<!--]-->\`)
- }"
- `)
+ _push(\`<!--[--><div></div>\`)
+ _push(_ssrRenderSkipComponent(_push, _ctx.ok, _component_Comp, null, {
+ default: _withCtx((_, _push, _parent, _scopeId) => {
+ if (_push) {
+ _push(\`<span\${_scopeId}></span>\`)
+ } else {
+ return [
+ _createVNode("span")
+ ]
+ }
+ }),
+ _: 1 /* STABLE */
+ }, _parent))
+ _push(\`<!--]-->\`)
+ }"
+ `)
})
})
export const SSR_INTERPOLATE: unique symbol = Symbol(`ssrInterpolate`)
export const SSR_RENDER_VNODE: unique symbol = Symbol(`ssrRenderVNode`)
export const SSR_RENDER_COMPONENT: unique symbol = Symbol(`ssrRenderComponent`)
+export const SSR_RENDER_SKIP_COMPONENT: unique symbol = Symbol(
+ `ssrRenderSkipComponent`,
+)
export const SSR_RENDER_SLOT: unique symbol = Symbol(`ssrRenderSlot`)
export const SSR_RENDER_SLOT_INNER: unique symbol = Symbol(`ssrRenderSlotInner`)
export const SSR_RENDER_CLASS: unique symbol = Symbol(`ssrRenderClass`)
[SSR_INTERPOLATE]: `ssrInterpolate`,
[SSR_RENDER_VNODE]: `ssrRenderVNode`,
[SSR_RENDER_COMPONENT]: `ssrRenderComponent`,
+ [SSR_RENDER_SKIP_COMPONENT]: `ssrRenderSkipComponent`,
[SSR_RENDER_SLOT]: `ssrRenderSlot`,
[SSR_RENDER_SLOT_INNER]: `ssrRenderSlotInner`,
[SSR_RENDER_CLASS]: `ssrRenderClass`,
import {
+ ElementTypes,
type NodeTransform,
NodeTypes,
type SkipNode,
+ createCallExpression,
createIfStatement,
createStructuralDirectiveTransform,
processSkip,
} from '@vue/compiler-core'
import { processIfBranch } from './ssrVIf'
import type { SSRTransformContext } from '../ssrCodegenTransform'
+import { SSR_RENDER_SKIP_COMPONENT } from '../runtimeHelpers'
export const ssrTransformSkip: NodeTransform =
- createStructuralDirectiveTransform('skip', processSkip)
+ createStructuralDirectiveTransform('skip', (node, dir, context) => {
+ processSkip(node, dir, context)
+ return () => {
+ if (node.tagType === ElementTypes.COMPONENT && node.ssrCodegenNode) {
+ const { arguments: args, loc } = node.ssrCodegenNode
+ node.ssrCodegenNode = createCallExpression(
+ context.helper(SSR_RENDER_SKIP_COMPONENT),
+ [`_push`, dir.exp!, ...args],
+ loc,
+ )
+ }
+ }
+ })
export function ssrProcessSkip(
node: SkipNode,
import { camelize, capitalize, isString } from '@vue/shared'
import { warn } from '../warning'
import type { VNodeTypes } from '../vnode'
+import {
+ type ComponentPublicInstance,
+ defineComponent,
+ renderSlot,
+} from '@vue/runtime-core'
export const COMPONENTS = 'components'
export const DIRECTIVES = 'directives'
registry[capitalize(camelize(name))])
)
}
+
+let _comp: ConcreteComponent | undefined
+/**
+ * @private
+ */
+export function resolveSkipComponent(
+ isSkip: boolean,
+ Comp: ConcreteComponent,
+): ConcreteComponent {
+ return isSkip
+ ? _comp ||
+ (_comp = defineComponent({
+ render(this: ComponentPublicInstance) {
+ return renderSlot(this.$slots, 'default')
+ },
+ }))
+ : Comp
+}
resolveComponent,
resolveDirective,
resolveDynamicComponent,
+ resolveSkipComponent,
} from './helpers/resolveAssets'
// For integration with runtime compiler
export { registerRuntimeCompiler, isRuntimeOnly } from './component'
--- /dev/null
+import {
+ type Component,
+ type ComponentInternalInstance,
+ type Slots,
+ createVNode,
+} from 'vue'
+import {
+ type Props,
+ type PushFn,
+ type SSRBuffer,
+ renderComponentVNode,
+} from '../render'
+import { type SSRSlots, ssrRenderSlot } from './ssrRenderSlot'
+
+export function ssrRenderSkipComponent(
+ push: PushFn,
+ isSkip: boolean,
+ comp: Component,
+ props: Props | null = null,
+ children: Slots | SSRSlots | null = null,
+ parentComponent: ComponentInternalInstance | null = null,
+ slotScopeId?: string,
+): SSRBuffer | Promise<SSRBuffer> {
+ if (isSkip) {
+ // only render default slot without slot props
+ ssrRenderSlot(
+ children!,
+ 'default',
+ {},
+ null,
+ push,
+ parentComponent!,
+ slotScopeId,
+ )
+ return []
+ }
+ return renderComponentVNode(
+ createVNode(comp, props, children),
+ parentComponent,
+ slotScopeId,
+ )
+}
// internal runtime helpers
export { renderVNode as ssrRenderVNode } from './render'
export { ssrRenderComponent } from './helpers/ssrRenderComponent'
+export { ssrRenderSkipComponent } from './helpers/ssrRenderSkipComponent'
export { ssrRenderSlot, ssrRenderSlotInner } from './helpers/ssrRenderSlot'
export { ssrRenderTeleport } from './helpers/ssrRenderTeleport'
export {