Files
breakpilot-compliance/backend-compliance/compliance/reasoning/rules_obligations_machine_data.py
T
Benjamin Admin 1607c89459 feat(reasoning): Regulatory Reasoning Engine MVP (scope/obligations/implementation/interpretation)
Deterministic reasoning layer ON TOP of the Legal Knowledge Graph (obligation
registry) and the Compliance Execution Graph (control mapping/evidence). Answers
which regulations apply to a concrete product, which obligations follow, whether
the customer's implementation covers them, and whether a customer interpretation
is too narrow/broad/plausible.

- ProductProfile with tri-state facts (Optional[bool]=None => uncertain, never
  false security); safe predicate evaluator (no eval).
- 6 regulation triggers (CRA/MaschinenVO/RED/EMV/DataAct/NIS2) with missing-fact
  prompts; 24 obligation scope rules.
- CRA obligation_ids RE-USED verbatim from the registry (93 ids) — never re-minted
  (control_uuid trap); Machine/Data-Act flagged proposed=True.
- required_evidence constrained to the framework-agnostic shared evidence catalog;
  capabilities echo the planned Obligation->Capability layer.
- Overlap groups (CRA<->MaschinenVO cyber-safety) + evidence-for-multiple (USP).
- 4 endpoints POST /reasoning/{scope,obligations,implementation-assessment,
  interpretation-assessment}; thin handlers, registered in api/__init__.py.
- 22 tests (5 machine-builder scenarios + 10 acceptance questions). No DB
  migration, no RAG, no new controls.

Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
2026-06-25 19:30:53 +02:00

140 lines
5.9 KiB
Python

"""MaschinenVO and Data Act obligation scope rules.
These regulations are NOT yet in the Legal-KG registry (which currently covers
the six CRA-P1 families). Every obligation here is therefore `proposed=True`:
the reasoning layer proposes the snake_case id, the Obligation Registry session
remains the only authority that may canonicalise it (re-link, never re-mint).
"""
from __future__ import annotations
from typing import List
from .enums import AuthorityLevel, Confidence
from .rules_types import ObligationRule
_EU = ("eu_market", "eq", True)
_IS_MACHINE = ("is_machine", "eq", True)
_LM = AuthorityLevel.LEGAL_TEXT
MACHINE_OBLIGATIONS: List[ObligationRule] = [
ObligationRule(
obligation_id="machine_risk_assessment",
title="Maschinen-Risikobeurteilung",
source_regulation="MaschinenVO",
obligation_text="Eine Risikobeurteilung der Maschine durchführen, um Gefährdungen zu ermitteln und zu mindern.",
legal_basis_refs=["MaschinenVO (EU) 2023/1230 Anhang III (1.1.1)", "EN ISO 12100"],
authority_level=_LM,
family="machine_safety",
applies_if={"all": [_IS_MACHINE, _EU]},
required_capabilities=["risk_assessment"],
required_evidence=["policy"],
lifecycle_phase=["development", "placing_on_market"],
overlap_group_id="RISK_ASSESSMENT",
proposed=True,
),
ObligationRule(
obligation_id="machine_safety_control_systems",
title="Sichere Steuerungssysteme",
source_regulation="MaschinenVO",
obligation_text="Sicherheitsbezogene Teile der Steuerung so auslegen, dass Ausfälle nicht zu gefährlichen Zuständen führen.",
legal_basis_refs=["MaschinenVO (EU) 2023/1230 Anhang III (1.2.1)", "EN ISO 13849-1"],
authority_level=_LM,
family="machine_safety",
applies_if={"all": [_IS_MACHINE, ("has_safety_function", "eq", True), _EU]},
required_capabilities=["functional_safety"],
required_evidence=["test_report", "policy"],
lifecycle_phase=["development", "placing_on_market"],
proposed=True,
),
ObligationRule(
obligation_id="machine_protection_against_corruption",
title="Schutz gegen Korrumpierung sicherheitsrelevanter Funktionen",
source_regulation="MaschinenVO",
obligation_text="Sicherstellen, dass eine (auch beabsichtigte) Korrumpierung der Software/Verbindung keine gefährliche Situation auslöst.",
legal_basis_refs=["MaschinenVO (EU) 2023/1230 Anhang III (1.1.9)"],
authority_level=_LM,
family="machine_safety",
applies_if={
"all": [
_IS_MACHINE,
("has_safety_function", "eq", True),
{"any": [("has_remote_access", "eq", True), ("has_software", "eq", True)]},
_EU,
]
},
required_capabilities=["software_integrity", "secure_by_default"],
required_evidence=["test_report", "config_export"],
lifecycle_phase=["development", "operation", "maintenance"],
overlap_group_id="VULNERABILITY_HANDLING",
proposed=True,
),
ObligationRule(
obligation_id="machine_instructions_for_use",
title="Betriebsanleitung",
source_regulation="MaschinenVO",
obligation_text="Eine vollständige Betriebsanleitung mit Sicherheitshinweisen bereitstellen.",
legal_basis_refs=["MaschinenVO (EU) 2023/1230 Anhang III (1.7.4)"],
authority_level=_LM,
family="machine_safety",
applies_if={"all": [_IS_MACHINE, _EU]},
required_capabilities=["technical_documentation"],
required_evidence=["policy"],
lifecycle_phase=["placing_on_market"],
overlap_group_id="INSTRUCTIONS_FOR_USE",
proposed=True,
),
ObligationRule(
obligation_id="machine_ce_conformity",
title="Konformitätsbewertung / CE (Maschine)",
source_regulation="MaschinenVO",
obligation_text="Das passende Konformitätsbewertungsverfahren der MaschinenVO durchlaufen und CE kennzeichnen.",
legal_basis_refs=["MaschinenVO (EU) 2023/1230 Art. 25", "Anhang IV"],
authority_level=_LM,
family="machine_safety",
applies_if={"all": [_IS_MACHINE, _EU]},
required_capabilities=["conformity_assessment"],
required_evidence=["test_report", "policy"],
lifecycle_phase=["placing_on_market"],
overlap_group_id="CE_CONFORMITY",
proposed=True,
),
]
DATA_ACT_OBLIGATIONS: List[ObligationRule] = [
ObligationRule(
obligation_id="data_act_data_access_by_design",
title="Datenzugang by design",
source_regulation="DataAct",
obligation_text="Vernetzte Produkte so gestalten, dass die erzeugten Produktdaten standardmäßig zugänglich sind.",
legal_basis_refs=["Data Act (EU) 2023/2854 Art. 3"],
authority_level=_LM,
family="data_act",
applies_if={
"all": [
("generates_usage_data", "eq", True),
{"any": [("has_cloud_connection", "eq", True), ("has_remote_access", "eq", True)]},
_EU,
]
},
required_capabilities=["data_access_provision"],
required_evidence=["config_export", "policy"],
lifecycle_phase=["development", "placing_on_market"],
proposed=True,
),
ObligationRule(
obligation_id="data_act_user_data_access",
title="Datenzugang für Nutzer",
source_regulation="DataAct",
obligation_text="Nutzern Zugang zu den von ihnen erzeugten Daten gewähren und Weitergabe an Dritte ermöglichen.",
legal_basis_refs=["Data Act (EU) 2023/2854 Art. 4", "Art. 5"],
authority_level=_LM,
family="data_act",
applies_if={"all": [("generates_usage_data", "eq", True), _EU]},
required_capabilities=["data_access_provision"],
required_evidence=["policy"],
lifecycle_phase=["operation"],
proposed=True,
),
]