import { useId, useMemo } from 'react'; import { useApp } from '../../app/AppProvider'; import type { AssessmentContextResponse } from '../../api/assessor-api-contract'; import { contextHeatmap, contextHeatmapFindingCount, contextSeverityLabels } from '../../assessment-context/context-heatmap'; import { useAssessmentContext } from './use-assessment-context'; import './context-heatmap.css'; /** Existing scoped Context request is shared with Work and the Finding Reader. */ export function ClientContextHeatmap({ onOpenCluster }: { onOpenCluster(clusterId: string): void }) { const app = useApp(); const state = useAssessmentContext(Boolean(app.dataset), app.targetProjectId, app.activeAssessmentIds, app.activeScanRunIds, app.dataset); if (state.status === 'off' || state.status === 'unavailable') return null; if (state.status === 'loading') return Context heatmapLoading Context… ; if (state.status === 'error') return Context heatmapContext could not be loaded. Reopen the client to retry. ; return ; } export function ContextHeatmap({ context, onOpenCluster }: { context: AssessmentContextResponse; onOpenCluster(clusterId: string): void }) { const id = useId(); const cells = useMemo(() => contextHeatmap(context), [context]); const findingCount = useMemo(() => contextHeatmapFindingCount(context), [context]); return Context heatmap Findings: {findingCount.toLocaleString('en-US')} {cells.map(({ cluster: item, reference, hasEvidence, scannerDeviations, gpoDeviations }) => onOpenCluster(item.clusterId)}> Base Severity · {contextSeverityLabels[reference.severity]} {item.label.en} {(scannerDeviations + gpoDeviations).toLocaleString('en-US')} {scannerDeviations + gpoDeviations === 1 ? 'finding' : 'findings'} )} ; }
Loading Context…
Context could not be loaded. Reopen the client to retry.