From a9ab53cb8b6bc377f21543b83d85cfcaa56c1ec2 Mon Sep 17 00:00:00 2001 From: Zach Parks Date: Sun, 20 Nov 2022 13:39:52 -0600 Subject: [PATCH] WebHost/Core: Defer creating slots that have patch files until after multidata is loaded and remove redundant code. (#1250) * WebHost: On uploads, infer player name if missing in file name. * Remove conditional logic for not including player name in file name. * quick readability tweak to "fix" * Refactored `upload_zip_to_db` to clean up redundancies and fix issues * Rename `patches` to `files` * fix comment --- BaseClasses.py | 5 +-- WebHostLib/upload.py | 88 +++++++++++++++++++------------------------- 2 files changed, 39 insertions(+), 54 deletions(-) diff --git a/BaseClasses.py b/BaseClasses.py index c51eaf9a..73c24cd8 100644 --- a/BaseClasses.py +++ b/BaseClasses.py @@ -308,10 +308,7 @@ class MultiWorld(): def get_out_file_name_base(self, player: int) -> str: """ the base name (without file extension) for each player's output file for a seed """ - return f"AP_{self.seed_name}_P{player}" \ - + (f"_{self.get_file_safe_player_name(player).replace(' ', '_')}" - if (self.player_name[player] != f"Player{player}") - else '') + return f"AP_{self.seed_name}_P{player}_{self.get_file_safe_player_name(player).replace(' ', '_')}" def initialize_regions(self, regions=None): for region in regions if regions else self.regions: diff --git a/WebHostLib/upload.py b/WebHostLib/upload.py index 22e1353f..1aa60ffc 100644 --- a/WebHostLib/upload.py +++ b/WebHostLib/upload.py @@ -15,7 +15,7 @@ from worlds.Files import AutoPatchRegister from . import app from .models import Seed, Room, Slot -banned_zip_contents = (".sfc",) +banned_zip_contents = (".sfc", ".z64", ".n64", ".sms", ".gb") def upload_zip_to_db(zfile: zipfile.ZipFile, owner=None, meta={"race": False}, sid=None): @@ -24,59 +24,28 @@ def upload_zip_to_db(zfile: zipfile.ZipFile, owner=None, meta={"race": False}, s infolist = zfile.infolist() slots: typing.Set[Slot] = set() spoiler = "" + files = {} multidata = None + + # Load files. for file in infolist: handler = AutoPatchRegister.get_handler(file.filename) if file.filename.endswith(banned_zip_contents): return "Uploaded data contained a rom file, which is likely to contain copyrighted material. " \ "Your file was deleted." + + # AP Container elif handler: - raw = zfile.open(file, "r").read() - patch = handler(BytesIO(raw)) - patch.read() - slots.add(Slot(data=raw, - player_name=patch.player_name, - player_id=patch.player, - game=patch.game)) - - elif file.filename.endswith(".apmc"): data = zfile.open(file, "r").read() - metadata = json.loads(base64.b64decode(data).decode("utf-8")) - slots.add(Slot(data=data, - player_name=metadata["player_name"], - player_id=metadata["player_id"], - game="Minecraft")) - - elif file.filename.endswith(".apv6"): - _, seed_name, slot_id, slot_name = file.filename.split('.')[0].split('_', 3) - slots.add(Slot(data=zfile.open(file, "r").read(), player_name=slot_name, - player_id=int(slot_id[1:]), game="VVVVVV")) - - elif file.filename.endswith(".apsm64ex"): - _, seed_name, slot_id, slot_name = file.filename.split('.')[0].split('_', 3) - slots.add(Slot(data=zfile.open(file, "r").read(), player_name=slot_name, - player_id=int(slot_id[1:]), game="Super Mario 64")) - - elif file.filename.endswith(".zip"): - # Factorio mods need a specific name or they do not function - _, seed_name, slot_id, slot_name = file.filename.rsplit("_", 1)[0].split("-", 3) - slots.add(Slot(data=zfile.open(file, "r").read(), player_name=slot_name, - player_id=int(slot_id[1:]), game="Factorio")) - - elif file.filename.endswith(".apz5"): - # .apz5 must be named specifically since they don't contain any metadata - _, seed_name, slot_id, slot_name = file.filename.split('.')[0].split('_', 3) - slots.add(Slot(data=zfile.open(file, "r").read(), player_name=slot_name, - player_id=int(slot_id[1:]), game="Ocarina of Time")) - - elif file.filename.endswith(".json"): - _, seed_name, slot_id, slot_name = file.filename.split('.')[0].split('-', 3) - slots.add(Slot(data=zfile.open(file, "r").read(), player_name=slot_name, - player_id=int(slot_id[1:]), game="Dark Souls III")) + patch = handler(BytesIO(data)) + patch.read() + files[patch.player] = data + # Spoiler elif file.filename.endswith(".txt"): spoiler = zfile.open(file, "r").read().decode("utf-8-sig") + # Multi-data elif file.filename.endswith(".archipelago"): try: multidata = zfile.open(file).read() @@ -84,17 +53,36 @@ def upload_zip_to_db(zfile: zipfile.ZipFile, owner=None, meta={"race": False}, s flash("Could not load multidata. File may be corrupted or incompatible.") multidata = None + # Minecraft + elif file.filename.endswith(".apmc"): + data = zfile.open(file, "r").read() + metadata = json.loads(base64.b64decode(data).decode("utf-8")) + files[metadata["player_id"]] = data + + # Factorio + elif file.filename.endswith(".zip"): + _, _, slot_id, *_ = file.filename.split('_')[0].split('-', 3) + data = zfile.open(file, "r").read() + files[int(slot_id[1:])] = data + + # All other files using the standard MultiWorld.get_out_file_name_base method + else: + _, _, slot_id, *_ = file.filename.split('.')[0].split('_', 3) + data = zfile.open(file, "r").read() + files[int(slot_id[1:])] = data + + # Load multi data. if multidata: decompressed_multidata = MultiServer.Context.decompress(multidata) if "slot_info" in decompressed_multidata: - player_names = {slot.player_name for slot in slots} - leftover_names: typing.Dict[int, NetworkSlot] = { - slot_id: slot_info for slot_id, slot_info in decompressed_multidata["slot_info"].items() - if slot_info.name not in player_names and slot_info.type != SlotType.group} - newslots = [(Slot(data=None, player_name=slot_info.name, player_id=slot, game=slot_info.game)) - for slot, slot_info in leftover_names.items()] - for slot in newslots: - slots.add(slot) + for slot, slot_info in decompressed_multidata["slot_info"].items(): + # Ignore Player Groups (e.g. item links) + if slot_info.type == SlotType.group: + continue + slots.add(Slot(data=files.get(slot, None), + player_name=slot_info.name, + player_id=slot, + game=slot_info.game)) flush() # commit slots