web-shell ships as an embeddable React component, so an uncaught render
error anywhere in the tree (Markdown / KaTeX / Mermaid / a tool panel)
unmounts the whole React root and blanks the host page. Add two layers of
isolation plus a generic boundary:
- ErrorBoundary (components/ErrorBoundary.tsx): generic class boundary with
reset-on-key recovery, so a streamed/edited/retried subtree recovers on its
own while a stably-broken one stays on the fallback without looping.
- Message level: each MessageItem body is wrapped, so one bad message degrades
to an inline notice instead of taking down the transcript. The notice is
role-aware (right-aligned for user messages, left for assistant) so it still
reads as the right turn and doesn't blur turn boundaries.
- Top level: the WebShell lib entry and the standalone main.tsx wrap <App> in a
self-contained RootErrorFallback (no provider/theme/i18n dependency, inherits
host text color) offering a retry, so an App-level crash shows a recoverable
surface instead of a blank page.
Adds message.renderError strings (en + zh-CN) and unit tests covering the
boundary mechanism and the root fallback + retry path.