Add list_cargo() to the admin client
The station queries and the cargo events name a cargo only by a bare numeric id -- get_station()'s and get_station_cargo()'s cargo_id, the cargo_waiting events, the per-cargo load on vehicle events. Those ids index the cargo table the loaded NewGRFs build for the running game, so the same id is coal in one save and grain in another and callers had no way to resolve them. The AdminBridge GameScript has answered a list_cargo command all along; no method on OpenTTDAdminClient sent it. This adds the missing half, so no GameScript change is needed for it to work. It goes through _gs_query() like get_station(), inheriting the request_id correlation and the Gamescript auto-subscribe, with one difference worth knowing: the GS handler defines no error reply for this command, so unlike the other queries it can time out but can never raise ValueError. The reply lists cargo in GSCargoList order rather than by id -- against the dev server the ids come back 10 down to 0 -- so the docstring and PROTOCOL.md both warn to index the list by cargo_id and not by position. Also teaches the main_admin.py demo to resolve the labels before printing a station's cargo, which is what the bare ids in its output were asking for all along. Co-Authored-By: Claude <[email protected]>
This commit is contained in:
@@ -738,6 +738,30 @@ class OpenTTDAdminClient:
|
||||
payload["via_station"] = via_station
|
||||
return await self._gs_query(payload, timeout, f"get_station_cargo({station_id}, {cargo_id})")
|
||||
|
||||
async def list_cargo(self, timeout=5.0):
|
||||
"""Fetch the running game's cargo table via the AdminBridge GameScript, id to label.
|
||||
|
||||
Every other reply names a cargo by its bare numeric id — get_station()'s and
|
||||
get_station_cargo()'s cargo_id, the cargo_waiting events, the per-cargo load on vehicle
|
||||
events. Those ids index the cargo table the loaded NewGRFs build, so they mean different
|
||||
things in different games and are not worth hardcoding; resolve them against this list
|
||||
instead. Auto-subscribes to Gamescript updates on first use; if you manage update
|
||||
frequencies yourself, ensure update_frequency(Gamescript, Automatic) is active before
|
||||
calling.
|
||||
|
||||
Returns a dict with a "cargo" list holding every cargo type in the game, in no particular
|
||||
order (index it by "cargo_id"; a cargo's position in the list is not its id). Each entry:
|
||||
- "cargo_id": the id used by all the replies above
|
||||
- "label": the cargo label ("PASS", "COAL", ...), or "" if the GameScript could not
|
||||
read it
|
||||
- "freight": 1 for freight cargo, 0 for the rest (passengers, mail, ...)
|
||||
|
||||
Raises asyncio.TimeoutError if no reply arrives (e.g. game paused, GS not loaded) and
|
||||
ConnectionError if the admin connection drops while waiting. The GameScript reports no
|
||||
error for this command, so unlike get_station() it never raises ValueError.
|
||||
"""
|
||||
return await self._gs_query({"command": "list_cargo"}, timeout, "list_cargo")
|
||||
|
||||
async def get_dispatch(self, vehicle_id, timeout=5.0):
|
||||
"""Fetch an authoritative snapshot of a vehicle's scheduled dispatch state via the AdminBridge GS.
|
||||
|
||||
|
||||
Reference in New Issue
Block a user