mirror of
https://github.com/facebook/react.git
synced 2025-11-01 09:12:30 +00:00
Give unresolved lazy() a name in component stack (#16104)
* Give unresolved lazy() a name in component stack * Normalize stack in tests Co-authored-by: Sebastian Markbage <sema@fb.com>
This commit is contained in:
co-authored by
Sebastian Markbage
parent
333deb707d
commit
3c7d52c3d6
@@ -6,6 +6,15 @@ let ReactFeatureFlags;
|
||||
let Suspense;
|
||||
let lazy;
|
||||
|
||||
function normalizeCodeLocInfo(str) {
|
||||
return (
|
||||
str &&
|
||||
str.replace(/\n +(?:at|in) ([\S]+)[^\n]*/g, function(m, name) {
|
||||
return '\n in ' + name + ' (at **)';
|
||||
})
|
||||
);
|
||||
}
|
||||
|
||||
describe('ReactLazy', () => {
|
||||
beforeEach(() => {
|
||||
jest.resetModules();
|
||||
@@ -1183,4 +1192,85 @@ describe('ReactLazy', () => {
|
||||
expect(Scheduler).toFlushAndYield([]);
|
||||
}).toErrorDev('Function components cannot be given refs');
|
||||
});
|
||||
|
||||
it('should error with a component stack naming the resolved component', async () => {
|
||||
let componentStackMessage;
|
||||
|
||||
const LazyText = lazy(() =>
|
||||
fakeImport(function ResolvedText() {
|
||||
throw new Error('oh no');
|
||||
}),
|
||||
);
|
||||
|
||||
class ErrorBoundary extends React.Component {
|
||||
state = {error: null};
|
||||
|
||||
componentDidCatch(error, errMessage) {
|
||||
componentStackMessage = normalizeCodeLocInfo(errMessage.componentStack);
|
||||
this.setState({
|
||||
error,
|
||||
});
|
||||
}
|
||||
|
||||
render() {
|
||||
return this.state.error ? null : this.props.children;
|
||||
}
|
||||
}
|
||||
|
||||
ReactTestRenderer.create(
|
||||
<ErrorBoundary>
|
||||
<Suspense fallback={<Text text="Loading..." />}>
|
||||
<LazyText text="Hi" />
|
||||
</Suspense>
|
||||
</ErrorBoundary>,
|
||||
{unstable_isConcurrent: true},
|
||||
);
|
||||
|
||||
expect(Scheduler).toFlushAndYield(['Loading...']);
|
||||
|
||||
try {
|
||||
await Promise.resolve();
|
||||
} catch (e) {}
|
||||
|
||||
expect(Scheduler).toFlushAndYield([]);
|
||||
|
||||
expect(componentStackMessage).toContain('in ResolvedText');
|
||||
});
|
||||
|
||||
it('should error with a component stack containing Lazy if unresolved', () => {
|
||||
let componentStackMessage;
|
||||
|
||||
const LazyText = lazy(() => ({
|
||||
then(resolve, reject) {
|
||||
reject(new Error('oh no'));
|
||||
},
|
||||
}));
|
||||
|
||||
class ErrorBoundary extends React.Component {
|
||||
state = {error: null};
|
||||
|
||||
componentDidCatch(error, errMessage) {
|
||||
componentStackMessage = normalizeCodeLocInfo(errMessage.componentStack);
|
||||
this.setState({
|
||||
error,
|
||||
});
|
||||
}
|
||||
|
||||
render() {
|
||||
return this.state.error ? null : this.props.children;
|
||||
}
|
||||
}
|
||||
|
||||
ReactTestRenderer.create(
|
||||
<ErrorBoundary>
|
||||
<Suspense fallback={<Text text="Loading..." />}>
|
||||
<LazyText text="Hi" />
|
||||
</Suspense>
|
||||
</ErrorBoundary>,
|
||||
);
|
||||
|
||||
expect(Scheduler).toHaveYielded([]);
|
||||
|
||||
expect(componentStackMessage).toContain('in Lazy');
|
||||
});
|
||||
});
|
||||
|
||||
Reference in New Issue
Block a user