Files
breakpilot-compliance/ai-compliance-sdk/internal/ucca/v2_loader_test.go
Benjamin Admin 38e278ee3c
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 29s
CI / test-python-document-crawler (push) Successful in 20s
CI / test-python-dsms-gateway (push) Successful in 18s
feat(ucca): Pflichtendatenbank v2 (325 Obligations), Trigger-Engine, TOM-Control-Mapping
- 9 Regulation-JSON-Dateien (DSGVO 80, AI Act 60, NIS2 40, BDSG 30, TTDSG 20, DSA 35, Data Act 25, EU-Maschinen 15, DORA 20)
- Condition-Tree-Engine fuer automatische Pflichtenselektion (all_of/any_of, 80+ Field-Paths)
- Generischer JSONRegulationModule-Loader mit YAML-Fallback
- Bidirektionales TOM-Control-Mapping (291 Obligation→Control, 92 Control→Obligation)
- Gap-Analyse-Engine (Compliance-%, Priority Actions, Domain Breakdown)
- ScopeDecision→UnifiedFacts Bridge fuer Auto-Profiling
- 4 neue API-Endpoints (assess-from-scope, tom-controls, gap-analysis, reverse-lookup)
- Frontend: Auto-Profiling Button, Regulation-Filter Chips, TOM-Panel, Gap-Analyse-View
- 18 Unit Tests (Condition Engine, v2 Loader, TOM Mapper)

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-03-05 14:51:44 +01:00

138 lines
3.6 KiB
Go

package ucca
import (
"os"
"testing"
)
func TestLoadV2Manifest(t *testing.T) {
manifest, err := LoadV2Manifest()
if err != nil {
t.Skipf("v2 manifest not found (expected in CI): %v", err)
}
if manifest.SchemaVersion != "2.0" {
t.Errorf("expected schema_version 2.0, got %s", manifest.SchemaVersion)
}
if len(manifest.Regulations) == 0 {
t.Error("expected at least one regulation in manifest")
}
// Check known regulations
regIDs := make(map[string]bool)
for _, r := range manifest.Regulations {
regIDs[r.ID] = true
}
for _, expected := range []string{"dsgvo", "ai_act", "nis2"} {
if !regIDs[expected] {
t.Errorf("expected regulation %s in manifest", expected)
}
}
}
func TestLoadV2RegulationFile_DSGVO(t *testing.T) {
basePath := getV2BasePath()
if _, err := os.Stat(basePath + "/dsgvo_v2.json"); os.IsNotExist(err) {
t.Skip("dsgvo_v2.json not found")
}
data, err := LoadV2RegulationFile("dsgvo_v2.json")
if err != nil {
t.Fatalf("failed to load dsgvo_v2.json: %v", err)
}
if data.Regulation != "dsgvo" {
t.Errorf("expected regulation dsgvo, got %s", data.Regulation)
}
if len(data.Obligations) < 11 {
t.Errorf("expected at least 11 DSGVO obligations (existing), got %d", len(data.Obligations))
}
// Verify first obligation preserves existing ID
if data.Obligations[0].ID != "DSGVO-OBL-001" {
t.Errorf("expected first obligation DSGVO-OBL-001, got %s", data.Obligations[0].ID)
}
// Verify v2 fields are present
obl := data.Obligations[0]
if obl.ValidFrom == "" {
t.Error("expected valid_from on first obligation")
}
if len(obl.TOMControlIDs) == 0 {
t.Error("expected tom_control_ids on first obligation")
}
}
func TestLoadV2RegulationFile_AIAct(t *testing.T) {
basePath := getV2BasePath()
if _, err := os.Stat(basePath + "/ai_act_v2.json"); os.IsNotExist(err) {
t.Skip("ai_act_v2.json not found")
}
data, err := LoadV2RegulationFile("ai_act_v2.json")
if err != nil {
t.Fatalf("failed to load: %v", err)
}
if len(data.Obligations) < 15 {
t.Errorf("expected at least 15 AI Act obligations (existing), got %d", len(data.Obligations))
}
}
func TestLoadV2RegulationFile_NIS2(t *testing.T) {
basePath := getV2BasePath()
if _, err := os.Stat(basePath + "/nis2_v2.json"); os.IsNotExist(err) {
t.Skip("nis2_v2.json not found")
}
data, err := LoadV2RegulationFile("nis2_v2.json")
if err != nil {
t.Fatalf("failed to load: %v", err)
}
if len(data.Obligations) < 14 {
t.Errorf("expected at least 14 NIS2 obligations (existing), got %d", len(data.Obligations))
}
}
func TestLoadAllV2Regulations(t *testing.T) {
regs, err := LoadAllV2Regulations()
if err != nil {
t.Skipf("v2 regulations not found: %v", err)
}
if len(regs) < 3 {
t.Errorf("expected at least 3 loaded regulations, got %d", len(regs))
}
totalObl := 0
for _, r := range regs {
totalObl += len(r.Obligations)
}
if totalObl < 40 {
t.Errorf("expected at least 40 total obligations, got %d", totalObl)
}
t.Logf("Loaded %d regulations with %d total obligations", len(regs), totalObl)
}
func TestLoadV2TOMMapping(t *testing.T) {
basePath := getV2BasePath()
if _, err := os.Stat(basePath + "/_tom_mapping.json"); os.IsNotExist(err) {
t.Skip("_tom_mapping.json not found")
}
mapping, err := LoadV2TOMMapping()
if err != nil {
t.Fatalf("failed to load TOM mapping: %v", err)
}
if len(mapping.ObligationToControl) == 0 {
t.Error("expected obligation_to_control mappings")
}
if len(mapping.ControlToObligation) == 0 {
t.Error("expected control_to_obligation mappings")
}
t.Logf("TOM mapping: %d obligation->control, %d control->obligation",
len(mapping.ObligationToControl), len(mapping.ControlToObligation))
}