Files
EscapistsReintroduced/docs/native-mortar-transfer.md
T

5.0 KiB

Native mortar transfer fixture

-errSmoke 1 -errSmokeOutcome mortar-transfer is an opt-in WORKBENCH-only inventory mechanism fixture. Compilation and native execution are pending. No first-release/manual/multiplayer acceptance is asserted by the source checks.

It waits for the production battery's completed finite startup (four physical crew, 27 original HE shell entities), captures each shell's original owner, and holds only this system's automatic scheduler through a WORKBENCH override. It uses the real mortar turret occupant, or seats an original gunner through native GetInVehicle and waits for actual occupancy. Two unchanged vanilla empty boxes receive the gunner's original nine shells through individual TryMoveItemToStorage operations. The boxes are not attached to the gunner's inventory manager.

The first fresh synthetic PendingSupplyReport/BeginRequest bypasses radio delivery explicitly. Production SupplyState must start one exact donor-to-gunner operation. Accepted requests remain pending until the real callback and destination parent slot prove completion. Repeated supply checks must reuse the physical shell without another request. The fixture stashes this supplied shell, starts a second fresh order and cancels it immediately after acceptance. Repeated checks must stay failed with the same order and exactly two production attempts. The accepted native move may still physically complete; cancellation withdraws authorization and does not promise to retract an inventory operation.

The fixture records callback state before canceling. Only an initially pending callback that later succeeds prints the late-completion assertion. If native completion was synchronous, the fixture prints late callback timing not exercised; that run establishes accepted-operation cancellation, not delayed-callback coverage. No delays or fake callbacks are injected into production to manufacture timing.

Every completed move verifies all 27 original identities occur exactly once across the four real crew and fixture boxes, with no additional HE identities. The fixture never spawns or deletes shell resources, modifies ammunition counters, creates an artillery activity or authorizes firing. Production TotalShots must remain unchanged, with Activity, RadioOrder and Released absent. This is not an independent projectile observer or a firing/radio test; mortar-fire owns that separate evidence.

Successful cleanup returns foreign shells from the gunner first, then all stored shells to their original owners using the same real native inventory operation. It verifies all exact owners, 27 shells, and empty boxes before deleting boxes. Stop() cancels and stops the battery/system and is idempotent. On failure, it retains boxes with borrowed shells or an outstanding operation for diagnostics and normal round-owned cleanup, rather than deleting those shells or issuing speculative retries. This case must finish with an explicit fixture round reset; the seated original gunner and stopped scheduler are deliberately not restored to ordinary gameplay.

The probe has a 180-second overall limit and eight-second per-operation limits. It makes no player health changes; the optional host integration can use the same explicit real-player damage protection as the other mortar smoke cases. Crew death, donor distance, unavailable storage or native rejection fails the fixture without bypassing the production checks.

Installed vanilla API evidence

Read-only extracted installed sources:

  • scripts/Game/generated/InventorySystem/InventoryStorageManagerComponent.c: TryMoveItemToStorage(IEntity, BaseInventoryStorageComponent, int=-1, InventoryOperationCallback=null) and FindStorageForItem.
  • scripts/Game/generated/InventorySystem/BaseInventoryStorageComponent.c: Contains, GetAll, GetEstimatedCountFitForItem.
  • Native item parent slot gives actual destination storage; no callback GetItem() is used for moves.
  • {EBBC859CCD94D96D}Prefabs/Props/EmptyStorages/USSR_AmmoBox_empty.et: native storage, 10,000 cumulative volume; no inventory manager. Two boxes accommodate ten temporarily stored 1,600-volume shells.
  • {98EC9C526AFBA282}Prefabs/Weapons/Ammo/Ammo_Shell_82mm_HE_O832DU.et: existing production HE shell, volume 1,600.

The source API allows a manager to request an explicit external-storage move. Returning a shell from a box without its own inventory manager uses the original recipient's manager; this exact route still requires native validation. An accepted request is never treated as completion.

Local verification

python3 -m unittest discover -s tests -p test_native_mortar_transfer.py -v

Four tests pass. Two execute extracted production-fixture methods as C++ against bounded inputs/native metadata fakes: exact identity conservation and callback/slot/deadline move completion. The remaining source checks guard opt-in hooks, cancellation generation, one-call moves, no shell creation/health mutation and safe storage deletion. They do not compile Enforce or simulate native inventory/replication.