Skip to content

Commit 309949a

Browse files
Merge pull request #1 from stephenkilbourn/stephenkilbourn-fix-ssr-after
feat: add test to reproduce testing-library#605
2 parents 8966a64 + bc73113 commit 309949a

File tree

4 files changed

+20865
-12
lines changed

4 files changed

+20865
-12
lines changed

package.json

+1
Original file line numberDiff line numberDiff line change
@@ -59,6 +59,7 @@
5959
"docz-theme-default": "1.2.0",
6060
"docz-utils": "2.3.0",
6161
"eslint": "7.24.0",
62+
"eslint-plugin-import": "^2.26.0",
6263
"kcd-scripts": "9.1.0",
6364
"prettier": "^2.2.1",
6465
"react": "17.0.2",

src/server/__tests__/ssr.test.ts

+22
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,22 @@
1+
/**
2+
* @jest-environment node
3+
*/
4+
import {useState} from 'react'
5+
import {renderHook, act} from '..'
6+
7+
// This verifies that renderHook can be called in
8+
// a SSR-like environment.
9+
describe('renderHook', () => {
10+
function useLoading() {
11+
if (typeof window !== 'undefined') {
12+
const [loading, setLoading] = useState(false)
13+
return {loading, setLoading}
14+
}
15+
}
16+
17+
test('should not throw in SSR environment', () => {
18+
expect(() => renderHook(() => useLoading())).not.toThrowError(
19+
'document is not defined',
20+
)
21+
})
22+
})

src/server/pure.ts

+13-12
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@ import ReactDOMServer from 'react-dom/server'
22
import ReactDOM from 'react-dom'
33
import { act } from 'react-dom/test-utils'
44

5-
import { RendererProps, RendererOptions } from '../types/react'
5+
import { RendererOptions, RendererProps } from '../types/react'
66

77
import { createRenderHook } from '../core'
88
import { createTestHarness } from '../helpers/createTestHarness'
@@ -12,44 +12,45 @@ function createServerRenderer<TProps, TResult>(
1212
{ wrapper }: RendererOptions<TProps>
1313
) {
1414
let renderProps: TProps | undefined
15-
let hydrated = false
16-
const container = document.createElement('div')
15+
let container: HTMLDivElement | undefined;
16+
let serverOutput = ''
1717
const testHarness = createTestHarness(rendererProps, wrapper, false)
1818

1919
return {
2020
render(props?: TProps) {
2121
renderProps = props
2222
act(() => {
2323
try {
24-
const serverOutput = ReactDOMServer.renderToString(testHarness(props))
25-
container.innerHTML = serverOutput
24+
serverOutput = ReactDOMServer.renderToString(testHarness(props))
2625
} catch (e: unknown) {
2726
rendererProps.setError(e as Error)
2827
}
2928
})
3029
},
3130
hydrate() {
32-
if (hydrated) {
31+
if (container) {
3332
throw new Error('The component can only be hydrated once')
3433
} else {
34+
container = document.createElement('div')
3535
act(() => {
36-
ReactDOM.hydrate(testHarness(renderProps), container)
36+
ReactDOM.hydrate(testHarness(renderProps), container || null)
3737
})
38-
hydrated = true
3938
}
4039
},
4140
rerender(props?: TProps) {
42-
if (!hydrated) {
41+
if (!container) {
4342
throw new Error('You must hydrate the component before you can rerender')
4443
}
4544
act(() => {
46-
ReactDOM.render(testHarness(props), container)
45+
ReactDOM.render(testHarness(props), container || null)
4746
})
4847
},
4948
unmount() {
50-
if (hydrated) {
49+
if (container) {
5150
act(() => {
52-
ReactDOM.unmountComponentAtNode(container)
51+
if (typeof container !== 'undefined') {
52+
ReactDOM.unmountComponentAtNode(container)
53+
}
5354
})
5455
}
5556
},

0 commit comments

Comments
 (0)