feat: remove Administration workspace — keep only Verwaltung + Suche
- Delete all ops page components (ReviewQueue, AIMonitoring, Governance, SourceMonitoring, ActivityTimeline, SignalPipeline) - Remove OPERATIONS workspace from AppShell config, nav order, path detection - Remove all /ops/* routes from App.tsx - Remove WorkspaceType.OPERATIONS from allowedWorkspaces in authService, sessionStore, permissions - Keep MarketIntelligence page (already moved to /supply/market-intelligence) Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
@@ -0,0 +1,101 @@
|
||||
import { Box, Chip, LinearProgress, Typography } from '@mui/material'
|
||||
import { SignalTypeBadge } from './SignalTypeBadge'
|
||||
import { SensitivityBadge } from './SensitivityBadge'
|
||||
import { SignalReviewStatusBadge } from './SignalReviewStatusBadge'
|
||||
import { FutureSignalDisclaimer } from './FutureSignalDisclaimer'
|
||||
import type { FutureSignal } from '../../domain/futureSignal'
|
||||
|
||||
const SOURCE_LABELS: Record<string, string> = {
|
||||
PRESS: 'Presse',
|
||||
CONSTRUCTION_PERMIT: 'Baubewilligung',
|
||||
JOB_POSTING: 'Stelleninserat',
|
||||
COMPANY_REPORT: 'Geschäftsbericht',
|
||||
MARKET_DATA: 'Marktdaten',
|
||||
MANUAL: 'Manuell',
|
||||
}
|
||||
|
||||
function probColor(p: number): string {
|
||||
return p >= 0.7 ? '#1a7a4a' : p >= 0.5 ? '#d97706' : '#c0392b'
|
||||
}
|
||||
|
||||
interface Props {
|
||||
signal: FutureSignal
|
||||
isSelected: boolean
|
||||
onSelect: (signal: FutureSignal) => void
|
||||
}
|
||||
|
||||
export function FutureSignalCard({ signal, isSelected, onSelect }: Props) {
|
||||
const isConfidential = signal.sensitivityLevel === 'CONFIDENTIAL'
|
||||
|
||||
return (
|
||||
<Box
|
||||
onClick={() => onSelect(signal)}
|
||||
sx={{
|
||||
p: 2,
|
||||
cursor: 'pointer',
|
||||
borderBottom: '1px solid #f1f5f9',
|
||||
borderLeft: isSelected
|
||||
? '3px solid #1e3a5f'
|
||||
: isConfidential
|
||||
? '3px solid #d97706'
|
||||
: '3px solid transparent',
|
||||
bgcolor: isSelected ? '#eff6ff' : isConfidential ? '#fffbeb' : 'transparent',
|
||||
'&:hover': { bgcolor: isSelected ? '#eff6ff' : '#f8fafc' },
|
||||
}}
|
||||
>
|
||||
{/* Row 1: type + sensitivity + review status */}
|
||||
<Box sx={{ display: 'flex', flexWrap: 'wrap', gap: 0.5, mb: 1 }}>
|
||||
<SignalTypeBadge type={signal.signalType} />
|
||||
<SensitivityBadge level={signal.sensitivityLevel} />
|
||||
<SignalReviewStatusBadge status={signal.reviewStatus} />
|
||||
</Box>
|
||||
|
||||
{/* Row 2: title / company / location */}
|
||||
<Typography variant="body2" sx={{ fontWeight: 600, mb: 0.25 }}>
|
||||
{signal.title ?? signal.companyName ?? signal.locationHint}
|
||||
</Typography>
|
||||
{(signal.title || signal.companyName) && (
|
||||
<Typography variant="caption" color="text.secondary" sx={{ display: 'block', mb: 0.75 }}>
|
||||
{signal.locationHint}
|
||||
</Typography>
|
||||
)}
|
||||
|
||||
{/* Row 3: probability */}
|
||||
<Box sx={{ mb: 0.75 }}>
|
||||
<Box sx={{ display: 'flex', justifyContent: 'space-between', mb: 0.25 }}>
|
||||
<Typography variant="caption" color="text.secondary">Wahrscheinlichkeit</Typography>
|
||||
<Typography variant="caption" sx={{ fontWeight: 700, color: probColor(signal.probability) }}>
|
||||
{Math.round(signal.probability * 100)}%
|
||||
</Typography>
|
||||
</Box>
|
||||
<LinearProgress
|
||||
variant="determinate"
|
||||
value={signal.probability * 100}
|
||||
sx={{
|
||||
height: 4,
|
||||
borderRadius: 2,
|
||||
bgcolor: '#f1f5f9',
|
||||
'& .MuiLinearProgress-bar': { bgcolor: probColor(signal.probability) },
|
||||
}}
|
||||
/>
|
||||
</Box>
|
||||
|
||||
{/* Row 4: meta chips */}
|
||||
<Box sx={{ display: 'flex', flexWrap: 'wrap', gap: 0.5, mb: 1 }}>
|
||||
<Chip label={`${signal.timeHorizonMonths}M`} size="small" sx={{ fontSize: 10, height: 18 }} />
|
||||
{signal.areaSqmEstimate && (
|
||||
<Chip label={`~${signal.areaSqmEstimate.toLocaleString('de-CH')} m²`} size="small" sx={{ fontSize: 10, height: 18 }} />
|
||||
)}
|
||||
<Chip
|
||||
label={SOURCE_LABELS[signal.source.type] ?? signal.source.type}
|
||||
size="small"
|
||||
variant="outlined"
|
||||
sx={{ fontSize: 10, height: 18 }}
|
||||
/>
|
||||
</Box>
|
||||
|
||||
{/* Footer: mini disclaimer */}
|
||||
<FutureSignalDisclaimer mini />
|
||||
</Box>
|
||||
)
|
||||
}
|
||||
Reference in New Issue
Block a user