Error: for reasons + a dev digest
', - ); + expect(container.innerHTML).toBe('for reasons + a dev digest
'); } else { expect(container.innerHTML).toBe('digest("for reasons")
'); } diff --git a/packages/react-server-dom-webpack/src/__tests__/ReactFlightDOMBrowser-test.js b/packages/react-server-dom-webpack/src/__tests__/ReactFlightDOMBrowser-test.js index 2427317ce2c32..f8f3a1c3f2877 100644 --- a/packages/react-server-dom-webpack/src/__tests__/ReactFlightDOMBrowser-test.js +++ b/packages/react-server-dom-webpack/src/__tests__/ReactFlightDOMBrowser-test.js @@ -583,7 +583,7 @@ describe('ReactFlightDOMBrowser', () => { controller.abort('for reasons'); }); const expectedValue = __DEV__ - ? 'Error: for reasons + a dev digest
' + ? 'for reasons + a dev digest
' : 'digest("for reasons")
'; expect(container.innerHTML).toBe(expectedValue); diff --git a/packages/react-server/src/ReactFizzServer.js b/packages/react-server/src/ReactFizzServer.js index a928b2651a934..e8ea394386df6 100644 --- a/packages/react-server/src/ReactFizzServer.js +++ b/packages/react-server/src/ReactFizzServer.js @@ -33,6 +33,7 @@ import type {ComponentStackNode} from './ReactFizzComponentStack'; import type {TreeContext} from './ReactFizzTreeContext'; import type {ThenableState} from './ReactFizzThenable'; import {enableRenderableContext} from 'shared/ReactFeatureFlags'; +import {describeObjectForErrorMessage} from 'shared/ReactSerializationErrors'; import { scheduleWork, @@ -816,18 +817,19 @@ function encodeErrorForBoundary( ) { boundary.errorDigest = digest; if (__DEV__) { + let message; // In dev we additionally encode the error message and component stack on the boundary - let errorMessage; - if (typeof error === 'string') { - errorMessage = error; - } else if (error && typeof error.message === 'string') { - errorMessage = error.message; + if (error instanceof Error) { + // eslint-disable-next-line react-internal/safe-string-coercion + message = String(error.message); + } else if (typeof error === 'object' && error !== null) { + message = describeObjectForErrorMessage(error); } else { // eslint-disable-next-line react-internal/safe-string-coercion - errorMessage = String(error); + message = String(error); } - boundary.errorMessage = errorMessage; + boundary.errorMessage = message; boundary.errorComponentStack = thrownInfo.componentStack; } } diff --git a/packages/react-server/src/ReactFlightServer.js b/packages/react-server/src/ReactFlightServer.js index 4c81931223e46..072a71b03dcc5 100644 --- a/packages/react-server/src/ReactFlightServer.js +++ b/packages/react-server/src/ReactFlightServer.js @@ -1678,10 +1678,10 @@ function emitErrorChunk( // eslint-disable-next-line react-internal/safe-string-coercion stack = String(error.stack); } else if (typeof error === 'object' && error !== null) { - message = 'Error: ' + describeObjectForErrorMessage(error); + message = describeObjectForErrorMessage(error); } else { // eslint-disable-next-line react-internal/safe-string-coercion - message = 'Error: ' + String(error); + message = String(error); } } catch (x) { message = 'An error occurred but serializing the error message failed.';