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
This commit is contained in:
parent
5ed8c2e1c0
commit
a9ab53cb8b
|
@ -308,10 +308,7 @@ class MultiWorld():
|
||||||
|
|
||||||
def get_out_file_name_base(self, player: int) -> str:
|
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 """
|
""" the base name (without file extension) for each player's output file for a seed """
|
||||||
return f"AP_{self.seed_name}_P{player}" \
|
return f"AP_{self.seed_name}_P{player}_{self.get_file_safe_player_name(player).replace(' ', '_')}"
|
||||||
+ (f"_{self.get_file_safe_player_name(player).replace(' ', '_')}"
|
|
||||||
if (self.player_name[player] != f"Player{player}")
|
|
||||||
else '')
|
|
||||||
|
|
||||||
def initialize_regions(self, regions=None):
|
def initialize_regions(self, regions=None):
|
||||||
for region in regions if regions else self.regions:
|
for region in regions if regions else self.regions:
|
||||||
|
|
|
@ -15,7 +15,7 @@ from worlds.Files import AutoPatchRegister
|
||||||
from . import app
|
from . import app
|
||||||
from .models import Seed, Room, Slot
|
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):
|
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()
|
infolist = zfile.infolist()
|
||||||
slots: typing.Set[Slot] = set()
|
slots: typing.Set[Slot] = set()
|
||||||
spoiler = ""
|
spoiler = ""
|
||||||
|
files = {}
|
||||||
multidata = None
|
multidata = None
|
||||||
|
|
||||||
|
# Load files.
|
||||||
for file in infolist:
|
for file in infolist:
|
||||||
handler = AutoPatchRegister.get_handler(file.filename)
|
handler = AutoPatchRegister.get_handler(file.filename)
|
||||||
if file.filename.endswith(banned_zip_contents):
|
if file.filename.endswith(banned_zip_contents):
|
||||||
return "Uploaded data contained a rom file, which is likely to contain copyrighted material. " \
|
return "Uploaded data contained a rom file, which is likely to contain copyrighted material. " \
|
||||||
"Your file was deleted."
|
"Your file was deleted."
|
||||||
|
|
||||||
|
# AP Container
|
||||||
elif handler:
|
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()
|
data = zfile.open(file, "r").read()
|
||||||
metadata = json.loads(base64.b64decode(data).decode("utf-8"))
|
patch = handler(BytesIO(data))
|
||||||
slots.add(Slot(data=data,
|
patch.read()
|
||||||
player_name=metadata["player_name"],
|
files[patch.player] = data
|
||||||
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"))
|
|
||||||
|
|
||||||
|
# Spoiler
|
||||||
elif file.filename.endswith(".txt"):
|
elif file.filename.endswith(".txt"):
|
||||||
spoiler = zfile.open(file, "r").read().decode("utf-8-sig")
|
spoiler = zfile.open(file, "r").read().decode("utf-8-sig")
|
||||||
|
|
||||||
|
# Multi-data
|
||||||
elif file.filename.endswith(".archipelago"):
|
elif file.filename.endswith(".archipelago"):
|
||||||
try:
|
try:
|
||||||
multidata = zfile.open(file).read()
|
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.")
|
flash("Could not load multidata. File may be corrupted or incompatible.")
|
||||||
multidata = None
|
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:
|
if multidata:
|
||||||
decompressed_multidata = MultiServer.Context.decompress(multidata)
|
decompressed_multidata = MultiServer.Context.decompress(multidata)
|
||||||
if "slot_info" in decompressed_multidata:
|
if "slot_info" in decompressed_multidata:
|
||||||
player_names = {slot.player_name for slot in slots}
|
for slot, slot_info in decompressed_multidata["slot_info"].items():
|
||||||
leftover_names: typing.Dict[int, NetworkSlot] = {
|
# Ignore Player Groups (e.g. item links)
|
||||||
slot_id: slot_info for slot_id, slot_info in decompressed_multidata["slot_info"].items()
|
if slot_info.type == SlotType.group:
|
||||||
if slot_info.name not in player_names and slot_info.type != SlotType.group}
|
continue
|
||||||
newslots = [(Slot(data=None, player_name=slot_info.name, player_id=slot, game=slot_info.game))
|
slots.add(Slot(data=files.get(slot, None),
|
||||||
for slot, slot_info in leftover_names.items()]
|
player_name=slot_info.name,
|
||||||
for slot in newslots:
|
player_id=slot,
|
||||||
slots.add(slot)
|
game=slot_info.game))
|
||||||
|
|
||||||
flush() # commit slots
|
flush() # commit slots
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue