Server: add slot_info key to Connected

This commit is contained in:
Fabian Dill
2022-01-30 13:57:12 +01:00
parent ddd3073132
commit 0bd252e7f5
6 changed files with 67 additions and 41 deletions

View File

@@ -33,7 +33,8 @@ from worlds import network_data_package, lookup_any_item_id_to_name, lookup_any_
import Utils
from Utils import get_item_name_from_id, get_location_name_from_id, \
version_tuple, restricted_loads, Version
from NetUtils import Endpoint, ClientStatus, NetworkItem, decode, encode, NetworkPlayer, Permission
from NetUtils import Endpoint, ClientStatus, NetworkItem, decode, encode, NetworkPlayer, Permission, NetworkSlot, \
SlotType
colorama.init()
@@ -104,6 +105,7 @@ class Context:
remaining_mode: str = "disabled", auto_shutdown: typing.SupportsFloat = 0, compatibility: int = 2,
log_network: bool = False):
super(Context, self).__init__()
self.slot_info: typing.Dict[int, NetworkSlot] = {}
self.log_network = log_network
self.endpoints = []
self.clients = {}
@@ -292,18 +294,35 @@ class Context:
self.slot_data = decoded_obj['slot_data']
self.er_hint_data = {int(player): {int(address): name for address, name in loc_data.items()}
for player, loc_data in decoded_obj["er_hint_data"].items()}
self.games = decoded_obj["games"]
# load start inventory:
for slot, item_codes in decoded_obj["precollected_items"].items():
self.start_inventory[slot] = [NetworkItem(item_code, -2, 0) for item_code in item_codes]
for team in range(len(decoded_obj['names'])):
for slot, hints in decoded_obj["precollected_hints"].items():
self.hints[team, slot].update(hints)
# declare slots without checks as done, as they're assumed to be spectators
for slot, locations in self.locations.items():
if not locations:
if "slot_info" in decoded_obj:
self.slot_info = decoded_obj["slot_info"]
self.games = {slot: slot_info.game for slot, slot_info in self.slot_info.items()}
else:
self.games = decoded_obj["games"]
self.slot_info = {
slot: NetworkSlot(
self.player_names[0, slot],
self.games[slot],
SlotType(int(bool(locations))))
for slot, locations in self.locations.items()
}
# declare slots that aren't players as done
for slot, slot_info in self.slot_info.items():
if slot_info.type.always_goal:
for team in self.clients:
self.client_game_state[team, slot] = ClientStatus.CLIENT_GOAL
if use_embedded_server_options:
server_options = decoded_obj.get("server_options", {})
self._set_options(server_options)
@@ -541,6 +560,8 @@ async def on_client_connected(ctx: Context, client: Client):
'cmd': 'RoomInfo',
'password': bool(ctx.password),
'players': players,
# TODO remove around 0.2.5 in favor of slot_info ?
# Maybe convert into a list of games that are present to fetch relevant datapackage entries before Connect?
'games': [ctx.games[x] for x in range(1, len(ctx.games) + 1)],
# tags are for additional features in the communication.
# Name them by feature or fork, as you feel is appropriate.
@@ -579,7 +600,7 @@ async def on_client_joined(ctx: Context, client: Client):
f"{verb} {ctx.games[client.slot]} has joined. "
f"Client({version_str}), {client.tags}).")
ctx.notify_client(client, "Now that you are connected, "
"you can use !help to list commands to run via the server."
"you can use !help to list commands to run via the server. "
"If your client supports it, "
"you may have additional local commands you can list with /help.")
ctx.client_connection_timers[client.team, client.slot] = datetime.datetime.now(datetime.timezone.utc)
@@ -705,12 +726,7 @@ def register_location_checks(ctx: Context, team: int, slot: int, locations: typi
if count_activity:
ctx.client_activity_timers[team, slot] = datetime.datetime.now(datetime.timezone.utc)
for location in new_locations:
if len(ctx.locations[slot][location]) == 3:
item_id, target_player, flags = ctx.locations[slot][location]
else:
# TODO: remove around version 0.2.5
item_id, target_player = ctx.locations[slot][location]
flags = 0
item_id, target_player, flags = ctx.locations[slot][location]
new_item = NetworkItem(item_id, location, slot, flags)
if target_player != slot:
@@ -739,12 +755,7 @@ def collect_hints(ctx: Context, team: int, slot: int, item: str) -> typing.List[
seeked_item_id = proxy_worlds[ctx.games[slot]].item_name_to_id[item]
for finding_player, check_data in ctx.locations.items():
for location_id, result in check_data.items():
if len(result) == 3:
item_id, receiving_player, item_flags = result
else:
# TODO: remove around version 0.2.5
item_id, receiving_player = result
item_flags = 0
item_id, receiving_player, item_flags = result
if receiving_player == slot and item_id == seeked_item_id:
found = location_id in ctx.location_checks[team, finding_player]
@@ -759,12 +770,7 @@ def collect_hints_location(ctx: Context, team: int, slot: int, location: str) ->
seeked_location: int = proxy_worlds[ctx.games[slot]].location_name_to_id[location]
result = ctx.locations[slot].get(seeked_location, (None, None, None))
if result:
if len(result) == 3:
item_id, receiving_player, item_flags = result
else:
# TODO: remove around version 0.2.5
item_id, receiving_player = result
item_flags = 0
item_id, receiving_player, item_flags = result
found = seeked_location in ctx.location_checks[team, slot]
entrance = ctx.er_hint_data.get(slot, {}).get(seeked_location, "")
@@ -1347,7 +1353,8 @@ async def process_client_cmd(ctx: Context, client: Client, args: dict):
"players": ctx.get_players_package(),
"missing_locations": get_missing_checks(ctx, team, slot),
"checked_locations": get_checked_checks(ctx, team, slot),
"slot_data": ctx.slot_data[client.slot]
"slot_data": ctx.slot_data[client.slot],
"slot_info": ctx.slot_info
}]
start_inventory = get_start_inventory(ctx, team, slot, client.remote_start_inventory)
items = get_received_items(ctx, client.team, client.slot, client.remote_items)
@@ -1431,13 +1438,8 @@ async def process_client_cmd(ctx: Context, client: Client, args: dict):
[{'cmd': 'InvalidPacket', "type": "arguments", "text": 'LocationScouts',
"original_cmd": cmd}])
return
if len(ctx.locations[client.slot][location]) == 3:
target_item, target_player, flags = ctx.locations[client.slot][location]
else:
# TODO: remove around version 0.2.5
target_item, target_player = ctx.locations[client.slot][location]
flags = 0
target_item, target_player, flags = ctx.locations[client.slot][location]
locs.append(NetworkItem(target_item, location, target_player, flags))
await ctx.send_msgs(client, [{'cmd': 'LocationInfo', 'locations': locs}])