Initial commit
Build check / build (push) Has been cancelled

This commit is contained in:
2026-05-07 19:31:21 -07:00
commit 02bfea8f02
110 changed files with 18550 additions and 0 deletions
@@ -0,0 +1,68 @@
import { AlertTriangle, RefreshCw } from 'lucide-react';
import { Component, type ErrorInfo, type ReactNode } from 'react';
import log from 'electron-log/renderer';
import TextButton from './styled/TextButton';
type Props = {
tabName: string;
children: ReactNode;
};
type State = {
error?: Error;
componentStack?: string;
};
class TabErrorBoundary extends Component<Props, State> {
state: State = {};
static getDerivedStateFromError(error: Error): State {
return { error };
}
componentDidCatch(error: Error, info: ErrorInfo) {
log.error(`Tab "${this.props.tabName}" crashed:`, error, info);
this.setState({ error, componentStack: info.componentStack ?? undefined });
}
componentDidUpdate(prevProps: Props) {
if (prevProps.tabName !== this.props.tabName) {
this.setState({ error: undefined, componentStack: undefined });
}
}
#reset = () => this.setState({ error: undefined, componentStack: undefined });
render() {
if (!this.state.error) return this.props.children;
const { error, componentStack } = this.state;
return (
<div className="tw-surface flex min-h-0 flex-grow flex-col gap-3">
<div className="flex items-center gap-2">
<AlertTriangle size={22} className="text-red" />
<h4 className="text-red">{this.props.tabName} crashed</h4>
</div>
<hr />
<p className="text-white">
{error.name}: {error.message}
</p>
{componentStack && (
<pre className="s1 max-h-[200px] overflow-auto whitespace-pre-wrap text-blueGray">
{componentStack.trim()}
</pre>
)}
<hr />
<TextButton
icon={RefreshCw}
onClick={this.#reset}
className="self-end text-warmGreen"
>
Try again
</TextButton>
</div>
);
}
}
export default TabErrorBoundary;