website refactor

This commit is contained in:
2026-01-18 16:18:18 +01:00
parent 0b301feb61
commit 13567d51af
329 changed files with 4701 additions and 4750 deletions

View File

@@ -5,14 +5,14 @@ import { X, RefreshCw, Copy, Terminal, Activity, AlertTriangle } from 'lucide-re
import { ApiError } from '@/lib/api/base/ApiError';
import { connectionMonitor } from '@/lib/api/base/ApiConnectionMonitor';
import { CircuitBreakerRegistry } from '@/lib/api/base/RetryHandler';
import { Box } from '@/ui/Box';
import { Text } from '@/ui/Text';
import { Stack } from '@/ui/Stack';
import { Text } from '@/ui/Text';
import { Icon } from '@/ui/Icon';
import { Badge } from '@/ui/Badge';
import { Button } from '@/ui/Button';
import { Heading } from '@/ui/Heading';
import { Surface } from '@/ui/Surface';
import { Card } from '@/ui/Card';
import { Grid } from '@/ui/Grid';
interface DevErrorPanelProps {
error: ApiError;
@@ -100,7 +100,7 @@ export function DevErrorPanel({ error, onReset }: DevErrorPanelProps) {
const reliability = connectionMonitor.getReliability();
return (
<Box
<Stack
position="fixed"
inset="0"
zIndex={50}
@@ -108,18 +108,18 @@ export function DevErrorPanel({ error, onReset }: DevErrorPanelProps) {
bg="bg-deep-graphite"
p={4}
>
<Box maxWidth="6xl" mx="auto">
<Stack maxWidth="6xl" mx="auto" fullWidth>
<Stack gap={4}>
{/* Header */}
<Box bg="bg-iron-gray" border borderColor="border-charcoal-outline" rounded="lg" p={4} display="flex" alignItems="center" justifyContent="between">
<Box display="flex" alignItems="center" gap={3}>
<Stack bg="bg-iron-gray" border borderColor="border-charcoal-outline" rounded="lg" p={4} direction="row" align="center" justify="between">
<Stack direction="row" align="center" gap={3}>
<Icon icon={Terminal} size={5} color="rgb(59, 130, 246)" />
<Heading level={2}>API Error Debug Panel</Heading>
<Badge variant={getSeverityVariant()}>
{error.type}
</Badge>
</Box>
<Box display="flex" gap={2}>
</Stack>
<Stack direction="row" gap={2}>
<Button
variant="secondary"
onClick={copyToClipboard}
@@ -134,141 +134,141 @@ export function DevErrorPanel({ error, onReset }: DevErrorPanelProps) {
>
Close
</Button>
</Box>
</Box>
</Stack>
</Stack>
{/* Error Details */}
<Box display="grid" gridCols={{ base: 1, lg: 2 }} gap={4}>
<Grid cols={1} lgCols={2} gap={4}>
<Stack gap={4}>
<Surface variant="muted" rounded="lg" overflow="hidden" border borderColor="border-charcoal-outline">
<Box bg="bg-charcoal-outline" px={4} py={2} display="flex" alignItems="center" gap={2}>
<Card p={0} rounded="lg" overflow="hidden" variant="outline" borderColor="border-charcoal-outline" className="bg-panel-gray/40">
<Stack bg="bg-charcoal-outline" px={4} py={2} direction="row" align="center" gap={2}>
<Icon icon={AlertTriangle} size={4} color="text-white" />
<Text weight="semibold" color="text-white">Error Details</Text>
</Box>
<Box p={4}>
<Stack gap={2} fontSize="0.75rem">
<Box display="grid" gridCols={3} gap={2}>
</Stack>
<Stack p={4}>
<Stack gap={2} style={{ fontSize: '0.75rem' }}>
<Grid cols={3} gap={2}>
<Text color="text-gray-500">Type:</Text>
<Text colSpan={2} color="text-red-400" weight="bold">{error.type}</Text>
</Box>
<Box display="grid" gridCols={3} gap={2}>
<Text className="col-span-2" color="text-red-400" weight="bold">{error.type}</Text>
</Grid>
<Grid cols={3} gap={2}>
<Text color="text-gray-500">Message:</Text>
<Text colSpan={2} color="text-gray-300">{error.message}</Text>
</Box>
<Box display="grid" gridCols={3} gap={2}>
<Text className="col-span-2" color="text-gray-300">{error.message}</Text>
</Grid>
<Grid cols={3} gap={2}>
<Text color="text-gray-500">Endpoint:</Text>
<Text colSpan={2} color="text-primary-blue">{error.context.endpoint || 'N/A'}</Text>
</Box>
<Box display="grid" gridCols={3} gap={2}>
<Text className="col-span-2" color="text-primary-blue">{error.context.endpoint || 'N/A'}</Text>
</Grid>
<Grid cols={3} gap={2}>
<Text color="text-gray-500">Method:</Text>
<Text colSpan={2} color="text-warning-amber">{error.context.method || 'N/A'}</Text>
</Box>
<Box display="grid" gridCols={3} gap={2}>
<Text className="col-span-2" color="text-warning-amber">{error.context.method || 'N/A'}</Text>
</Grid>
<Grid cols={3} gap={2}>
<Text color="text-gray-500">Status:</Text>
<Text colSpan={2}>{error.context.statusCode || 'N/A'}</Text>
</Box>
<Box display="grid" gridCols={3} gap={2}>
<Text className="col-span-2">{error.context.statusCode || 'N/A'}</Text>
</Grid>
<Grid cols={3} gap={2}>
<Text color="text-gray-500">Retry Count:</Text>
<Text colSpan={2}>{error.context.retryCount || 0}</Text>
</Box>
<Box display="grid" gridCols={3} gap={2}>
<Text className="col-span-2">{error.context.retryCount || 0}</Text>
</Grid>
<Grid cols={3} gap={2}>
<Text color="text-gray-500">Timestamp:</Text>
<Text colSpan={2} color="text-gray-500">{error.context.timestamp}</Text>
</Box>
<Box display="grid" gridCols={3} gap={2}>
<Text className="col-span-2" color="text-gray-500">{error.context.timestamp}</Text>
</Grid>
<Grid cols={3} gap={2}>
<Text color="text-gray-500">Retryable:</Text>
<Text colSpan={2} color={error.isRetryable() ? 'text-performance-green' : 'text-red-400'}>
<Text className="col-span-2" color={error.isRetryable() ? 'text-performance-green' : 'text-red-400'}>
{error.isRetryable() ? 'Yes' : 'No'}
</Text>
</Box>
<Box display="grid" gridCols={3} gap={2}>
</Grid>
<Grid cols={3} gap={2}>
<Text color="text-gray-500">Connectivity:</Text>
<Text colSpan={2} color={error.isConnectivityIssue() ? 'text-red-400' : 'text-performance-green'}>
<Text className="col-span-2" color={error.isConnectivityIssue() ? 'text-red-400' : 'text-performance-green'}>
{error.isConnectivityIssue() ? 'Yes' : 'No'}
</Text>
</Box>
</Grid>
{error.context.troubleshooting && (
<Box display="grid" gridCols={3} gap={2}>
<Grid cols={3} gap={2}>
<Text color="text-gray-500">Troubleshoot:</Text>
<Text colSpan={2} color="text-warning-amber">{error.context.troubleshooting}</Text>
</Box>
<Text className="col-span-2" color="text-warning-amber">{error.context.troubleshooting}</Text>
</Grid>
)}
</Stack>
</Box>
</Surface>
</Stack>
</Card>
{/* Connection Status */}
<Surface variant="muted" rounded="lg" overflow="hidden" border borderColor="border-charcoal-outline">
<Box bg="bg-charcoal-outline" px={4} py={2} display="flex" alignItems="center" gap={2}>
<Card p={0} rounded="lg" overflow="hidden" variant="outline" borderColor="border-charcoal-outline" className="bg-panel-gray/40">
<Stack bg="bg-charcoal-outline" px={4} py={2} direction="row" align="center" gap={2}>
<Icon icon={Activity} size={4} color="text-white" />
<Text weight="semibold" color="text-white">Connection Health</Text>
</Box>
<Box p={4}>
<Stack gap={2} fontSize="0.75rem">
<Box display="grid" gridCols={3} gap={2}>
</Stack>
<Stack p={4}>
<Stack gap={2} style={{ fontSize: '0.75rem' }}>
<Grid cols={3} gap={2}>
<Text color="text-gray-500">Status:</Text>
<Text colSpan={2} weight="bold" color={
<Text className="col-span-2" weight="bold" color={
connectionStatus.status === 'connected' ? 'text-performance-green' :
connectionStatus.status === 'degraded' ? 'text-warning-amber' :
'text-red-400'
}>
{connectionStatus.status.toUpperCase()}
</Text>
</Box>
<Box display="grid" gridCols={3} gap={2}>
</Grid>
<Grid cols={3} gap={2}>
<Text color="text-gray-500">Reliability:</Text>
<Text colSpan={2}>{reliability.toFixed(2)}%</Text>
</Box>
<Box display="grid" gridCols={3} gap={2}>
<Text className="col-span-2">{reliability.toFixed(2)}%</Text>
</Grid>
<Grid cols={3} gap={2}>
<Text color="text-gray-500">Total Requests:</Text>
<Text colSpan={2}>{connectionStatus.totalRequests}</Text>
</Box>
<Box display="grid" gridCols={3} gap={2}>
<Text className="col-span-2">{connectionStatus.totalRequests}</Text>
</Grid>
<Grid cols={3} gap={2}>
<Text color="text-gray-500">Successful:</Text>
<Text colSpan={2} color="text-performance-green">{connectionStatus.successfulRequests}</Text>
</Box>
<Box display="grid" gridCols={3} gap={2}>
<Text className="col-span-2" color="text-performance-green">{connectionStatus.successfulRequests}</Text>
</Grid>
<Grid cols={3} gap={2}>
<Text color="text-gray-500">Failed:</Text>
<Text colSpan={2} color="text-red-400">{connectionStatus.failedRequests}</Text>
</Box>
<Box display="grid" gridCols={3} gap={2}>
<Text className="col-span-2" color="text-red-400">{connectionStatus.failedRequests}</Text>
</Grid>
<Grid cols={3} gap={2}>
<Text color="text-gray-500">Consecutive Failures:</Text>
<Text colSpan={2}>{connectionStatus.consecutiveFailures}</Text>
</Box>
<Box display="grid" gridCols={3} gap={2}>
<Text className="col-span-2">{connectionStatus.consecutiveFailures}</Text>
</Grid>
<Grid cols={3} gap={2}>
<Text color="text-gray-500">Avg Response:</Text>
<Text colSpan={2}>{connectionStatus.averageResponseTime.toFixed(2)}ms</Text>
</Box>
<Box display="grid" gridCols={3} gap={2}>
<Text className="col-span-2">{connectionStatus.averageResponseTime.toFixed(2)}ms</Text>
</Grid>
<Grid cols={3} gap={2}>
<Text color="text-gray-500">Last Check:</Text>
<Text colSpan={2} color="text-gray-500">
<Text className="col-span-2" color="text-gray-500">
{connectionStatus.lastCheck?.toLocaleTimeString() || 'Never'}
</Text>
</Box>
</Grid>
</Stack>
</Box>
</Surface>
</Stack>
</Card>
</Stack>
{/* Right Column */}
<Stack gap={4}>
{/* Circuit Breakers */}
<Surface variant="muted" rounded="lg" overflow="hidden" border borderColor="border-charcoal-outline">
<Box bg="bg-charcoal-outline" px={4} py={2} display="flex" alignItems="center" gap={2}>
<Card p={0} rounded="lg" overflow="hidden" variant="outline" borderColor="border-charcoal-outline" className="bg-panel-gray/40">
<Stack bg="bg-charcoal-outline" px={4} py={2} direction="row" align="center" gap={2}>
<Text size="lg"></Text>
<Text weight="semibold" color="text-white">Circuit Breakers</Text>
</Box>
<Box p={4}>
</Stack>
<Stack p={4}>
{Object.keys(circuitBreakers).length === 0 ? (
<Box textAlign="center" py={4}>
<Stack align="center" py={4}>
<Text color="text-gray-500">No circuit breakers active</Text>
</Box>
</Stack>
) : (
<Stack gap={2} maxHeight="12rem" overflow="auto" fontSize="0.75rem">
<Stack gap={2} maxHeight="12rem" overflow="auto" style={{ fontSize: '0.75rem' }}>
{Object.entries(circuitBreakers).map(([endpoint, status]) => (
<Box key={endpoint} display="flex" alignItems="center" justifyContent="between" p={2} bg="bg-deep-graphite" rounded="md" border borderColor="border-charcoal-outline">
<Stack key={endpoint} direction="row" align="center" justify="between" p={2} bg="bg-deep-graphite" rounded="md" border borderColor="border-charcoal-outline">
<Text color="text-primary-blue" truncate flexGrow={1}>{endpoint}</Text>
<Box px={2} py={1} rounded="sm" bg={
<Stack px={2} py={1} rounded="sm" bg={
status.state === 'CLOSED' ? 'bg-green-500/20' :
status.state === 'OPEN' ? 'bg-red-500/20' :
'bg-yellow-500/20'
@@ -280,21 +280,21 @@ export function DevErrorPanel({ error, onReset }: DevErrorPanelProps) {
}>
{status.state}
</Text>
</Box>
<Text color="text-gray-500" ml={2}>{status.failures} failures</Text>
</Box>
</Stack>
<Text color="text-gray-500" className="ml-2">{status.failures} failures</Text>
</Stack>
))}
</Stack>
)}
</Box>
</Surface>
</Stack>
</Card>
{/* Actions */}
<Surface variant="muted" rounded="lg" overflow="hidden" border borderColor="border-charcoal-outline">
<Box bg="bg-charcoal-outline" px={4} py={2}>
<Card p={0} rounded="lg" overflow="hidden" variant="outline" borderColor="border-charcoal-outline" className="bg-panel-gray/40">
<Stack bg="bg-charcoal-outline" px={4} py={2}>
<Text weight="semibold" color="text-white">Actions</Text>
</Box>
<Box p={4}>
</Stack>
<Stack p={4}>
<Stack gap={2}>
<Button
variant="primary"
@@ -324,59 +324,59 @@ export function DevErrorPanel({ error, onReset }: DevErrorPanelProps) {
Reset Connection Stats
</Button>
</Stack>
</Box>
</Surface>
</Stack>
</Card>
{/* Quick Fixes */}
<Surface variant="muted" rounded="lg" overflow="hidden" border borderColor="border-charcoal-outline">
<Box bg="bg-charcoal-outline" px={4} py={2}>
<Card p={0} rounded="lg" overflow="hidden" variant="outline" borderColor="border-charcoal-outline" className="bg-panel-gray/40">
<Stack bg="bg-charcoal-outline" px={4} py={2}>
<Text weight="semibold" color="text-white">Quick Fixes</Text>
</Box>
<Box p={4}>
<Stack gap={2} fontSize="0.75rem">
</Stack>
<Stack p={4}>
<Stack gap={2} style={{ fontSize: '0.75rem' }}>
<Text color="text-gray-400">Common solutions:</Text>
<Stack as="ul" gap={1} pl={4}>
<Box as="li"><Text color="text-gray-300">Check API server is running</Text></Box>
<Box as="li"><Text color="text-gray-300">Verify CORS configuration</Text></Box>
<Box as="li"><Text color="text-gray-300">Check environment variables</Text></Box>
<Box as="li"><Text color="text-gray-300">Review network connectivity</Text></Box>
<Box as="li"><Text color="text-gray-300">Check API rate limits</Text></Box>
<Stack as="li"><Text color="text-gray-300">Check API server is running</Text></Stack>
<Stack as="li"><Text color="text-gray-300">Verify CORS configuration</Text></Stack>
<Stack as="li"><Text color="text-gray-300">Check environment variables</Text></Stack>
<Stack as="li"><Text color="text-gray-300">Review network connectivity</Text></Stack>
<Stack as="li"><Text color="text-gray-300">Check API rate limits</Text></Stack>
</Stack>
</Stack>
</Box>
</Surface>
</Stack>
</Card>
{/* Raw Error */}
<Surface variant="muted" rounded="lg" overflow="hidden" border borderColor="border-charcoal-outline">
<Box bg="bg-charcoal-outline" px={4} py={2}>
<Card p={0} rounded="lg" overflow="hidden" variant="outline" borderColor="border-charcoal-outline" className="bg-panel-gray/40">
<Stack bg="bg-charcoal-outline" px={4} py={2}>
<Text weight="semibold" color="text-white">Raw Error</Text>
</Box>
<Box p={4}>
<Box as="pre" p={2} bg="bg-deep-graphite" rounded="md" overflow="auto" maxHeight="8rem" fontSize="0.75rem" color="text-gray-400">
</Stack>
<Stack p={4}>
<Stack as="pre" p={2} bg="bg-deep-graphite" rounded="md" overflow="auto" maxHeight="8rem" style={{ fontSize: '0.75rem' }} color="text-gray-400">
{JSON.stringify({
type: error.type,
message: error.message,
context: error.context,
}, null, 2)}
</Box>
</Box>
</Surface>
</Stack>
</Stack>
</Card>
</Stack>
</Box>
</Grid>
{/* Console Output */}
<Surface variant="muted" rounded="lg" overflow="hidden" border borderColor="border-charcoal-outline">
<Box bg="bg-charcoal-outline" px={4} py={2} display="flex" alignItems="center" gap={2}>
<Card p={0} rounded="lg" overflow="hidden" variant="outline" borderColor="border-charcoal-outline" className="bg-panel-gray/40">
<Stack bg="bg-charcoal-outline" px={4} py={2} direction="row" align="center" gap={2}>
<Icon icon={Terminal} size={4} color="text-white" />
<Text weight="semibold" color="text-white">Console Output</Text>
</Box>
<Box p={4} bg="bg-deep-graphite" fontSize="0.75rem">
</Stack>
<Stack p={4} bg="bg-deep-graphite" style={{ fontSize: '0.75rem' }}>
<Text color="text-gray-500" block mb={2}>{'>'} {error.getDeveloperMessage()}</Text>
<Text color="text-gray-600" block>Check browser console for full stack trace and additional debug info.</Text>
</Box>
</Surface>
</Stack>
</Card>
</Stack>
</Box>
</Box>
</Stack>
</Stack>
);
}