ar9avg's picture
fix: align rl-state API shape with frontend, add error boundary
ce1c471
import React from 'react'
import ReactDOM from 'react-dom/client'
import App from './App'
import './index.css'
// Restore persisted theme
try {
const saved = localStorage.getItem('theme') as 'dark' | 'light' | null
if (saved) document.documentElement.setAttribute('data-theme', saved)
else document.documentElement.setAttribute('data-theme', 'dark')
} catch {
document.documentElement.setAttribute('data-theme', 'dark')
}
class ErrorBoundary extends React.Component<
{ children: React.ReactNode },
{ error: Error | null }
> {
constructor(props: { children: React.ReactNode }) {
super(props)
this.state = { error: null }
}
static getDerivedStateFromError(error: Error) {
return { error }
}
render() {
if (this.state.error) {
return (
<div style={{
height: '100vh', display: 'flex', alignItems: 'center', justifyContent: 'center',
background: '#08080d', color: '#fff', flexDirection: 'column', gap: 16, padding: 32,
fontFamily: 'monospace'
}}>
<div style={{ fontSize: 14, color: '#ef4444', marginBottom: 8 }}>Runtime error</div>
<pre style={{ fontSize: 11, color: '#9ca3af', maxWidth: 600, overflow: 'auto' }}>
{this.state.error.message}
</pre>
<button
onClick={() => window.location.reload()}
style={{ marginTop: 8, padding: '8px 16px', background: '#8b5cf6', border: 'none',
color: '#fff', borderRadius: 8, cursor: 'pointer', fontSize: 12 }}
>
Reload
</button>
</div>
)
}
return this.props.children
}
}
ReactDOM.createRoot(document.getElementById('root')!).render(
<ErrorBoundary>
<App />
</ErrorBoundary>
)