Init
This commit is contained in:
@@ -0,0 +1,42 @@
|
||||
import React from 'react';
|
||||
import { ScheduleItem } from '../types';
|
||||
|
||||
interface LiveOrdersTableProps {
|
||||
orders: ScheduleItem[];
|
||||
}
|
||||
|
||||
export const LiveOrdersTable: React.FC<LiveOrdersTableProps> = ({ orders }) => {
|
||||
return (
|
||||
<div className="content-card">
|
||||
<h2 className="card-heading">Heutige Live-Aufträge (Dispatching)</h2>
|
||||
<table className="orders-table">
|
||||
<thead>
|
||||
<tr>
|
||||
<th>Kunde</th>
|
||||
<th>Monteur</th>
|
||||
<th>Status</th>
|
||||
</tr>
|
||||
</thead>
|
||||
<tbody>
|
||||
{orders.map((order) => (
|
||||
<tr key={order.id}>
|
||||
<td style={{ fontWeight: 600, color: '#0f172a' }}>{order.customerName}</td>
|
||||
<td style={{ color: '#334155' }}>{order.technicianName}</td>
|
||||
<td>
|
||||
<span
|
||||
className={`badge ${
|
||||
order.status === 'In Bearbeitung'
|
||||
? 'badge-in-progress'
|
||||
: 'badge-scheduled'
|
||||
}`}
|
||||
>
|
||||
{order.status === 'Geplant' ? `Geplant (${order.startTime})` : order.status}
|
||||
</span>
|
||||
</td>
|
||||
</tr>
|
||||
))}
|
||||
</tbody>
|
||||
</table>
|
||||
</div>
|
||||
);
|
||||
};
|
||||
@@ -0,0 +1,56 @@
|
||||
import React from 'react';
|
||||
import {
|
||||
Wrench,
|
||||
LayoutDashboard,
|
||||
CalendarDays,
|
||||
Package,
|
||||
Users,
|
||||
Clock,
|
||||
Database
|
||||
} from 'lucide-react';
|
||||
|
||||
interface SidebarProps {
|
||||
activeTab: string;
|
||||
setActiveTab: (tab: string) => void;
|
||||
}
|
||||
|
||||
export const Sidebar: React.FC<SidebarProps> = ({ activeTab, setActiveTab }) => {
|
||||
const menuItems = [
|
||||
{ id: 'dashboard', label: 'Dashboard', icon: LayoutDashboard },
|
||||
{ id: 'dispatching', label: 'Dispatching', icon: CalendarDays },
|
||||
{ id: 'lager', label: 'Lager & Teile', icon: Package },
|
||||
{ id: 'monteure', label: 'Monteure', icon: Users },
|
||||
{ id: 'zeiterfassung', label: 'Zeiterfassung', icon: Clock },
|
||||
{ id: 'supabase', label: 'Supabase Sync', icon: Database },
|
||||
];
|
||||
|
||||
return (
|
||||
<aside className="sidebar">
|
||||
<div className="brand">
|
||||
<Wrench className="brand-icon" size={24} />
|
||||
<span>Handwerksfreund</span>
|
||||
</div>
|
||||
|
||||
<nav>
|
||||
<ul className="nav-list">
|
||||
{menuItems.map((item) => {
|
||||
const Icon = item.icon;
|
||||
const isActive = activeTab === item.id;
|
||||
return (
|
||||
<li key={item.id}>
|
||||
<button
|
||||
className={`nav-item ${isActive ? 'active' : ''}`}
|
||||
onClick={() => setActiveTab(item.id)}
|
||||
style={{ width: '100%', background: 'none', border: 'none', textAlign: 'left' }}
|
||||
>
|
||||
<Icon className="icon" size={20} />
|
||||
<span>{item.label}</span>
|
||||
</button>
|
||||
</li>
|
||||
);
|
||||
})}
|
||||
</ul>
|
||||
</nav>
|
||||
</aside>
|
||||
);
|
||||
};
|
||||
@@ -0,0 +1,16 @@
|
||||
import React from 'react';
|
||||
|
||||
interface StatCardProps {
|
||||
label: string;
|
||||
value: string;
|
||||
isWarning?: boolean;
|
||||
}
|
||||
|
||||
export const StatCard: React.FC<StatCardProps> = ({ label, value, isWarning }) => {
|
||||
return (
|
||||
<div className="kpi-card">
|
||||
<span className="kpi-label">{label}</span>
|
||||
<span className={`kpi-value ${isWarning ? 'warning' : ''}`}>{value}</span>
|
||||
</div>
|
||||
);
|
||||
};
|
||||
@@ -0,0 +1,37 @@
|
||||
import React from 'react';
|
||||
import { SystemStatus } from '../types';
|
||||
|
||||
interface SystemStatusCardProps {
|
||||
status: SystemStatus | null;
|
||||
}
|
||||
|
||||
export const SystemStatusCard: React.FC<SystemStatusCardProps> = ({ status }) => {
|
||||
const host = status?.host || 'supabase.marc-wieland.de';
|
||||
const latency = status?.latencyMs ?? 18;
|
||||
|
||||
return (
|
||||
<div className="content-card">
|
||||
<h2 className="card-heading">Supabase System-Status</h2>
|
||||
<p className="status-panel-description">
|
||||
Datenbank-Verbindung und Realtime-Sync laufen stabil.
|
||||
</p>
|
||||
|
||||
<div className="status-details-box">
|
||||
<div className="status-item">
|
||||
<span className="status-key">DB Host:</span>
|
||||
<span className="status-val">{host}</span>
|
||||
</div>
|
||||
|
||||
<div className="status-item">
|
||||
<span className="status-key">Latency:</span>
|
||||
<span className="status-val">{latency}ms</span>
|
||||
</div>
|
||||
|
||||
<div className="status-item">
|
||||
<span className="status-key">Letzter Sync:</span>
|
||||
<span className="status-val">Vor wenigen Sekunden</span>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
);
|
||||
};
|
||||
Reference in New Issue
Block a user