Skip to content

Commit df686ab

Browse files
committedJun 10, 2024··
fix(ssr): directive binding.instance should respect exposed during ssr
close #7499 close #7502
1 parent 9daf90e commit df686ab

File tree

3 files changed

+55
-3
lines changed

3 files changed

+55
-3
lines changed
 

‎packages/runtime-core/src/index.ts

+6-1
Original file line numberDiff line numberDiff line change
@@ -363,7 +363,11 @@ export { transformVNodeArgs } from './vnode'
363363
// **IMPORTANT** These APIs are exposed solely for @vue/server-renderer and may
364364
// change without notice between versions. User code should never rely on them.
365365

366-
import { createComponentInstance, setupComponent } from './component'
366+
import {
367+
createComponentInstance,
368+
getComponentPublicInstance,
369+
setupComponent,
370+
} from './component'
367371
import { renderComponentRoot } from './componentRenderUtils'
368372
import { setCurrentRenderingInstance } from './componentRenderContext'
369373
import { isVNode, normalizeVNode } from './vnode'
@@ -375,6 +379,7 @@ const _ssrUtils = {
375379
setCurrentRenderingInstance,
376380
isVNode,
377381
normalizeVNode,
382+
getComponentPublicInstance,
378383
}
379384

380385
/**

‎packages/server-renderer/__tests__/ssrDirectives.spec.ts

+43
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,10 @@ import { renderToString } from '../src/renderToString'
22
import {
33
createApp,
44
h,
5+
mergeProps,
6+
ref,
57
resolveDirective,
8+
unref,
69
vModelCheckbox,
710
vModelDynamic,
811
vModelRadio,
@@ -542,4 +545,44 @@ describe('ssr: directives', () => {
542545
),
543546
).toBe(`<div id="foo-arg-true"></div>`)
544547
})
548+
549+
// #7499
550+
test('custom directive w/ getSSRProps (expose)', async () => {
551+
let exposeVars: null | string | undefined = null
552+
const useTestDirective = () => ({
553+
vTest: {
554+
getSSRProps({ instance }: any) {
555+
if (instance) {
556+
exposeVars = instance.x
557+
}
558+
return { id: exposeVars }
559+
},
560+
},
561+
})
562+
const { vTest } = useTestDirective()
563+
564+
const renderString = await renderToString(
565+
createApp({
566+
setup(props, { expose }) {
567+
const x = ref('foo')
568+
expose({ x })
569+
const __returned__ = { useTestDirective, vTest, ref, x }
570+
Object.defineProperty(__returned__, '__isScriptSetup', {
571+
enumerable: false,
572+
value: true,
573+
})
574+
return __returned__
575+
},
576+
ssrRender(_ctx, _push, _parent, _attrs) {
577+
_push(
578+
`<div${ssrRenderAttrs(
579+
mergeProps(_attrs!, ssrGetDirectiveProps(_ctx, unref(vTest))),
580+
)}></div>`,
581+
)
582+
},
583+
}),
584+
)
585+
expect(renderString).toBe(`<div id="foo"></div>`)
586+
expect(exposeVars).toBe('foo')
587+
})
545588
})

‎packages/server-renderer/src/helpers/ssrGetDirectiveProps.ts

+6-2
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,8 @@
1-
import type { ComponentPublicInstance, Directive } from '@vue/runtime-core'
1+
import {
2+
type ComponentPublicInstance,
3+
type Directive,
4+
ssrUtils,
5+
} from '@vue/runtime-core'
26

37
export function ssrGetDirectiveProps(
48
instance: ComponentPublicInstance,
@@ -12,7 +16,7 @@ export function ssrGetDirectiveProps(
1216
dir.getSSRProps(
1317
{
1418
dir,
15-
instance,
19+
instance: ssrUtils.getComponentPublicInstance(instance.$),
1620
value,
1721
oldValue: undefined,
1822
arg,

0 commit comments

Comments
 (0)
Please sign in to comment.