Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
feat: react-dom and SSR compatible rendering
- Abstracted rendering out of library core to allow different types of renderers - Auto-detection of `react-test-renderer` or `react-dom` renderers. Submodules for: - `dom` (`react-dom`) - `native` (`react-test-renderer`) - `server` (`react-dom/server`) Co-authored-by: Michael Peyper <mpeyper7@gmail.com> BREAKING CHANGE: Importing from `renderHook` and `act` from `@testing-library/react-hooks` will now auto-detect which renderer to used based on the project's dependencies - `peerDependencies` are now optional to support different dependencies being required - This means there will be no warning if the dependency is not installed at all, but it will still warn if an incompatible version is installed
- Loading branch information
1 parent
b35b152
commit a25993f
Showing
74 changed files
with
2,568 additions
and
201 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,5 +1,9 @@ | ||
node_modules | ||
coverage | ||
lib | ||
dom | ||
native | ||
server | ||
pure | ||
.docz | ||
site |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,5 +1,10 @@ | ||
node_modules | ||
coverage | ||
lib | ||
dom | ||
native | ||
server | ||
pure | ||
.docz | ||
site | ||
site | ||
.vscode |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,63 @@ | ||
import fs from 'fs' | ||
import path from 'path' | ||
|
||
type Template = (submodule: string) => string | ||
|
||
const templates = { | ||
index: { | ||
'.js': (submodule: string) => `module.exports = require('../lib/${submodule}')`, | ||
'.d.ts': (submodule: string) => `export * from '../lib/${submodule}'` | ||
}, | ||
pure: { | ||
'.js': (submodule: string) => `module.exports = require('../lib/${submodule}/pure')`, | ||
'.d.ts': (submodule: string) => `export * from '../lib/${submodule}/pure'` | ||
} | ||
} | ||
|
||
const submodules = ['dom', 'native', 'server', 'pure'] | ||
|
||
function cleanDirectory(directory: string) { | ||
const files = fs.readdirSync(directory) | ||
files.forEach((file) => fs.unlinkSync(path.join(directory, file))) | ||
} | ||
|
||
function makeDirectory(submodule: string) { | ||
const submoduleDir = path.join(process.cwd(), submodule) | ||
|
||
if (fs.existsSync(submoduleDir)) { | ||
cleanDirectory(submoduleDir) | ||
} else { | ||
fs.mkdirSync(submoduleDir) | ||
} | ||
|
||
return submoduleDir | ||
} | ||
|
||
function requiredFile(submodule: string) { | ||
return ([name]: [string, unknown]) => { | ||
return name !== submodule | ||
} | ||
} | ||
|
||
function makeFile(directory: string, submodule: string) { | ||
return ([name, extensions]: [string, Record<string, Template>]) => { | ||
Object.entries(extensions).forEach(([extension, template]) => { | ||
const fileName = `${name}${extension}` | ||
console.log(` - ${fileName}`) | ||
const filePath = path.join(directory, fileName) | ||
fs.writeFileSync(filePath, template(submodule)) | ||
}) | ||
} | ||
} | ||
|
||
function makeFiles(directory: string, submodule: string) { | ||
Object.entries(templates).filter(requiredFile(submodule)).forEach(makeFile(directory, submodule)) | ||
} | ||
|
||
function createSubmodule(submodule: string) { | ||
console.log(`Generating submodule: ${submodule}`) | ||
const submoduleDir = makeDirectory(submodule) | ||
makeFiles(submoduleDir, submodule) | ||
} | ||
|
||
submodules.forEach(createSubmodule) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,8 @@ | ||
{ | ||
"extends": "../tsconfig", | ||
"compilerOptions": { | ||
"declaration": false | ||
}, | ||
"exclude": [], | ||
"include": ["./**/*.ts"] | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,78 @@ | ||
import { CreateRenderer, Renderer, RenderResult, RenderHook } from '../types' | ||
import { ResultContainer, RenderHookOptions } from '../types/internal' | ||
|
||
import asyncUtils from './asyncUtils' | ||
import { cleanup, addCleanup, removeCleanup } from './cleanup' | ||
|
||
function resultContainer<TValue>(): ResultContainer<TValue> { | ||
const results: Array<{ value?: TValue; error?: Error }> = [] | ||
const resolvers: Array<() => void> = [] | ||
|
||
const result: RenderResult<TValue> = { | ||
get all() { | ||
return results.map(({ value, error }) => error ?? value) | ||
}, | ||
get current() { | ||
const { value, error } = results[results.length - 1] | ||
if (error) { | ||
throw error | ||
} | ||
return value as TValue | ||
}, | ||
get error() { | ||
const { error } = results[results.length - 1] | ||
return error | ||
} | ||
} | ||
|
||
const updateResult = (value?: TValue, error?: Error) => { | ||
results.push({ value, error }) | ||
resolvers.splice(0, resolvers.length).forEach((resolve) => resolve()) | ||
} | ||
|
||
return { | ||
result, | ||
addResolver: (resolver: () => void) => { | ||
resolvers.push(resolver) | ||
}, | ||
setValue: (value: TValue) => updateResult(value), | ||
setError: (error: Error) => updateResult(undefined, error) | ||
} | ||
} | ||
|
||
const createRenderHook = <TProps, TResult, TOptions extends {}, TRenderer extends Renderer<TProps>>( | ||
createRenderer: CreateRenderer<TProps, TResult, TOptions, TRenderer> | ||
) => ( | ||
callback: (props: TProps) => TResult, | ||
options: RenderHookOptions<TProps, TOptions> = {} as RenderHookOptions<TProps, TOptions> | ||
): RenderHook<TProps, TResult, TRenderer> => { | ||
const { result, setValue, setError, addResolver } = resultContainer<TResult>() | ||
const renderProps = { callback, setValue, setError } | ||
let hookProps = options.initialProps | ||
|
||
const { render, rerender, unmount, act, ...renderUtils } = createRenderer(renderProps, options) | ||
|
||
render(hookProps) | ||
|
||
function rerenderHook(newProps = hookProps) { | ||
hookProps = newProps | ||
rerender(hookProps) | ||
} | ||
|
||
function unmountHook() { | ||
removeCleanup(unmountHook) | ||
unmount() | ||
} | ||
|
||
addCleanup(unmountHook) | ||
|
||
return { | ||
result, | ||
rerender: rerenderHook, | ||
unmount: unmountHook, | ||
...asyncUtils(act, addResolver), | ||
...renderUtils | ||
} | ||
} | ||
|
||
export { createRenderHook, cleanup, addCleanup, removeCleanup } |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,5 @@ | ||
import { autoRegisterCleanup } from '../core/cleanup' | ||
|
||
autoRegisterCleanup() | ||
|
||
export * from './pure' |
Oops, something went wrong.