refactor: Admin-Layout komplett entfernt — SDK als einziges Layout
All checks were successful
CI / go-lint (push) Has been skipped
CI / python-lint (push) Has been skipped
CI / nodejs-lint (push) Has been skipped
CI / test-go-ai-compliance (push) Successful in 32s
CI / test-python-backend-compliance (push) Successful in 31s
CI / test-python-document-crawler (push) Successful in 21s
CI / test-python-dsms-gateway (push) Successful in 19s
All checks were successful
CI / go-lint (push) Has been skipped
CI / python-lint (push) Has been skipped
CI / nodejs-lint (push) Has been skipped
CI / test-go-ai-compliance (push) Successful in 32s
CI / test-python-backend-compliance (push) Successful in 31s
CI / test-python-document-crawler (push) Successful in 21s
CI / test-python-dsms-gateway (push) Successful in 19s
Kaputtes (admin) Layout geloescht (Role-Selection, 404-Sidebar, localhost-Dashboard). SDK-Flow nach /sdk/sdk-flow verschoben. Route-Gruppe (sdk) aufgeloest. Root-Seite redirected auf /sdk. ~25 ungenutzte Dateien/Verzeichnisse entfernt. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
This commit is contained in:
215
admin-compliance/app/sdk/tom-generator/page.tsx
Normal file
215
admin-compliance/app/sdk/tom-generator/page.tsx
Normal file
@@ -0,0 +1,215 @@
|
||||
'use client'
|
||||
|
||||
import React from 'react'
|
||||
import { useRouter } from 'next/navigation'
|
||||
import { useTOMGenerator } from '@/lib/sdk/tom-generator'
|
||||
import { TOM_GENERATOR_STEPS } from '@/lib/sdk/tom-generator/types'
|
||||
|
||||
/**
|
||||
* TOM Generator Landing Page
|
||||
*
|
||||
* Shows overview of the wizard and allows starting or resuming.
|
||||
*/
|
||||
export default function TOMGeneratorPage() {
|
||||
const router = useRouter()
|
||||
const { state, resetState } = useTOMGenerator()
|
||||
|
||||
// Calculate progress
|
||||
const completedSteps = state.steps.filter((s) => s.completed).length
|
||||
const totalSteps = state.steps.length
|
||||
const progressPercent = totalSteps > 0 ? Math.round((completedSteps / totalSteps) * 100) : 0
|
||||
|
||||
// Determine the current step URL
|
||||
const currentStepConfig = TOM_GENERATOR_STEPS.find((s) => s.id === state.currentStep)
|
||||
const currentStepUrl = currentStepConfig?.url || '/sdk/tom-generator/scope'
|
||||
|
||||
const handleStartNew = () => {
|
||||
resetState()
|
||||
router.push('/sdk/tom-generator/scope')
|
||||
}
|
||||
|
||||
const handleResume = () => {
|
||||
router.push(currentStepUrl)
|
||||
}
|
||||
|
||||
const hasProgress = completedSteps > 0
|
||||
|
||||
return (
|
||||
<div className="max-w-4xl mx-auto px-4 py-8">
|
||||
{/* Header */}
|
||||
<div className="mb-8">
|
||||
<h1 className="text-3xl font-bold text-gray-900">TOM Generator</h1>
|
||||
<p className="mt-2 text-gray-600">
|
||||
Leiten Sie Ihre Technischen und Organisatorischen Massnahmen (TOMs) nach Art. 32 DSGVO
|
||||
systematisch ab und dokumentieren Sie diese.
|
||||
</p>
|
||||
</div>
|
||||
|
||||
{/* Progress Card */}
|
||||
{hasProgress && (
|
||||
<div className="bg-white rounded-xl border border-gray-200 p-6 mb-8">
|
||||
<div className="flex items-center justify-between mb-4">
|
||||
<h2 className="text-lg font-semibold text-gray-900">Ihr Fortschritt</h2>
|
||||
<span className="text-sm text-gray-500">
|
||||
{completedSteps} von {totalSteps} Schritten abgeschlossen
|
||||
</span>
|
||||
</div>
|
||||
|
||||
{/* Progress Bar */}
|
||||
<div className="h-3 bg-gray-100 rounded-full overflow-hidden mb-4">
|
||||
<div
|
||||
className="h-full bg-gradient-to-r from-blue-500 to-purple-500 transition-all duration-500"
|
||||
style={{ width: `${progressPercent}%` }}
|
||||
/>
|
||||
</div>
|
||||
|
||||
{/* Steps Overview */}
|
||||
<div className="grid grid-cols-2 md:grid-cols-3 gap-3">
|
||||
{TOM_GENERATOR_STEPS.map((step, index) => {
|
||||
const stepState = state.steps.find((s) => s.id === step.id)
|
||||
const isCompleted = stepState?.completed
|
||||
const isCurrent = state.currentStep === step.id
|
||||
|
||||
return (
|
||||
<button
|
||||
key={step.id}
|
||||
onClick={() => router.push(step.url)}
|
||||
className={`flex items-center gap-3 p-3 rounded-lg border transition-all ${
|
||||
isCompleted
|
||||
? 'bg-green-50 border-green-200 text-green-700'
|
||||
: isCurrent
|
||||
? 'bg-blue-50 border-blue-200 text-blue-700'
|
||||
: 'bg-gray-50 border-gray-200 text-gray-500 hover:bg-gray-100'
|
||||
}`}
|
||||
>
|
||||
<div
|
||||
className={`w-8 h-8 rounded-full flex items-center justify-center text-sm font-medium ${
|
||||
isCompleted
|
||||
? 'bg-green-500 text-white'
|
||||
: isCurrent
|
||||
? 'bg-blue-500 text-white'
|
||||
: 'bg-gray-200 text-gray-500'
|
||||
}`}
|
||||
>
|
||||
{isCompleted ? (
|
||||
<svg className="w-4 h-4" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
||||
<path strokeLinecap="round" strokeLinejoin="round" strokeWidth={2} d="M5 13l4 4L19 7" />
|
||||
</svg>
|
||||
) : (
|
||||
index + 1
|
||||
)}
|
||||
</div>
|
||||
<span className="text-sm font-medium">{step.name}</span>
|
||||
</button>
|
||||
)
|
||||
})}
|
||||
</div>
|
||||
|
||||
{/* Actions */}
|
||||
<div className="flex gap-3 mt-6">
|
||||
<button
|
||||
onClick={handleResume}
|
||||
className="flex-1 px-4 py-3 bg-blue-600 text-white rounded-lg hover:bg-blue-700 transition-colors font-medium"
|
||||
>
|
||||
Fortfahren
|
||||
</button>
|
||||
<button
|
||||
onClick={handleStartNew}
|
||||
className="px-4 py-3 border border-gray-300 text-gray-700 rounded-lg hover:bg-gray-50 transition-colors"
|
||||
>
|
||||
Neu starten
|
||||
</button>
|
||||
</div>
|
||||
</div>
|
||||
)}
|
||||
|
||||
{/* Introduction Card */}
|
||||
<div className="bg-white rounded-xl border border-gray-200 p-6 mb-8">
|
||||
<h2 className="text-lg font-semibold text-gray-900 mb-4">Was ist der TOM Generator?</h2>
|
||||
<p className="text-gray-600 mb-4">
|
||||
Der TOM Generator fuehrt Sie in 6 Schritten durch die Erstellung Ihrer DSGVO-konformen
|
||||
Technischen und Organisatorischen Massnahmen:
|
||||
</p>
|
||||
|
||||
<div className="space-y-3">
|
||||
{TOM_GENERATOR_STEPS.map((step, index) => (
|
||||
<div key={step.id} className="flex items-start gap-3">
|
||||
<div className="w-6 h-6 rounded-full bg-blue-100 text-blue-600 flex items-center justify-center text-sm font-medium flex-shrink-0">
|
||||
{index + 1}
|
||||
</div>
|
||||
<div>
|
||||
<div className="font-medium text-gray-900">{step.name}</div>
|
||||
<div className="text-sm text-gray-500">{step.description.de}</div>
|
||||
</div>
|
||||
</div>
|
||||
))}
|
||||
</div>
|
||||
|
||||
{!hasProgress && (
|
||||
<button
|
||||
onClick={handleStartNew}
|
||||
className="w-full mt-6 px-4 py-3 bg-blue-600 text-white rounded-lg hover:bg-blue-700 transition-colors font-medium"
|
||||
>
|
||||
Jetzt starten
|
||||
</button>
|
||||
)}
|
||||
</div>
|
||||
|
||||
{/* Features */}
|
||||
<div className="grid md:grid-cols-3 gap-4">
|
||||
<div className="bg-white rounded-xl border border-gray-200 p-6">
|
||||
<div className="w-10 h-10 rounded-lg bg-purple-100 flex items-center justify-center mb-4">
|
||||
<svg className="w-5 h-5 text-purple-600" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
||||
<path strokeLinecap="round" strokeLinejoin="round" strokeWidth={2} d="M9 12l2 2 4-4m5.618-4.016A11.955 11.955 0 0112 2.944a11.955 11.955 0 01-8.618 3.04A12.02 12.02 0 003 9c0 5.591 3.824 10.29 9 11.622 5.176-1.332 9-6.03 9-11.622 0-1.042-.133-2.052-.382-3.016z" />
|
||||
</svg>
|
||||
</div>
|
||||
<h3 className="font-semibold text-gray-900 mb-2">60+ Kontrollen</h3>
|
||||
<p className="text-sm text-gray-500">
|
||||
Vordefinierte Kontrollen mit Mapping zu DSGVO, ISO 27001 und BSI-Grundschutz
|
||||
</p>
|
||||
</div>
|
||||
|
||||
<div className="bg-white rounded-xl border border-gray-200 p-6">
|
||||
<div className="w-10 h-10 rounded-lg bg-green-100 flex items-center justify-center mb-4">
|
||||
<svg className="w-5 h-5 text-green-600" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
||||
<path strokeLinecap="round" strokeLinejoin="round" strokeWidth={2} d="M9 19v-6a2 2 0 00-2-2H5a2 2 0 00-2 2v6a2 2 0 002 2h2a2 2 0 002-2zm0 0V9a2 2 0 012-2h2a2 2 0 012 2v10m-6 0a2 2 0 002 2h2a2 2 0 002-2m0 0V5a2 2 0 012-2h2a2 2 0 012 2v14a2 2 0 01-2 2h-2a2 2 0 01-2-2z" />
|
||||
</svg>
|
||||
</div>
|
||||
<h3 className="font-semibold text-gray-900 mb-2">Lueckenanalyse</h3>
|
||||
<p className="text-sm text-gray-500">
|
||||
Automatische Identifikation fehlender Massnahmen mit Handlungsempfehlungen
|
||||
</p>
|
||||
</div>
|
||||
|
||||
<div className="bg-white rounded-xl border border-gray-200 p-6">
|
||||
<div className="w-10 h-10 rounded-lg bg-blue-100 flex items-center justify-center mb-4">
|
||||
<svg className="w-5 h-5 text-blue-600" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
||||
<path strokeLinecap="round" strokeLinejoin="round" strokeWidth={2} d="M12 10v6m0 0l-3-3m3 3l3-3m2 8H7a2 2 0 01-2-2V5a2 2 0 012-2h5.586a1 1 0 01.707.293l5.414 5.414a1 1 0 01.293.707V19a2 2 0 01-2 2z" />
|
||||
</svg>
|
||||
</div>
|
||||
<h3 className="font-semibold text-gray-900 mb-2">Export</h3>
|
||||
<p className="text-sm text-gray-500">
|
||||
Generieren Sie Ihre TOM-Dokumentation als Word, PDF oder strukturiertes JSON
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
{/* Legal Note */}
|
||||
<div className="mt-8 p-4 bg-blue-50 rounded-lg border border-blue-200">
|
||||
<div className="flex gap-3">
|
||||
<svg className="w-5 h-5 text-blue-600 flex-shrink-0 mt-0.5" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
||||
<path strokeLinecap="round" strokeLinejoin="round" strokeWidth={2} d="M13 16h-1v-4h-1m1-4h.01M21 12a9 9 0 11-18 0 9 9 0 0118 0z" />
|
||||
</svg>
|
||||
<div>
|
||||
<div className="font-medium text-blue-900">Hinweis zur Rechtsgrundlage</div>
|
||||
<p className="text-sm text-blue-700 mt-1">
|
||||
Die generierten TOMs basieren auf Art. 32 DSGVO. Die Auswahl der konkreten Massnahmen
|
||||
sollte immer unter Beruecksichtigung des Stands der Technik, der Implementierungskosten
|
||||
und der Art, des Umfangs und der Zwecke der Verarbeitung erfolgen.
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
)
|
||||
}
|
||||
Reference in New Issue
Block a user