feat(backend): sprint 3 — multi-technique simulations + MITRE matrix
- Simulation model: replace mitre_technique_id/name scalars with techniques JSON column [{id, name}]
- Alembic migration 0003: add techniques, backfill from scalars, drop old columns (reversible)
- MITRE service: add get_tactics(), lookup_name(), get_matrix() with canonical tactic order and sub-technique nesting
- serializer: enrich techniques with tactics from service at serialize time (graceful empty tactics if bundle outdated)
- simulation_workflow: PATCH now accepts technique_ids list, validates against bundle, deduplicates preserving order, auto-transitions on non-empty list
- simulations API: add GET /api/mitre/matrix endpoint (503 if bundle absent)
- test_mitre.py: updated _reset_mitre fixture, added T1059.006 sub-technique, 14 new tests for get_tactics/lookup_name/get_matrix/matrix endpoint
- test_simulations_techniques.py: 20 new tests covering AC-13.1 to AC-13.5 (create, PATCH, dedup, auto-transition, SOC blocked, migration backfill logic)
Total: 161 tests passing. ruff clean. mypy: no new errors.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
@@ -121,7 +121,7 @@ def transition_simulation(sid: int):
|
||||
|
||||
|
||||
# ---------------------------------------------------------------------------
|
||||
# MITRE autocomplete
|
||||
# MITRE autocomplete + matrix
|
||||
# ---------------------------------------------------------------------------
|
||||
|
||||
|
||||
@@ -136,3 +136,14 @@ def mitre_techniques():
|
||||
q = request.args.get("q", "").strip()
|
||||
results = mitre_svc.search(q)
|
||||
return jsonify(results), 200
|
||||
|
||||
|
||||
@simulations_bp.get("/api/mitre/matrix")
|
||||
@login_required
|
||||
def mitre_matrix():
|
||||
from backend.app.services import mitre as mitre_svc
|
||||
|
||||
if not mitre_svc.mitre_loaded:
|
||||
return jsonify({"error": "mitre bundle not loaded"}), 503
|
||||
|
||||
return jsonify(mitre_svc.get_matrix()), 200
|
||||
|
||||
Reference in New Issue
Block a user