Skip to content

Commit 77fef97

Browse files
committed
fix(ssr): resolve teleports for stream render APIs
1 parent 57d3a05 commit 77fef97

File tree

3 files changed

+37
-1
lines changed

3 files changed

+37
-1
lines changed

packages/server-renderer/__tests__/ssrTeleport.spec.ts

Lines changed: 34 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@
44

55
import { createApp, h, Teleport } from 'vue'
66
import { renderToString } from '../src/renderToString'
7+
import { renderToSimpleStream } from '../src/renderToStream'
78
import { SSRContext } from '../src/render'
89
import { ssrRenderTeleport } from '../src/helpers/ssrRenderTeleport'
910

@@ -134,4 +135,37 @@ describe('ssrRenderTeleport', () => {
134135
expect(html).toBe('<!--teleport start--><!--teleport end-->')
135136
expect(ctx.teleports!['#target']).toBe(`<div>content</div><!---->`)
136137
})
138+
139+
test('teleport inside async component (stream)', async () => {
140+
const ctx: SSRContext = {}
141+
const asyncComponent = {
142+
template: '<teleport to="#target"><div>content</div></teleport>',
143+
async setup() {}
144+
}
145+
let html = ''
146+
let resolve: any
147+
const p = new Promise(r => (resolve = r))
148+
renderToSimpleStream(
149+
h({
150+
template: '<async-component />',
151+
components: { asyncComponent }
152+
}),
153+
ctx,
154+
{
155+
push(chunk) {
156+
if (chunk === null) {
157+
resolve()
158+
} else {
159+
html += chunk
160+
}
161+
},
162+
destroy(err) {
163+
throw err
164+
}
165+
}
166+
)
167+
await p
168+
expect(html).toBe('<!--teleport start--><!--teleport end-->')
169+
expect(ctx.teleports!['#target']).toBe(`<div>content</div><!---->`)
170+
})
137171
})

packages/server-renderer/src/renderToStream.ts

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,7 @@ import {
99
import { isString, isPromise } from '@vue/shared'
1010
import { renderComponentVNode, SSRBuffer, SSRContext } from './render'
1111
import { Readable, Writable } from 'stream'
12+
import { resolveTeleports } from './renderToString'
1213

1314
const { isVNode } = ssrUtils
1415

@@ -74,6 +75,7 @@ export function renderToSimpleStream<T extends SimpleReadable>(
7475

7576
Promise.resolve(renderComponentVNode(vnode))
7677
.then(buffer => unrollBuffer(buffer, stream))
78+
.then(() => resolveTeleports(context))
7779
.then(() => stream.push(null))
7880
.catch(error => {
7981
stream.destroy(error)

packages/server-renderer/src/renderToString.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -70,7 +70,7 @@ export async function renderToString(
7070
return result
7171
}
7272

73-
async function resolveTeleports(context: SSRContext) {
73+
export async function resolveTeleports(context: SSRContext) {
7474
if (context.__teleportBuffers) {
7575
context.teleports = context.teleports || {}
7676
for (const key in context.__teleportBuffers) {

0 commit comments

Comments
 (0)