Files
e-tib.com/app/[locale]/error.tsx
Marc Mintel 843d61cd5d
Some checks failed
Build & Deploy / 🔍 Prepare (push) Successful in 23s
Build & Deploy / 🧪 QA (push) Failing after 1m8s
Build & Deploy / 🏗️ Build (push) Has been skipped
Build & Deploy / 🚀 Deploy (push) Has been skipped
Build & Deploy / 🧪 Post-Deploy Verification (push) Has been skipped
Build & Deploy / 🔔 Notify (push) Successful in 1s
feat: overhaul competence pages, unify brand colors, and polish site integrity
- Rewrote all 5 competence pages (Kabeltiefbau, Bohrtechnik, Glasfaser, Planung, Vermessung) with factual data from references
- Unified brand colors: replaced toxic neon green with brand-aligned teal (#10a379)
- Fixed ReferencesSlider injection in dynamic MDX pages
- Enhanced Footer with icon parity, improved branding placement, and unified hover effects
- Refined Header with 3D micro-animations and improved dropdown visibility
- Fixed localized tracking API (rewrites for /stats/api/send)
- Resolved ReferenceErrors in InteractiveGermanyMap and Header state management
- Cleaned reference titles and truncated metadata in lists
2026-05-15 21:07:25 +02:00

165 lines
8.1 KiB
TypeScript

'use client';
import { useEffect } from 'react';
import { useTranslations } from 'next-intl';
import { getAppServices } from '@/lib/services/create-services';
import { Button, Heading } from '@/components/ui';
import { Terminal, Activity, AlertTriangle, RefreshCw, Home, ShieldAlert } from 'lucide-react';
import { motion } from 'framer-motion';
export default function Error({
error,
reset,
}: {
error: Error & { digest?: string };
reset: () => void;
}) {
const t = useTranslations('Error');
useEffect(() => {
// Force standard solid header
document.body.setAttribute('data-header-variant', 'standard');
// Treat "Failed to find Server Action" as a deployment sync issue and reload
if (error?.message?.includes('Failed to find Server Action')) {
window.location.reload();
return;
}
const services = getAppServices();
services.errors.captureException(error);
services.logger.error('Application error caught by boundary', {
message: error?.message || 'Unknown error',
stack: error?.stack,
digest: error?.digest,
});
return () => {
document.body.removeAttribute('data-header-variant');
};
}, [error]);
return (
<div className="relative min-h-screen flex flex-col items-center justify-center overflow-hidden bg-[#050B14] py-24 px-4">
{/* Industrial Blueprint Background */}
<div className="absolute inset-0 opacity-[0.03] pointer-events-none">
<div className="absolute inset-0 bg-[linear-gradient(to_right,#ffffff_1px,transparent_1px),linear-gradient(to_bottom,#ffffff_1px,transparent_1px)] bg-[size:100px_100px]" />
<div className="absolute inset-0 bg-[linear-gradient(to_right,#ffffff_1px,transparent_1px),linear-gradient(to_bottom,#ffffff_1px,transparent_1px)] bg-[size:20px_20px]" />
</div>
{/* Decorative Technical Annotations */}
<div className="absolute inset-0 pointer-events-none overflow-hidden select-none">
<div className="absolute top-40 left-10 text-[10px] font-mono text-primary/30 uppercase tracking-[0.2em] rotate-90 origin-left">
System_Core_Access :: Restricted
</div>
<div className="absolute bottom-40 right-10 text-[10px] font-mono text-primary/30 uppercase tracking-[0.2em] -rotate-90 origin-right">
Protocol_Failure :: Type_500
</div>
<div className="absolute top-1/4 right-20 w-32 h-px bg-primary/20" />
<div className="absolute top-1/4 right-20 w-px h-32 bg-primary/20" />
</div>
{/* Background Glow */}
<div className="absolute top-1/2 left-1/2 -translate-x-1/2 -translate-y-1/2 w-[600px] h-[600px] bg-red-500/10 blur-[150px] rounded-full pointer-events-none animate-pulse" />
<div className="relative z-10 w-full max-w-4xl mx-auto flex flex-col items-center">
{/* The "Broken" Machine Visual */}
<div className="relative mb-12">
<motion.div
initial={{ opacity: 0, scale: 0.8 }}
animate={{ opacity: 1, scale: 1 }}
className="relative"
>
<h1 className="text-[12rem] md:text-[18rem] font-heading font-black leading-none select-none">
<span className="relative inline-block text-transparent bg-clip-text bg-gradient-to-b from-white to-white/5 drop-shadow-[0_0_50px_rgba(255,255,255,0.1)]">
500
{/* Glitch Layers */}
<span className="absolute inset-0 text-red-500/30 translate-x-[2px] -translate-y-[1px] mix-blend-screen animate-pulse pointer-events-none">500</span>
<span className="absolute inset-0 text-blue-500/30 -translate-x-[2px] translate-y-[1px] mix-blend-screen animate-pulse pointer-events-none">500</span>
</span>
</h1>
{/* Warning Overlay */}
<div className="absolute top-1/2 left-1/2 -translate-x-1/2 -translate-y-1/2 flex flex-col items-center">
<motion.div
animate={{
opacity: [0.4, 1, 0.4],
scale: [0.95, 1.05, 0.95]
}}
transition={{ duration: 2, repeat: Infinity }}
className="p-4 rounded-2xl bg-red-500/20 border border-red-500/40 backdrop-blur-md shadow-[0_0_30px_rgba(239,68,68,0.3)]"
>
<ShieldAlert className="w-12 h-12 text-red-500" />
</motion.div>
</div>
</motion.div>
</div>
<div className="grid grid-cols-1 md:grid-cols-12 gap-8 w-full items-start">
{/* Main Content */}
<div className="md:col-span-7 text-center md:text-left">
<div className="inline-flex items-center gap-3 px-4 py-2 mb-6 rounded-lg bg-red-500/10 border border-red-500/20 text-[10px] font-mono uppercase tracking-widest text-red-400">
<Activity className="w-4 h-4 animate-pulse" />
CRITICAL_SYSTEM_OVERRIDE :: ACTIVE
</div>
<Heading level={1} className="text-3xl md:text-5xl font-bold mb-6 text-white leading-tight">
{t('title')}
</Heading>
<p className="text-white/50 mb-10 max-w-lg text-lg leading-relaxed">
{t('description')}
</p>
<div className="flex flex-col sm:flex-row gap-4 justify-center md:justify-start">
<Button
onClick={() => reset()}
variant="primary"
className="group h-14 px-10 shadow-[0_0_30px_rgba(var(--color-primary),0.2)] hover:shadow-primary/40 transition-all"
>
<RefreshCw className="w-5 h-5 mr-3 group-hover:rotate-180 transition-transform duration-700" />
{t('tryAgain')}
</Button>
<Button
href="/"
variant="outline"
className="h-14 px-8 border-white/10 text-white hover:bg-white/5"
>
<Home className="w-5 h-5 mr-3" />
{t('goHome')}
</Button>
</div>
</div>
{/* Technical Log Terminal */}
<div className="md:col-span-5">
<div className="bg-black/40 backdrop-blur-xl border border-white/10 rounded-2xl overflow-hidden shadow-2xl">
<div className="bg-white/5 px-4 py-2 border-b border-white/10 flex items-center justify-between">
<div className="flex gap-1.5">
<div className="w-2.5 h-2.5 rounded-full bg-red-500/50" />
<div className="w-2.5 h-2.5 rounded-full bg-yellow-500/50" />
<div className="w-2.5 h-2.5 rounded-full bg-green-500/50" />
</div>
<div className="text-[10px] font-mono text-white/30 tracking-wider">TERMINAL_OUTPUT</div>
</div>
<div className="p-6 font-mono text-xs leading-relaxed overflow-hidden h-[240px]">
<div className="text-primary/70 mb-1 animate-[fade-in_0.5s_ease-out_forwards]">[SYSTEM] Initializing recovery protocol...</div>
<div className="text-red-500/80 mb-1 animate-[fade-in_0.5s_ease-out_0.5s_forwards] opacity-0">[ERROR] Connection timeout at node 0x7F</div>
<div className="text-white/40 mb-1 animate-[fade-in_0.5s_ease-out_1s_forwards] opacity-0">[INFO] Request ID: {error?.digest || '0xDEADBEEF'}</div>
<div className="text-white/40 mb-1 animate-[fade-in_0.5s_ease-out_1.5s_forwards] opacity-0">[INFO] Timestamp: {new Date().toISOString()}</div>
<div className="text-white/40 mb-1 animate-[fade-in_0.5s_ease-out_2s_forwards] opacity-0">[INFO] Trace: {error?.message?.slice(0, 40)}...</div>
<div className="text-primary/70 mt-4 animate-[pulse_1.5s_infinite] opacity-0 animate-[fade-in_0.5s_ease-out_2.5s_forwards]">_ Waiting for user input...</div>
</div>
<div className="bg-red-500/10 p-3 flex items-center gap-3">
<Terminal className="w-4 h-4 text-red-400" />
<div className="text-[10px] font-bold text-red-400 uppercase tracking-tighter">Status: Handshake_Failed</div>
</div>
</div>
</div>
</div>
</div>
</div>
);
}