From 776b145cf2e98a255804b645aa0090b2b953d7a0 Mon Sep 17 00:00:00 2001 From: Kristjan Eimre Date: Thu, 25 Jan 2024 19:32:03 +0200 Subject: [PATCH] update dependencies; migrate tests --- aiida_optimade/mappers/entries.py | 6 +++ aiida_optimade/mappers/structures.py | 4 +- requirements.txt | 6 +-- tests/cli/conftest.py | 14 ++--- tests/cli/test_calc.py | 18 +++---- tests/cli/test_init.py | 26 +++++----- tests/cli/test_run.py | 10 ++-- tests/conftest.py | 77 ++++++++++++---------------- 8 files changed, 79 insertions(+), 82 deletions(-) diff --git a/aiida_optimade/mappers/entries.py b/aiida_optimade/mappers/entries.py index d98fe465..8c7111ff 100644 --- a/aiida_optimade/mappers/entries.py +++ b/aiida_optimade/mappers/entries.py @@ -21,6 +21,12 @@ class ResourceMapper(OptimadeResourceMapper): "relationships", "links", "meta", + "description", + "related", + "structures", + "data", + "self", + "references", } @classmethod diff --git a/aiida_optimade/mappers/structures.py b/aiida_optimade/mappers/structures.py index c7f67b41..d2fa8dff 100644 --- a/aiida_optimade/mappers/structures.py +++ b/aiida_optimade/mappers/structures.py @@ -22,7 +22,9 @@ class StructureMapper(ResourceMapper): "data.core.cif.CifData.": CifDataTranslator, "data.core.structure.StructureData.": StructureDataTranslator, } - REQUIRED_ATTRIBUTES = set(StructureResourceAttributes.schema().get("required")) + REQUIRED_ATTRIBUTES = set( + StructureResourceAttributes.model_json_schema().get("required") + ) # This should be REQUIRED_FIELDS, but should be set as such in `optimade` ENTRY_RESOURCE_CLASS = StructureResource diff --git a/requirements.txt b/requirements.txt index d466b9ba..fe3201c1 100644 --- a/requirements.txt +++ b/requirements.txt @@ -1,6 +1,6 @@ -optimade[server]~=0.25.3 -aiida-core~=2.4.0 -pymatgen>=2019.7.2,!=2019.9.7,<2023.11.13 +optimade[server]~=1.0.1 +aiida-core~=2.5.0 +#pymatgen>=2019.7.2,!=2019.9.7,<2023.11.13 # Dependencies used directly in this package, but included through other dependencies: # aiida-core: diff --git a/tests/cli/conftest.py b/tests/cli/conftest.py index 0379dc00..ce6bb79f 100644 --- a/tests/cli/conftest.py +++ b/tests/cli/conftest.py @@ -10,7 +10,7 @@ @pytest.fixture -def aiida_test_profile() -> str: +def aiida_test_profile_name() -> str: """Return AiiDA test profile used for AiiDA-OPTIMADE""" from aiida_optimade.cli.cmd_aiida_optimade import AIIDA_OPTIMADE_TEST_PROFILE @@ -18,7 +18,7 @@ def aiida_test_profile() -> str: @pytest.fixture -def run_cli_command(aiida_test_profile: str): +def run_cli_command(aiida_test_profile_name: str): """Run a `click` command with the given options. The call will raise if the command triggered an exception or the exit code returned @@ -42,10 +42,10 @@ def _run_cli_command( import traceback runner = click.testing.CliRunner() - profile = os.getenv("AIIDA_PROFILE", aiida_test_profile) + profile = os.getenv("AIIDA_PROFILE", aiida_test_profile_name) if profile == "test_profile": # This is for local tests only - profile = aiida_test_profile + profile = aiida_test_profile_name result = runner.invoke(command, options or [], env={"AIIDA_PROFILE": profile}) if raises: @@ -67,7 +67,7 @@ def _run_cli_command( @pytest.fixture -def run_and_terminate_server(aiida_test_profile: str): +def run_and_terminate_server(aiida_test_profile_name: str): """Run a `click` command with the given options. The call will raise if the command triggered an exception or the exit code returned @@ -88,10 +88,10 @@ def _run_and_terminate_server( :param raises: Whether the command is expected to raise an exception :return: Test result """ - profile = os.getenv("AIIDA_PROFILE", aiida_test_profile) + profile = os.getenv("AIIDA_PROFILE", aiida_test_profile_name) if profile == "test_profile": # This is for local tests only - profile = aiida_test_profile + profile = aiida_test_profile_name args = ["aiida-optimade", "-p", profile] args.append(command) diff --git a/tests/cli/test_calc.py b/tests/cli/test_calc.py index ac89a691..1eb07942 100644 --- a/tests/cli/test_calc.py +++ b/tests/cli/test_calc.py @@ -10,7 +10,7 @@ os.getenv("PYTEST_OPTIMADE_CONFIG_FILE") is not None, reason="Test is not for MongoDB", ) -def test_calc_all_new(run_cli_command, aiida_profile, top_dir, caplog): +def test_calc_all_new(run_cli_command, aiida_profile_populated, top_dir, caplog): """Test `aiida-optimade -p profile_name calc` works for non-existent fields. By "non-existent" the meaning is calculating fields that don't already exist for @@ -23,7 +23,7 @@ def test_calc_all_new(run_cli_command, aiida_profile, top_dir, caplog): from aiida_optimade.translators.entities import AiidaEntityTranslator # Clear database and get initialized_structure_nodes.aiida - aiida_profile.reset_db() + aiida_profile_populated.clear_profile() archive = top_dir.joinpath("tests/cli/static/initialized_structure_nodes.aiida") import_archive(archive) @@ -96,7 +96,7 @@ def test_calc_all_new(run_cli_command, aiida_profile, top_dir, caplog): ), caplog.text # Repopulate database with the "proper" test data - aiida_profile.reset_db() + aiida_profile_populated.clear_profile() original_data = top_dir.joinpath("tests/static/test_structures.aiida") import_archive(original_data) @@ -105,7 +105,7 @@ def test_calc_all_new(run_cli_command, aiida_profile, top_dir, caplog): os.getenv("PYTEST_OPTIMADE_CONFIG_FILE") is not None, reason="Test is not for MongoDB", ) -def test_calc(run_cli_command, aiida_profile, top_dir): +def test_calc(run_cli_command, aiida_profile_populated, top_dir): """Test `aiida-optimade -p profile_name calc` works.""" from aiida import orm from aiida.tools.archive.imports import import_archive @@ -114,7 +114,7 @@ def test_calc(run_cli_command, aiida_profile, top_dir): from aiida_optimade.translators.entities import AiidaEntityTranslator # Clear database and get initialized_structure_nodes.aiida - aiida_profile.reset_db() + aiida_profile_populated.clear_profile() archive = top_dir.joinpath("tests/cli/static/initialized_structure_nodes.aiida") import_archive(archive) @@ -158,7 +158,7 @@ def test_calc(run_cli_command, aiida_profile, top_dir): assert n_structure_data == n_updated_structure_data # Repopulate database with the "proper" test data - aiida_profile.reset_db() + aiida_profile_populated.clear_profile() original_data = top_dir.joinpath("tests/static/test_structures.aiida") import_archive(original_data) @@ -167,7 +167,7 @@ def test_calc(run_cli_command, aiida_profile, top_dir): os.getenv("PYTEST_OPTIMADE_CONFIG_FILE") is not None, reason="Test is not for MongoDB", ) -def test_calc_partially_init(run_cli_command, aiida_profile, top_dir, caplog): +def test_calc_partially_init(run_cli_command, aiida_profile_populated, top_dir, caplog): """Test `aiida-optimade -p profile_name calc` works for a partially initalized DB""" from aiida import orm from aiida.tools.archive.imports import import_archive @@ -176,7 +176,7 @@ def test_calc_partially_init(run_cli_command, aiida_profile, top_dir, caplog): from aiida_optimade.translators.entities import AiidaEntityTranslator # Clear database and get initialized_structure_nodes.aiida - aiida_profile.reset_db() + aiida_profile_populated.clear_profile() archive = top_dir.joinpath("tests/cli/static/initialized_structure_nodes.aiida") import_archive(archive) @@ -255,6 +255,6 @@ def test_calc_partially_init(run_cli_command, aiida_profile, top_dir, caplog): ), caplog.text # Repopulate database with the "proper" test data - aiida_profile.reset_db() + aiida_profile_populated.clear_profile() original_data = top_dir.joinpath("tests/static/test_structures.aiida") import_archive(original_data) diff --git a/tests/cli/test_init.py b/tests/cli/test_init.py index 06e52a66..b5ab43f0 100644 --- a/tests/cli/test_init.py +++ b/tests/cli/test_init.py @@ -10,7 +10,7 @@ os.getenv("PYTEST_OPTIMADE_CONFIG_FILE") is not None, reason="Test is not for MongoDB", ) -def test_init_structuredata(run_cli_command, aiida_profile, top_dir, caplog): +def test_init_structuredata(run_cli_command, aiida_profile_populated, top_dir, caplog): """Test `aiida-optimade -p profile_name init` works for StructureData Nodes. Also, check the `-f/--force` option. @@ -22,7 +22,7 @@ def test_init_structuredata(run_cli_command, aiida_profile, top_dir, caplog): from aiida_optimade.translators.entities import AiidaEntityTranslator # Clear database - aiida_profile.reset_db() + aiida_profile_populated.clear_profile() archive = top_dir.joinpath("tests/cli/static/structure_data_nodes.aiida") import_archive(archive) @@ -82,7 +82,7 @@ def test_init_structuredata(run_cli_command, aiida_profile, top_dir, caplog): ), caplog.text # Repopulate database with the "proper" test data - aiida_profile.reset_db() + aiida_profile_populated.clear_profile() original_data = top_dir.joinpath("tests/static/test_structures.aiida") import_archive(original_data) @@ -91,7 +91,7 @@ def test_init_structuredata(run_cli_command, aiida_profile, top_dir, caplog): os.getenv("PYTEST_OPTIMADE_CONFIG_FILE") is not None, reason="Test is not for MongoDB", ) -def test_init_cifdata(run_cli_command, aiida_profile, top_dir, caplog): +def test_init_cifdata(run_cli_command, aiida_profile_populated, top_dir, caplog): """Test `aiida-optimade -p profile_name init` works for CifData Nodes.""" from aiida import orm from aiida.tools.archive.imports import import_archive @@ -100,7 +100,7 @@ def test_init_cifdata(run_cli_command, aiida_profile, top_dir, caplog): from aiida_optimade.translators.entities import AiidaEntityTranslator # Clear database - aiida_profile.reset_db() + aiida_profile_populated.clear_profile() archive = top_dir.joinpath("tests/cli/static/cif_data_nodes.aiida") import_archive(archive) @@ -136,7 +136,7 @@ def test_init_cifdata(run_cli_command, aiida_profile, top_dir, caplog): ), caplog.text # Repopulate database with the "proper" test data - aiida_profile.reset_db() + aiida_profile_populated.clear_profile() original_data = top_dir.joinpath("tests/static/test_structures.aiida") import_archive(original_data) @@ -144,7 +144,9 @@ def test_init_cifdata(run_cli_command, aiida_profile, top_dir, caplog): @pytest.mark.skipif( os.getenv("PYTEST_OPTIMADE_CONFIG_FILE") is None, reason="Test is only for MongoDB" ) -def test_init_structuredata_mongo(run_cli_command, aiida_profile, top_dir, caplog): +def test_init_structuredata_mongo( + run_cli_command, aiida_profile_populated, top_dir, caplog +): """Test `aiida-optimade -p profile_name init --mongo` works for StructureData Nodes. Also, check the `-f/--force` option. @@ -158,7 +160,7 @@ def test_init_structuredata_mongo(run_cli_command, aiida_profile, top_dir, caplo from aiida_optimade.translators.entities import AiidaEntityTranslator # Clear databases - aiida_profile.reset_db() + aiida_profile_populated.clear_profile() STRUCTURES_MONGO.collection.drop() archive = top_dir.joinpath("tests/cli/static/structure_data_nodes.aiida") @@ -222,7 +224,7 @@ def test_init_structuredata_mongo(run_cli_command, aiida_profile, top_dir, caplo ), caplog.text # Repopulate databases with the "proper" test data - aiida_profile.reset_db() + aiida_profile_populated.clear_profile() import_archive(top_dir.joinpath("tests/static/test_structures.aiida")) STRUCTURES_MONGO.collection.drop() with open(top_dir.joinpath("tests/static/test_structures_mongo.json")) as handle: @@ -233,7 +235,7 @@ def test_init_structuredata_mongo(run_cli_command, aiida_profile, top_dir, caplo @pytest.mark.skipif( os.getenv("PYTEST_OPTIMADE_CONFIG_FILE") is None, reason="Test is only for MongoDB" ) -def test_init_cifdata_mongo(run_cli_command, aiida_profile, top_dir, caplog): +def test_init_cifdata_mongo(run_cli_command, aiida_profile_populated, top_dir, caplog): """Test `aiida-optimade -p profile_name init` works for CifData Nodes.""" import bson.json_util from aiida import orm @@ -244,7 +246,7 @@ def test_init_cifdata_mongo(run_cli_command, aiida_profile, top_dir, caplog): from aiida_optimade.translators.entities import AiidaEntityTranslator # Clear databases - aiida_profile.reset_db() + aiida_profile_populated.clear_profile() STRUCTURES_MONGO.collection.drop() archive = top_dir.joinpath("tests/cli/static/cif_data_nodes.aiida") @@ -283,7 +285,7 @@ def test_init_cifdata_mongo(run_cli_command, aiida_profile, top_dir, caplog): ), caplog.text # Repopulate database with the "proper" test data - aiida_profile.reset_db() + aiida_profile_populated.clear_profile() import_archive(top_dir.joinpath("tests/static/test_structures.aiida")) STRUCTURES_MONGO.collection.drop() with open(top_dir.joinpath("tests/static/test_structures_mongo.json")) as handle: diff --git a/tests/cli/test_run.py b/tests/cli/test_run.py index f41450c9..68ec1567 100644 --- a/tests/cli/test_run.py +++ b/tests/cli/test_run.py @@ -10,17 +10,17 @@ @pytest.fixture -def run_server(aiida_test_profile: str): +def run_server(aiida_test_profile_name: str): """Run the server using `aiida-optimade run` :param options: the list of command line options to pass to `aiida-optimade run` invocation :param raises: whether `aiida-optimade run` is expected to raise an exception """ - profile = os.getenv("AIIDA_PROFILE", aiida_test_profile) + profile = os.getenv("AIIDA_PROFILE", aiida_test_profile_name) if profile == "test_profile": # This is for local tests only - profile = aiida_test_profile + profile = aiida_test_profile_name args = ["aiida-optimade", "-p", profile, "run"] env = dict(os.environ) @@ -115,7 +115,7 @@ def test_logging_precedence(run_and_terminate_server): ), f"output: {output!r}, errors: {errors!r}" -def test_env_var_is_set(run_and_terminate_server, aiida_test_profile: str): +def test_env_var_is_set(run_and_terminate_server, aiida_test_profile_name: str): """Test the AIIDA_PROFILE env var is set The issue with this test, is that the set "AIIDA_PROFILE" environment variable @@ -131,7 +131,7 @@ def test_env_var_is_set(run_and_terminate_server, aiida_test_profile: str): assert fixture_profile is not None if fixture_profile == "test_profile": # This is for local tests only - fixture_profile = aiida_test_profile + fixture_profile = aiida_test_profile_name output, errors = run_and_terminate_server(command="run") assert fixture_profile in output, f"output: {output!r}, errors: {errors!r}" diff --git a/tests/conftest.py b/tests/conftest.py index eb983da4..0410fe1b 100644 --- a/tests/conftest.py +++ b/tests/conftest.py @@ -3,7 +3,8 @@ from pathlib import Path import pytest -from aiida.manage.tests import TestManager + +pytest_plugins = ["aiida.manage.tests.pytest_fixtures"] @pytest.fixture(scope="session") @@ -32,56 +33,42 @@ def setup_config(top_dir) -> None: @pytest.fixture(scope="session", autouse=True) -def aiida_profile(top_dir, setup_config) -> TestManager: - """Load test data for AiiDA test profile - - It is necessary to remove `AIIDA_PROFILE`, since it clashes with the test profile - """ - from aiida import load_profile - from aiida.manage.tests import ( - get_test_backend_name, - get_test_profile_name, - test_manager, - ) +def aiida_profile_populated(top_dir, setup_config, aiida_profile): + """Load test data for AiiDA test profile""" from aiida.tools.archive.imports import import_archive org_env_var = os.getenv("AIIDA_PROFILE") test_env_var = os.getenv("PYTEST_OPTIMADE_CONFIG_FILE") try: - # Setup profile - with test_manager( - backend=get_test_backend_name(), profile_name=get_test_profile_name() - ) as manager: - manager.reset_db() - - profile = load_profile() - # If test locally `AIIDA_TEST_PROFILE` may not set and `test_profile` will be used - assert profile.name in ["test_profile", "test_psql_dos"] - os.environ["AIIDA_PROFILE"] = profile.name - - # Use AiiDA DB - import_archive(top_dir.joinpath("tests/static/test_structures.aiida")) - - if test_env_var: - # Use MongoDB - assert os.getenv("OPTIMADE_CONFIG_FILE", "") == test_env_var, ( - "Config file env var not set prior to updating the MongoDB! Found " - "it to be a MongoDB backend, since PYTEST_OPTIMADE_CONFIG_FILE is " - f"set to {test_env_var}" - ) - import bson.json_util - - from aiida_optimade.routers.structures import STRUCTURES_MONGO - - STRUCTURES_MONGO.collection.drop() - with open( - top_dir.joinpath("tests/static/test_structures_mongo.json") - ) as handle: - data = bson.json_util.loads(handle.read()) - STRUCTURES_MONGO.collection.insert_many(data) - - yield manager + aiida_profile.clear_profile() + + # If test locally `AIIDA_TEST_PROFILE` may not set and `test_profile` will be used + # assert profile.name in ["test_profile", "test_psql_dos"] + os.environ["AIIDA_PROFILE"] = aiida_profile.name + + # Use AiiDA DB + import_archive(top_dir.joinpath("tests/static/test_structures.aiida")) + + if test_env_var: + # Use MongoDB + assert os.getenv("OPTIMADE_CONFIG_FILE", "") == test_env_var, ( + "Config file env var not set prior to updating the MongoDB! Found " + "it to be a MongoDB backend, since PYTEST_OPTIMADE_CONFIG_FILE is " + f"set to {test_env_var}" + ) + import bson.json_util + + from aiida_optimade.routers.structures import STRUCTURES_MONGO + + STRUCTURES_MONGO.collection.drop() + with open( + top_dir.joinpath("tests/static/test_structures_mongo.json") + ) as handle: + data = bson.json_util.loads(handle.read()) + STRUCTURES_MONGO.collection.insert_many(data) + + yield aiida_profile finally: if org_env_var is not None: os.environ["AIIDA_PROFILE"] = org_env_var