diff --git a/.github/workflows/unittests.yml b/.github/workflows/unittests.yml index 2691fa9b..1c8ab10c 100644 --- a/.github/workflows/unittests.yml +++ b/.github/workflows/unittests.yml @@ -34,7 +34,7 @@ jobs: run: | python -m pip install --upgrade pip pip install flake8 pytest - python ModuleUpdate.py --yes --force + python ModuleUpdate.py --yes --force --append "WebHostLib/requirements.txt" - name: Unittests run: | pytest test diff --git a/ModuleUpdate.py b/ModuleUpdate.py index d8b01171..17eb0906 100644 --- a/ModuleUpdate.py +++ b/ModuleUpdate.py @@ -62,6 +62,9 @@ if __name__ == "__main__": parser = argparse.ArgumentParser(description='Install archipelago requirements') parser.add_argument('-y', '--yes', dest='yes', action='store_true', help='answer "yes" to all questions') parser.add_argument('-f', '--force', dest='force', action='store_true', help='force update') + parser.add_argument('-a', '--append', nargs="*", dest='additional_requirements', + help='List paths to additional requirement files.') args = parser.parse_args() - + if args.additional_requirements: + requirements_files.update(args.additional_requirements) update(args.yes, args.force) diff --git a/WebHost.py b/WebHost.py index 773120b7..42547272 100644 --- a/WebHost.py +++ b/WebHost.py @@ -1,6 +1,7 @@ import os import multiprocessing import logging +import typing import ModuleUpdate @@ -36,13 +37,19 @@ def get_app(): return app -def create_ordered_tutorials_file(): +def create_ordered_tutorials_file() -> typing.List[typing.Dict[str, typing.Any]]: import json - with open(os.path.join("WebHostLib", "static", "assets", "tutorial", "tutorials.json")) as source: + + with open(Utils.local_path("WebHostLib", "static", "assets", "tutorial", "tutorials.json")) as source: data = json.load(source) + data = sorted(data, key=lambda entry: entry["gameTitle"].lower()) - with open(os.path.join("WebHostLib", "static", "generated", "tutorials.json"), "w") as target: + + folder = Utils.local_path("WebHostLib", "static", "generated") + os.makedirs(folder, exist_ok=True) + with open(os.path.join(folder, "tutorials.json"), "w") as target: json.dump(data, target) + return data if __name__ == "__main__": diff --git a/test/webhost/TestTutorial.py b/test/webhost/TestTutorial.py new file mode 100644 index 00000000..78d619d3 --- /dev/null +++ b/test/webhost/TestTutorial.py @@ -0,0 +1,22 @@ +import unittest +from worlds.AutoWorld import AutoWorldRegister + + +class TestBase(unittest.TestCase): + def testCreateItem(self): + import WebHost + tutorials_data = WebHost.create_ordered_tutorials_file() + games_with_tutorial = set(entry["gameTitle"] for entry in tutorials_data) + for game_name, world_type in AutoWorldRegister.world_types.items(): + if not world_type.hidden: + with self.subTest(game_name): + try: + self.assertIn(game_name, games_with_tutorial) + except AssertionError: + # look for partial name in the tutorial name + for game in games_with_tutorial: + if game_name in game: + break + else: + self.fail(f"{game_name} has no setup tutorial. " + f"Games with Tutorial: {games_with_tutorial}") diff --git a/test/webhost/__init__.py b/test/webhost/__init__.py new file mode 100644 index 00000000..e69de29b diff --git a/worlds/AutoWorld.py b/worlds/AutoWorld.py index 7f974741..ffd2c6b3 100644 --- a/worlds/AutoWorld.py +++ b/worlds/AutoWorld.py @@ -8,9 +8,9 @@ from Options import Option class AutoWorldRegister(type): - world_types: Dict[str, AutoWorldRegister] = {} + world_types: Dict[str, type(World)] = {} - def __new__(cls, name: str, bases: Tuple[type, ...], dct: Dict[str, Any]) -> AutoWorldRegister: + def __new__(mcs, name: str, bases: Tuple[type, ...], dct: Dict[str, Any]) -> AutoWorldRegister: if "web" in dct: assert isinstance(dct["web"], WebWorld), "WebWorld has to be instantiated." # filter out any events @@ -38,7 +38,7 @@ class AutoWorldRegister(type): base.__dict__["required_client_version"]) # construct class - new_class = super().__new__(cls, name, bases, dct) + new_class = super().__new__(mcs, name, bases, dct) if "game" in dct: AutoWorldRegister.world_types[dct["game"]] = new_class return new_class