Ship the 0.8.0 first-hour and campaign milestone
Add the campaign shell, pause-safe checkpoint resume, post-shift campaign continue, confirmed campaign reset, difficulty presets, searchable Help, content-matrix validation, recovery events, contextual dialogue, policy/debrief context and eligible-event previews. Extend persistence with atomic separate files and add campaign/checkpoint/tutorial smokes. Headless 247/247, Python 94/94, tutorial/campaign/session/scenario smokes green.
This commit is contained in:
1 parent
86332cd401
commit
aa51ee331e
38 files changed
+1361
-1144
No files matched your search
@@ -0,0 +1,44 @@
|
||||
extends RefCounted
|
||||
## Mid-shift checkpoint data survives a JSON round-trip and restores the
|
||||
## coordinator's systems without replaying completed interactions.
|
||||
|
||||
const ScenarioFactory := preload("res://src/content/scenario_factory.gd")
|
||||
const ShiftCoordinator := preload("res://src/core/shift_coordinator.gd")
|
||||
const IncidentRecorder := preload("res://src/core/incident_recorder.gd")
|
||||
const Rules := preload("res://src/core/rules.gd")
|
||||
|
||||
func test_coordinator_snapshot_round_trip() -> bool:
|
||||
var scenario := ScenarioFactory.hollywood_building()
|
||||
var first := ShiftCoordinator.new()
|
||||
first.setup(scenario, 900.0, 42)
|
||||
first.start()
|
||||
first.elapsed_s = 123.0
|
||||
first.recorder.start_incident("guest", "focus")
|
||||
first.recorder.add_escalation("guest", Rules.Level.FORMAL_WARNING, "warning")
|
||||
first.recorder.close_incident("guest", "peaceful")
|
||||
first.reputation.apply("peaceful", 5.0, "test")
|
||||
first.crowd.mood = 0.4
|
||||
first.radio.battery = 70.0
|
||||
var payload: Dictionary = JSON.parse_string(JSON.stringify(first.snapshot()))
|
||||
var second := ShiftCoordinator.new()
|
||||
second.setup(scenario, 900.0, 42)
|
||||
second.restore(payload)
|
||||
var a := TestUtils.check(is_equal_approx(second.elapsed_s, 123.0), "elapsed time restores")
|
||||
var b := TestUtils.check_eq(second.recorder.to_dict()["open_count"], 0, "incident state restores")
|
||||
var c := TestUtils.check_eq(second.recorder.to_dict()["incidents"].size(), 1,
|
||||
"closed incidents restore")
|
||||
var d := TestUtils.check(is_equal_approx(second.reputation.rating, 75.0), "reputation restores")
|
||||
var e := TestUtils.check(is_equal_approx(second.crowd.mood, 0.4), "crowd mood restores")
|
||||
var f := TestUtils.check(is_equal_approx(second.radio.battery, 70.0), "radio battery restores")
|
||||
return a and b and c and d and e and f
|
||||
|
||||
func test_open_incident_snapshot_restores_evidence() -> bool:
|
||||
var recorder := IncidentRecorder.new()
|
||||
recorder.start_incident("guest", "focus")
|
||||
recorder.add_access_evidence("guest", {"kind": "wristband", "status": "valid"})
|
||||
var restored := IncidentRecorder.new()
|
||||
restored.restore(JSON.parse_string(JSON.stringify(recorder.snapshot())))
|
||||
var a := TestUtils.check(restored.has_open_incident("guest"), "open incident restores")
|
||||
restored.add_event("guest", {"type": "player_action"})
|
||||
var b := TestUtils.check(restored.open_incidents_count() == 1, "restored incident accepts events")
|
||||
return a and b
|
||||
Reference in new issue
Block a user