Skip to content

Commit

Permalink
Add tests
Browse files Browse the repository at this point in the history
  • Loading branch information
GianlucaFicarelli committed Feb 29, 2024
1 parent 214f214 commit d0496ec
Show file tree
Hide file tree
Showing 11 changed files with 2,325 additions and 7 deletions.
23 changes: 18 additions & 5 deletions tests/conftest.py
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,15 @@
from tests.utils import DATA, cwd


@pytest.fixture(scope="session")
def nrnivmodl(tmp_path_factory):
"""Compile the mechanisms only once per session."""
path = tmp_path_factory.mktemp("nrnivmodl_dir")
with cwd(path):
os.popen(f"nrnivmodl {DATA}/mechanisms").read()
return path


@pytest.fixture
def workspace(tmp_path):
"""Change the working directory to tmp_path.
Expand All @@ -35,7 +44,7 @@ def workspace(tmp_path):


@pytest.fixture
def emodel_dir(workspace):
def emodel_dir(workspace, nrnivmodl):
"""Copy the required files to workspace/emodel."""
dirs = ["config", "mechanisms", "morphology", "ephys_data"]
files = ["final.json"]
Expand All @@ -44,6 +53,7 @@ def emodel_dir(workspace):
shutil.copytree(DATA / name, dst / name)
for name in files:
shutil.copyfile(DATA / name, dst / name)
shutil.copytree(nrnivmodl / "x86_64", workspace / "x86_64")
yield dst


Expand Down Expand Up @@ -72,7 +82,10 @@ def db_restart(emodel_dir):


@pytest.fixture
def evaluator(db, emodel_dir):
os.popen(f"nrnivmodl {emodel_dir}/mechanisms").read()
db.get_mechanisms_directory = lambda: None
return get_evaluator_from_access_point(access_point=db)
def db_from_nexus(emodel_dir):
return get_access_point(
"local",
emodel="L5PC",
emodel_dir=emodel_dir,
recipes_path=emodel_dir / "config/recipes_nexus.json",
)
4 changes: 3 additions & 1 deletion tests/functional_tests/test_protocols.py
Original file line number Diff line number Diff line change
Expand Up @@ -20,13 +20,15 @@
from numpy.testing import assert_allclose
from pandas.testing import assert_frame_equal

from bluepyemodel.evaluation.evaluation import get_evaluator_from_access_point

def test_protocols(db, evaluator, tmp_path):

def test_protocols(db, tmp_path):
logging.basicConfig(level=logging.DEBUG)
logging.getLogger().setLevel(logging.DEBUG)

params = db.get_emodel().parameters
evaluator = get_evaluator_from_access_point(access_point=db)

responses = evaluator.run_protocols(
protocols=evaluator.fitness_protocols.values(), param_values=params
Expand Down
58 changes: 58 additions & 0 deletions tests/functional_tests/test_protocols_from_nexus.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,58 @@
"""
Copyright 2024, EPFL/Blue Brain Project
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
"""

import logging

import pandas as pd
from numpy.testing import assert_allclose
from pandas.testing import assert_frame_equal

from bluepyemodel.evaluation.evaluation import get_evaluator_from_access_point


def test_protocols(db_from_nexus, tmp_path):
logging.basicConfig(level=logging.DEBUG)
logging.getLogger().setLevel(logging.DEBUG)

params = db_from_nexus.get_emodel().parameters
evaluator = get_evaluator_from_access_point(access_point=db_from_nexus)

responses = evaluator.run_protocols(
protocols=evaluator.fitness_protocols.values(), param_values=params
)

# FIXME: remove print after clarifying the different result when executing the test alone
print(responses)
assert_allclose(responses["bpo_rmp"], -82.61402706564716, rtol=1e-06)
assert_allclose(responses["bpo_holding_current"], -0.05, rtol=1e-06)
assert_allclose(responses["bpo_rin"], 41.13626022273351, rtol=1e-06)
assert_allclose(responses["bpo_threshold_current"], 0.3757011543411314, rtol=1e-06)

for prot_name in [
"APWaveform_280.soma.v",
"IDrest_150.soma.v",
"IDrest_250.soma.v",
"IV_-100.soma.v",
"RinProtocol.soma.v",
"RMPProtocol.soma.v",
"SearchHoldingCurrent.soma.v",
"SearchThresholdCurrent.soma.v",
]:
output_path = f"{tmp_path}/test_{prot_name}.csv"
responses[prot_name].response.to_csv(output_path, index=False)
expected_df = pd.read_csv(output_path)
response = responses[prot_name].response
assert_frame_equal(response, expected_df)
2 changes: 1 addition & 1 deletion tests/functional_tests/test_validation.py
Original file line number Diff line number Diff line change
Expand Up @@ -57,4 +57,4 @@ def test_validation(db):
)

assert len(emodels) == 1
assert emodels[0].passed_validation
assert emodels[0].passed_validation is True
70 changes: 70 additions & 0 deletions tests/functional_tests/test_validation_from_nexus.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,70 @@
"""
Copyright 2024, EPFL/Blue Brain Project
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
"""

import logging

from bluepyemodel.validation.validation import define_validation_function, validate


def _always_true_validation(model, threshold=5.0, validation_protocols_only=False):
return True


def test_define_validation_function(db_from_nexus):

model = {
"scores": {"a": 0.0, "b": 4.9, "c": 0.5, "d": 9.9},
"scores_validation": {"c": 0.5, "d": 9.9},
}

db_from_nexus.pipeline_settings.validation_function = _always_true_validation

validation_function = define_validation_function(db_from_nexus)

validated = bool(
validation_function(
model,
db_from_nexus.pipeline_settings.validation_threshold,
False,
)
)

assert validated


def test_validation(db_from_nexus):

logging.basicConfig(level=logging.DEBUG)
logging.getLogger().setLevel(logging.DEBUG)

def _get_final_content(lock_file=True):
# enforce validated to None to ensure that the validation is run
result = get_final_content(lock_file=lock_file)
for key, value in result.items():
assert "validated" in value
value["validated"] = None
return result

get_final_content = db_from_nexus.get_final_content
db_from_nexus.get_final_content = _get_final_content
db_from_nexus.get_mechanisms_directory = lambda: None
emodels = validate(
access_point=db_from_nexus,
mapper=map,
)

assert len(emodels) == 1
assert emodels[0].passed_validation is True
Loading

0 comments on commit d0496ec

Please sign in to comment.