Skip to content
This repository has been archived by the owner on Feb 23, 2024. It is now read-only.

Commit

Permalink
test functions for validate_mesh_structure_pairs (#114)
Browse files Browse the repository at this point in the history
* first test functions for validate_mesh_structure_pairs

* [pre-commit.ci] auto fixes from pre-commit.com hooks

for more information, see https://pre-commit.ci

* adding docstring

* [pre-commit.ci] auto fixes from pre-commit.com hooks

for more information, see https://pre-commit.ci

* writing docstrings to explain the behaviour of the test functions

* validate_atlases.py: updated validate_mesh_structure_pairs function, test_validation.py: updated tests

* [pre-commit.ci] auto fixes from pre-commit.com hooks

for more information, see https://pre-commit.ci

* spliting validate_mesh_structure_pairs function, checking mesh files and structures separately

* writing tests for catch_missing_mesh_files and catch_missing_structures validation functions

* creating an atlas with a missing structure to test catch_missing_structures function

* Update tests/test_unit/test_validation.py

Co-authored-by: Alessandro Felder <[email protected]>

---------

Co-authored-by: pre-commit-ci[bot] <66853113+pre-commit-ci[bot]@users.noreply.github.com>
Co-authored-by: Alessandro Felder <[email protected]>
  • Loading branch information
3 people authored Feb 21, 2024
1 parent b195cb6 commit 76a513a
Show file tree
Hide file tree
Showing 2 changed files with 82 additions and 10 deletions.
44 changes: 34 additions & 10 deletions bg_atlasgen/validate_atlases.py
Original file line number Diff line number Diff line change
Expand Up @@ -110,8 +110,9 @@ def check_additional_references(atlas: BrainGlobeAtlas):
pass


def validate_mesh_structure_pairs(atlas: BrainGlobeAtlas):
"""Ensure mesh files (.obj) exist for each expected structure in the atlas."""
def catch_missing_mesh_files(atlas: BrainGlobeAtlas):
"""Checks if all the structures in the atlas have a corresponding mesh file"""

ids_from_bg_atlas_api = list(atlas.structures.keys())

atlas_path = (
Expand All @@ -126,19 +127,41 @@ def validate_mesh_structure_pairs(atlas: BrainGlobeAtlas):
if file.endswith(".obj")
]

in_mesh_not_bg = []
for id in ids_from_mesh_files:
if id not in ids_from_bg_atlas_api:
in_mesh_not_bg.append(id)

in_bg_not_mesh = []
for id in ids_from_bg_atlas_api:
if id not in ids_from_mesh_files:
in_bg_not_mesh.append(id)

if len(in_mesh_not_bg) or len(in_bg_not_mesh):
if len(in_bg_not_mesh) != 0:
raise AssertionError(
f"Structures with IDs {in_bg_not_mesh} are in the atlas, but don't have a corresponding mesh file."
)


def catch_missing_structures(atlas: BrainGlobeAtlas):
"""Checks if all the mesh files in the atlas folder are listed as a structure in the atlas"""

ids_from_bg_atlas_api = list(atlas.structures.keys())

atlas_path = (
Path(get_brainglobe_dir())
/ f"{atlas.atlas_name}_v{get_local_atlas_version(atlas.atlas_name)}"
)
obj_path = Path(atlas_path / "meshes")

ids_from_mesh_files = [
int(Path(file).stem)
for file in os.listdir(obj_path)
if file.endswith(".obj")
]

in_mesh_not_bg = []
for id in ids_from_mesh_files:
if id not in ids_from_bg_atlas_api:
in_mesh_not_bg.append(id)

if len(in_mesh_not_bg) != 0:
raise AssertionError(
f"Structures with ID {in_bg_not_mesh} are in the atlas, but don't have a corresponding mesh file; "
f"Structures with IDs {in_mesh_not_bg} have a mesh file, but are not accessible through the atlas."
)

Expand Down Expand Up @@ -176,7 +199,8 @@ def validate_atlas(atlas_name, version, validation_functions):
open_for_visual_check,
validate_checksum,
check_additional_references,
validate_mesh_structure_pairs,
catch_missing_mesh_files,
catch_missing_structures,
]

valid_atlases = []
Expand Down
48 changes: 48 additions & 0 deletions tests/test_unit/test_validation.py
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,8 @@

from bg_atlasgen.validate_atlases import (
_assert_close,
catch_missing_mesh_files,
catch_missing_structures,
validate_atlas_files,
validate_mesh_matches_image_extents,
)
Expand Down Expand Up @@ -34,6 +36,17 @@ def atlas_with_bad_reference_file():
os.rename(bad_name, good_name)


@pytest.fixture
def atlas_with_missing_structure():
atlas = BrainGlobeAtlas("osten_mouse_100um")
modified_structures = atlas.structures.copy()
modified_structures.pop(688)

modified_atlas = BrainGlobeAtlas("osten_mouse_100um")
modified_atlas.structures = modified_structures
return modified_atlas


def test_validate_mesh_matches_image_extents(atlas):
assert validate_mesh_matches_image_extents(atlas)

Expand Down Expand Up @@ -69,3 +82,38 @@ def test_assert_close_negative():
AssertionError, match="differ by more than 10 times pixel size"
):
_assert_close(99.5, 30, 2)


def test_catch_missing_mesh_files(atlas):
"""
Tests if catch_missing_mesh_files function raises an error,
when there is at least one structure in the atlas that doesn't have
a corresponding obj file.
Expected behaviour:
True for "allen_mouse_10um" (structure 545 doesn't have an obj file): fails
the validation function, raises an error --> no output from this test function
"""

with pytest.raises(
AssertionError,
match=r"Structures with IDs \[.*?\] are in the atlas, but don't have a corresponding mesh file.",
):
catch_missing_mesh_files(atlas)


def test_catch_missing_structures(atlas_with_missing_structure):
"""
Tests if catch_missing_structures function raises an error,
when there is at least one orphan obj file (doesn't have a corresponding structure in the atlas)
Expected behaviour:
Currently no atlas fails the validation function this way so the [] is always empty
--> this test function should always raise an error
"""

with pytest.raises(
AssertionError,
match=r"Structures with IDs \[.*?\] have a mesh file, but are not accessible through the atlas.",
):
catch_missing_structures(atlas_with_missing_structure)

0 comments on commit 76a513a

Please sign in to comment.