diff --git a/isatools/model/datafile.py b/isatools/model/datafile.py index 04aa8f742..ea0f35b4a 100644 --- a/isatools/model/datafile.py +++ b/isatools/model/datafile.py @@ -202,6 +202,42 @@ def __ne__(self, other): return not self == other +class ImageFile(DataFile): + """Represents an Image file in an experimental graph.""" + + def __init__(self, filename="", id_="", generated_from=None, comments=None): + super().__init__(filename=filename, id_=id_, generated_from=generated_from, comments=comments) + + self.label = "Image File" + + def __repr__(self): + return ( + "isatools.model.ImageFile(filename='{0.filename}', " + "generated_from={0.generated_from}, comments={0.comments})".format(self) + ) + + def __str__(self): + return """ImageFile( + filename={data_file.filename} + generated_from={num_generated_from} Sample objects + comments={num_comments} Comment objects +)""".format(data_file=self, num_generated_from=len(self.generated_from), num_comments=len(self.comments)) + + def __hash__(self): + return hash(repr(self)) + + def __eq__(self, other): + return ( + isinstance(other, ImageFile) + and self.filename == other.filename + and self.generated_from == other.generated_from + and self.comments == other.comments + ) + + def __ne__(self, other): + return not self == other + + class RawSpectralDataFile(DataFile): """Represents a raw spectral data file in an experimental graph.""" @@ -428,6 +464,44 @@ def __ne__(self, other): return not self == other +class MetaboliteAssignmentFile(DataFile): + """Represents a metabolite assignment file in an experimental graph.""" + + def __init__(self, filename="", id_="", generated_from=None, comments=None): + super().__init__(filename=filename, id_=id_, generated_from=generated_from, comments=comments) + + self.label = "Metabolite Assignment File" + + def __repr__(self): + return ( + "isatools.model.MetaboliteAssignmentFile(" + "filename='{data_file.filename}', " + "generated_from={data_file.generated_from}, " + "comments={data_file.comments})".format(data_file=self) + ) + + def __str__(self): + return """MetaboliteAssignmentFile( + filename={data_file.filename} + generated_from={num_generated_from} Sample objects + comments={num_comments} Comment objects +)""".format(data_file=self, num_generated_from=len(self.generated_from), num_comments=len(self.comments)) + + def __hash__(self): + return hash(repr(self)) + + def __eq__(self, other): + return ( + isinstance(other, MetaboliteAssignmentFile) + and self.filename == other.filename + and self.generated_from == other.generated_from + and self.comments == other.comments + ) + + def __ne__(self, other): + return not self == other + + class DerivedArrayDataMatrixFile(DataFile): """Represents a derived array data matrix file in an experimental graph.""" diff --git a/isatools/resources/config/xml/histology.xml b/isatools/resources/config/xml/histology.xml index 2255a4454..8a8ef0360 100644 --- a/isatools/resources/config/xml/histology.xml +++ b/isatools/resources/config/xml/histology.xml @@ -1 +1,50 @@ -[INSTITUTION].Group-[GROUP_NO].Subject-[SUBJECT_NO].[SAMPLE_EXTRACT].Extract-[EXTRACT_COUNT].LE-[LABEL_COUNT].ASSAY-[HYB_COUNT][INSTITUTION].Group-[GROUP_NO].Subject-[SUBJECT_NO].[SAMPLE_EXTRACT] \ No newline at end of file + + + + + + + + + + + + + + + [INSTITUTION].Group-[GROUP_NO].Subject-[SUBJECT_NO].[SAMPLE_EXTRACT].Extract-[EXTRACT_COUNT].LE-[LABEL_COUNT].ASSAY-[HYB_COUNT] + + + + + + + + + + [INSTITUTION].Group-[GROUP_NO].Subject-[SUBJECT_NO].[SAMPLE_EXTRACT] + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/isatools/resources/config/xml/phenotyping_imaging.xml b/isatools/resources/config/xml/phenotyping_imaging.xml new file mode 100644 index 000000000..b4de93680 --- /dev/null +++ b/isatools/resources/config/xml/phenotyping_imaging.xml @@ -0,0 +1,46 @@ + + + + + + + + + [INSTITUTION].Group-[GROUP_NO].Subject-[SUBJECT_NO].[SAMPLE_EXTRACT] + + + + + + + + [INSTITUTION].Group-[GROUP_NO].Subject-[SUBJECT_NO].[SAMPLE_EXTRACT].Extract-[EXTRACT_COUNT].LE-[LABEL_COUNT].ASSAY-[HYB_COUNT] + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/tests/isajson/test_isajson.py b/tests/isajson/test_isajson.py index 6f8ea1a29..91b36019e 100644 --- a/tests/isajson/test_isajson.py +++ b/tests/isajson/test_isajson.py @@ -460,6 +460,18 @@ def test_json_load_and_dump_bii_s_test(self): assays = [a for a in studies["assays"] if a["filename"] == "a_assay.txt"][0] self.assertEqual(assays["materials"]["otherMaterials"][1]["type"], "Extract Name") + + def test_json_load_and_dump_imagefile_test(self): + # Load into ISA objects + with open(os.path.join(utils.JSON_DATA_DIR, "ISA-Image", "isa-image.json")) as isajson_fp: + investigation = isajson.load(isajson_fp) + + # Dump into ISA JSON from ISA objects + investigation_reload = json.loads(json.dumps(investigation, cls=isajson.ISAJSONEncoder)) + studies = [s for s in investigation_reload["studies"] if s["filename"] == "s_study.txt"][0] + assays = [a for a in studies["assays"] if a["filename"] == "a_assay.txt"][0] + self.assertEqual(assays["dataFiles"][1]["type"], "Image File") + def test_json_load_and_dump_isa_labeled_extract(self): # Load into ISA objects with open(os.path.join(utils.JSON_DATA_DIR, "TEST-ISA-LabeledExtract1", "isa-test-le1.json")) as isajson_fp: diff --git a/tests/isatab/validate/test_core.py b/tests/isatab/validate/test_core.py index cfb5b9f8f..45cd333ca 100644 --- a/tests/isatab/validate/test_core.py +++ b/tests/isatab/validate/test_core.py @@ -43,6 +43,14 @@ def test_bii_s_7(self): report = validate(fp=data_file, config_dir=self.default_conf) self.assertEqual(len(report["warnings"]), 1) + def test_imaging(self): + data_path = path.join(path.dirname(path.abspath(__file__)), "..", "..", "data", "tab", "Imaging") + with open(path.join(data_path, "i_Investigation.txt"), "r") as data_file: + report = validate(fp=data_file, config_dir=self.default_conf) + print(report["errors"]) + self.assertEqual(len(report["errors"]), 0) + + def test_print_rule(self): raw_rule = INVESTIGATION_RULES_MAPPING[0] rule = Rule(**raw_rule) diff --git a/tests/model/test_datafile.py b/tests/model/test_datafile.py index 0d2a35f51..3ce831293 100644 --- a/tests/model/test_datafile.py +++ b/tests/model/test_datafile.py @@ -81,6 +81,7 @@ class TestSubDataFile(TestCase): def setUp(self): self.types = { "RawDataFile": RawDataFile, + "ImageFile": ImageFile, "DerivedDataFile": DerivedDataFile, "RawSpectralDataFile": RawSpectralDataFile, "DerivedArrayDataFile": DerivedArrayDataFile, @@ -92,6 +93,7 @@ def setUp(self): "PostTranslationalModificationAssignmentFile": PostTranslationalModificationAssignmentFile, "AcquisitionParameterDataFile": AcquisitionParameterDataFile, "FreeInductionDecayDataFile": FreeInductionDecayDataFile, + "MetaboliteAssignmentFile": MetaboliteAssignmentFile } self.classes = {} for filetype in self.types: diff --git a/tests/utils/test_isatab_configurator.py b/tests/utils/test_isatab_configurator.py index 2e172541e..434e5550f 100644 --- a/tests/utils/test_isatab_configurator.py +++ b/tests/utils/test_isatab_configurator.py @@ -50,7 +50,7 @@ def test_load_config_metagenome_seq(self): from isatools.io import isatab_configurator as configurator config_dict = configurator.load(self._config_dir) - self.assertEqual(len(config_dict), 30) + self.assertEqual(len(config_dict), 31) self.assertEqual( config_dict[("metagenome sequencing", "nucleotide sequencing")].isatab_configuration[0].table_name, "metagenome_seq",