extends SceneTree var _checks := 0 var _failures := 0 var _clock: Variant var _state: Variant var _runtime: Variant var _facility_id: StringName var _facility_inventory_id: StringName func _initialize() -> void: call_deferred("_run") func _run() -> void: print("S2: runtime supply-to-service cycle") _reset_runtime() _build_operational_cafeteria() _deliver_inputs_through_logistics() _run_service_sale_with_round_trip() _test_power_projection() _cleanup() if _failures == 0: print("PASS: %d checks" % _checks) else: push_error("FAIL: %d of %d checks failed" % [_failures, _checks]) quit(_failures) func _reset_runtime() -> void: _cleanup() _clock = load("res://autoload/game_clock.gd").new() _state = load("res://autoload/game_state.gd").new() _runtime = load("res://autoload/simulation_runtime.gd").new() _clock.reset(1, 6, 0) _state.reset() var report: Dictionary = _runtime.initialize(_clock, _state, 2202) _clock.set_paused(true) _expect(report[&"valid"], "runtime initializes all S2 definitions") _expect(_runtime.economy_service.get_balance(&"PLAYER_CASH") == 5000, "starting Gold is initialized through the ledger") _expect(_runtime.economy_service.validate_ledger()[&"ok"], "initial ledger reconciles") func _cleanup() -> void: if _runtime != null: _runtime.free() if _clock != null: _clock.free() if _state != null: _state.free() _runtime = null _clock = null _state = null func _build_operational_cafeteria() -> void: var build = _runtime.submit_command( &"build_facility", {&"definition_id": &"cafeteria", &"origin": Vector3i(-5, 0, WorldService.LAYER_FRONT), &"rotation": 0}, &"player", &"", 50, -1, &"s2.build.cafeteria" ) _expect(build.is_success(), "cafeteria construction starts") _clock.advance_minutes(180) var facilities: Array[Dictionary] = _runtime.construction_service.get_facilities() _expect(facilities.size() == 1, "construction produces one authoritative facility") _facility_id = StringName(facilities[0][&"instance_id"]) var operational = _runtime.facility_service.get_instance(_facility_id) _expect(operational != null and operational.definition_id == &"cafeteria", "completed construction registers with FacilityService") _expect(operational.state == FacilityInstance.State.NO_STAFF, "staff requirement prevents premature opening") _expect(_runtime.economy_service.has_account(StringName("FACILITY_REVENUE:%s" % _facility_id)), "facility receives a dedicated revenue account") _expect(not _runtime.mana_network_service.get_node(_facility_id).is_empty(), "Mana demand is registered for the completed facility") _facility_inventory_id = operational.local_inventory_id var staffing = _runtime.submit_command( &"set_facility_conditions", {&"facility_id": _facility_id, &"conditions": {&"active_staff_ids": [&"cook_1", &"server_1"]}}, &"manager", _facility_id, 20, -1, &"s2.staff.cafeteria" ) _expect(staffing.is_success(), "two active staff can be assigned through a command") _expect(operational.state == FacilityInstance.State.OPEN, "staffed and powered cafeteria becomes operational") _expect(_state.get_resource(&"gold") == 4200, "construction Gold is paid once through the authoritative ledger") _expect(_runtime.economy_service.get_balance(&"CONSTRUCTION_EXPENSE") == 800, "construction counter-account retains the capital flow") func _deliver_inputs_through_logistics() -> void: var stocked = _runtime.submit_command( &"add_inventory_stack", { &"owner_inventory_id": &"supplier.main", &"item_id": &"ingredient/basic_meal", &"quantity": 3, &"quality": 70, &"unit_weight": 1, }, &"supplier", &"supplier.main", 10, -1, &"s2.stock.ingredients" ) _expect(stocked.is_success(), "supplier stock enters InventoryService") var created = _runtime.submit_command( &"create_logistics_request", { &"request_id": &"delivery_meals_1", &"source_inventory_id": &"supplier.main", &"destination_inventory_id": _facility_inventory_id, &"item_requirements": {&"ingredient/basic_meal": 2}, &"priority": 80, &"deadline": _clock.absolute_minute + 120, }, &"manager", _facility_id, 10, -1, &"s2.logistics.create" ) _expect(created.is_success(), "logistics request reserves supplier stock") var logistics: LogisticsRequest = _runtime.logistics_requests[&"delivery_meals_1"] _expect(logistics.state == LogisticsRequest.State.RESERVED and logistics.total_weight == 2, "request records reserved weight and state") _expect(_runtime.inventory_service.available_quantity(&"supplier.main", &"ingredient/basic_meal") == 1, "reserved supplier stock cannot be reused") var dispatched = _runtime.submit_command( &"dispatch_logistics", {&"carriers": { &"porter_1": {&"capacity": 10, &"current_load": 0, &"path_minutes": 2, &"role": &"logistics"}, &"porter_2": {&"capacity": 10, &"current_load": 0, &"path_minutes": 4, &"role": &"carrier"}, }}, &"dispatcher", &"delivery_meals_1", 10, -1, &"s2.logistics.dispatch" ) _expect(dispatched.is_success(), "dispatcher evaluates the reserved request") _expect(logistics.assigned_carrier_id == &"porter_1", "deterministic score chooses the suitable nearest carrier") _expect(logistics.state == LogisticsRequest.State.ASSIGNED, "dispatch advances request to ASSIGNED") var start_pickup = _advance_delivery(&"s2.logistics.to_pickup") _expect(start_pickup.is_success() and logistics.state == LogisticsRequest.State.PICKING_UP, "assigned carrier begins pickup") var picked_up = _advance_delivery(&"s2.logistics.pickup") _expect(picked_up.is_success() and logistics.state == LogisticsRequest.State.DELIVERING, "source arrival transfers reserved stock into cargo") _expect(_runtime.inventory_service.total_quantity(&"cargo:porter_1", &"ingredient/basic_meal") == 2, "cargo owns exactly the picked quantity") _expect(_runtime.inventory_service.total_quantity(&"supplier.main", &"ingredient/basic_meal") == 1, "pickup subtracts source stock without duplication") var delivered = _advance_delivery(&"s2.logistics.delivery") _expect(delivered.is_success() and logistics.state == LogisticsRequest.State.COMPLETED, "destination arrival completes logistics") _expect(_runtime.inventory_service.total_quantity(_facility_inventory_id, &"ingredient/basic_meal") == 2, "facility inventory receives the delivered inputs") _expect(_runtime.inventory_service.total_quantity(&"cargo:porter_1", &"ingredient/basic_meal") == 0, "completed delivery leaves no duplicated cargo") _expect(_runtime.logistics_dispatcher.get_reserved_load(&"porter_1") == 0, "carrier capacity releases on completion") _expect(_runtime.inventory_service.validate_invariants()[&"ok"], "delivery preserves every inventory invariant") func _advance_delivery(idempotency_key: StringName) -> CommandResult: return _runtime.submit_command( &"advance_logistics_request", {&"request_id": &"delivery_meals_1"}, &"porter_1", &"delivery_meals_1", 10, -1, idempotency_key ) func _run_service_sale_with_round_trip() -> void: var wallet = _runtime.submit_command( &"register_guest_wallet", {&"guest_id": &"guest_1", &"gold": 100}, &"guest_1", &"guest_1", 10, -1, &"s2.guest.wallet" ) _expect(wallet.is_success(), "guest wallet is initialized through SYSTEM_SOURCE") var requested = _runtime.submit_command( &"create_service_request", { &"request_id": &"meal_request_1", &"facility_id": _facility_id, &"guest_ids": [&"guest_1"], &"service_type": &"meal", &"options": {&"service_minutes": 3}, }, &"guest_1", _facility_id, 10, -1, &"s2.service.request" ) _expect(requested.is_success(), "service request reserves its recipe input and enters the queue") _expect(_runtime.inventory_service.available_quantity(_facility_inventory_id, &"ingredient/basic_meal") == 1, "queued service protects one ingredient from reuse") _clock.advance_one_minute() var active: Array = _runtime.facility_service.get_active_services(_facility_id) _expect(active.size() == 1, "facility queue fills an available service slot") var service_id: StringName = active[0].service_id _expect(active[0].price_snapshot == 25 and active[0].duration_minutes == 3, "service freezes quoted price and duration") var mid_snapshot: Dictionary = _runtime.create_snapshot() var mid_digest := SimulationDigest.compute(mid_snapshot) _clock.advance_minutes(3) var completed: ServiceInstance = _runtime.facility_service.get_service(service_id) _expect(completed != null and completed.state == ServiceInstance.State.COMPLETED, "three active minutes complete the service") _expect(_runtime.inventory_service.total_quantity(_facility_inventory_id, &"ingredient/basic_meal") == 1, "completion consumes exactly one reserved ingredient") _expect(_runtime.economy_service.get_balance(&"GUEST_WALLET:guest_1") == 75, "guest pays the immutable quoted price") _expect(_runtime.economy_service.get_balance(&"PLAYER_CASH") == 4225, "service cash sweep increases player Gold") _expect(_state.get_resource(&"gold") == 4225, "UI Gold mirror follows the ledger transaction") _expect(_runtime.economy_service.validate_ledger()[&"ok"], "service sale remains double-entry balanced") var saw_completion := false for event in _runtime.domain_events.recent_events(): if event.event_type == &"SERVICE_COMPLETED" and service_id in event.entity_ids: saw_completion = true _expect(saw_completion, "service completion is projected as a domain event") var final_digest: String = _runtime.latest_digest _expect(_runtime.restore_snapshot(mid_snapshot), "mid-service snapshot restores all S2 services") _expect(_runtime.latest_digest == mid_digest, "mid-service restore reproduces the exact digest") _expect(_runtime.economy_service.get_balance(&"GUEST_WALLET:guest_1") == 100, "restore rolls payment back to the pre-completion ledger") _clock.advance_minutes(3) _expect(_runtime.latest_digest == final_digest, "replaying completion reproduces inventory, ledger, events and IDs exactly") _expect(_runtime.economy_service.get_entries().filter(func(entry: LedgerEntry) -> bool: return entry.category == &"SERVICE_SALE").size() == 1, "replayed service sale is recorded exactly once") var no_stock = _runtime.submit_command( &"create_service_request", { &"request_id": &"meal_request_too_many", &"facility_id": _facility_id, &"guest_ids": [&"guest_1"], &"options": {&"service_minutes": 20}, }, &"guest_1", _facility_id, 10, -1, &"s2.service.second" ) _expect(no_stock.is_success(), "remaining delivered input can fund one more queued service") var before_rejected: Dictionary = _runtime.inventory_service.create_snapshot() var rejected = _runtime.submit_command( &"create_service_request", { &"request_id": &"meal_request_no_stock", &"facility_id": _facility_id, &"guest_ids": [&"guest_1"], }, &"guest_1", _facility_id, 10, -1, &"s2.service.no_stock" ) _expect(not rejected.is_success(), "service without available recipe input is rejected") _expect(_runtime.inventory_service.create_snapshot() == before_rejected, "rejected service request leaves reservations and stock unchanged") func _test_power_projection() -> void: _runtime.mana_network_service.set_source_output(_runtime.STARTER_MANA_SOURCE, 0) var minutes_to_boundary: int = 10 - (_clock.absolute_minute % 10) _clock.advance_minutes(minutes_to_boundary) var facility = _runtime.facility_service.get_instance(_facility_id) _expect(_runtime.mana_network_service.get_consumer_state(_facility_id) == ManaNetworkService.ConsumerState.NO_POWER, "Mana shortage shuts the cafeteria consumer down") _expect(facility.state == FacilityInstance.State.NO_POWER, "Mana consumer state projects into FacilityService") var interrupted_request_id := &"meal_request_too_many" var interrupted_services: Array = _runtime.facility_service.get_active_services(_facility_id) _expect( _runtime.facility_service.get_request(interrupted_request_id) != null \ and interrupted_services.size() == 1 \ and interrupted_services[0].state == ServiceInstance.State.PAUSED, "power loss safely pauses the active service without losing its request" ) func _expect(condition: bool, label: String) -> void: _checks += 1 if condition: print(" ✓ %s" % label) return _failures += 1 push_error(" ✗ %s" % label)