diff --git a/CHANGELOG.md b/CHANGELOG.md index 2c35279..02b214c 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -4,6 +4,12 @@ ### Fixed +- Fixed issue where mlst results with no calls crashed PRP. + +### Changed + +- Added mypy as test dependency + ### Changed ## [0.11.1] diff --git a/prp/parse/typing.py b/prp/parse/typing.py index 6b4cec8..5512b8a 100644 --- a/prp/parse/typing.py +++ b/prp/parse/typing.py @@ -43,6 +43,9 @@ def parse_mlst_results(mlst_fpath: str) -> TypingResultMlst: LOG.info("Parsing mlst results") with open(mlst_fpath, "r", encoding="utf-8") as jsonfile: result = json.load(jsonfile)[0] + # get raw allele info + alleles = {} if result.get("alleles") is None else result["alleles"] + # create typing result object result_obj = TypingResultMlst( scheme=result["scheme"], sequence_type=( @@ -50,7 +53,7 @@ def parse_mlst_results(mlst_fpath: str) -> TypingResultMlst: ), alleles={ gene: _process_allele_call(allele) - for gene, allele in result["alleles"].items() + for gene, allele in alleles.items() }, ) return MethodIndex( diff --git a/pyproject.toml b/pyproject.toml index 61aff58..4dbbef4 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -46,6 +46,7 @@ dev = [ ] test = [ "pytest-cov ~=4.1.0", + "mypy == 1.13.0" ] [build-system] diff --git a/tests/fixtures/__init__.py b/tests/fixtures/__init__.py index 214fa3e..527fa3c 100644 --- a/tests/fixtures/__init__.py +++ b/tests/fixtures/__init__.py @@ -5,3 +5,8 @@ from .saureus import * from .shigella import * from .streptococcus import * + +@pytest.fixture() +def mlst_result_path_no_call(data_path): + """Get path for mlst file where alleles was not called.""" + return str(data_path.joinpath("mlst.nocall.json")) \ No newline at end of file diff --git a/tests/fixtures/mlst.nocall.json b/tests/fixtures/mlst.nocall.json new file mode 100644 index 0000000..8aa1b81 --- /dev/null +++ b/tests/fixtures/mlst.nocall.json @@ -0,0 +1,9 @@ +[ + { + "sequence_type" : "-", + "scheme" : "-", + "alleles" : null, + "id" : "unique_file_id", + "filename" : "assembly_file_name.fasta" + } +] \ No newline at end of file diff --git a/tests/parse/test_typing.py b/tests/parse/test_typing.py index 74000b9..c2015b8 100644 --- a/tests/parse/test_typing.py +++ b/tests/parse/test_typing.py @@ -2,7 +2,7 @@ import pytest import logging -from prp.parse.typing import replace_cgmlst_errors +from prp.parse.typing import replace_cgmlst_errors, parse_mlst_results from prp.models.typing import ChewbbacaErrors # build test cases for handeling chewbacca allele caller errors and annotations @@ -84,4 +84,28 @@ def test_replace_cgmlst_errors_warnings(caplog): # run test that a warning was triggered if input is unknown string allele = "A_STRANGE_STRING" replace_cgmlst_errors(allele, include_novel_alleles=True, correct_alleles=True) - assert allele in caplog.text \ No newline at end of file + assert allele in caplog.text + + +def test_parse_mlst_result(ecoli_mlst_path): + """Test parsing of MLST result file.""" + # FIRST run result parser + res_obj = parse_mlst_results(ecoli_mlst_path) + + # THEN verify result type + assert res_obj.type == 'mlst' + # THEN verify software + assert res_obj.software == 'mlst' + # THEN verify sequence type and allele assignment + assert res_obj.result.sequence_type == 58 + assert len(res_obj.result.alleles) == 8 + + +def test_parse_mlst_result_w_no_call(mlst_result_path_no_call): + """Test parsing of MLST results file where the alleles was not called.""" + # FIRST run result parser + res_obj = parse_mlst_results(mlst_result_path_no_call) + + # THEN verify that sequence type is None + assert res_obj.result.sequence_type is None + assert len(res_obj.result.alleles) == 0 \ No newline at end of file