diff options
Diffstat (limited to 'src/silx/io/test/test_fabioh5.py')
-rwxr-xr-x | src/silx/io/test/test_fabioh5.py | 627 |
1 files changed, 627 insertions, 0 deletions
diff --git a/src/silx/io/test/test_fabioh5.py b/src/silx/io/test/test_fabioh5.py new file mode 100755 index 0000000..9c92f15 --- /dev/null +++ b/src/silx/io/test/test_fabioh5.py @@ -0,0 +1,627 @@ +# /*########################################################################## +# Copyright (C) 2016-2023 European Synchrotron Radiation Facility +# +# Permission is hereby granted, free of charge, to any person obtaining a copy +# of this software and associated documentation files (the "Software"), to deal +# in the Software without restriction, including without limitation the rights +# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +# copies of the Software, and to permit persons to whom the Software is +# furnished to do so, subject to the following conditions: +# +# The above copyright notice and this permission notice shall be included in +# all copies or substantial portions of the Software. +# +# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +# THE SOFTWARE. +# +# ############################################################################*/ +"""Tests for fabioh5 wrapper""" + +__authors__ = ["V. Valls"] +__license__ = "MIT" +__date__ = "02/07/2018" + +import os +import logging +import numpy +import unittest +import tempfile +import shutil + +_logger = logging.getLogger(__name__) + +import fabio +import fabio.file_series +import h5py + +from .. import commonh5 +from .. import fabioh5 + + +class TestFabioH5(unittest.TestCase): + def setUp(self): + header = { + "integer": "-100", + "float": "1.0", + "string": "hi!", + "list_integer": "100 50 0", + "list_float": "1.0 2.0 3.5", + "string_looks_like_list": "2000 hi!", + } + data = numpy.array([[10, 11], [12, 13], [14, 15]], dtype=numpy.int64) + self.fabio_image = fabio.numpyimage.NumpyImage(data, header) + self.h5_image = fabioh5.File(fabio_image=self.fabio_image) + + def test_main_groups(self): + self.assertEqual(self.h5_image.h5py_class, h5py.File) + self.assertEqual(self.h5_image["/"].h5py_class, h5py.File) + self.assertEqual(self.h5_image["/scan_0"].h5py_class, h5py.Group) + self.assertEqual(self.h5_image["/scan_0/instrument"].h5py_class, h5py.Group) + self.assertEqual(self.h5_image["/scan_0/measurement"].h5py_class, h5py.Group) + + def test_wrong_path_syntax(self): + # result tested with a default h5py file + self.assertRaises(ValueError, lambda: self.h5_image[""]) + + def test_wrong_root_name(self): + # result tested with a default h5py file + self.assertRaises(KeyError, lambda: self.h5_image["/foo"]) + + def test_wrong_root_path(self): + # result tested with a default h5py file + self.assertRaises(KeyError, lambda: self.h5_image["/foo/foo"]) + + def test_wrong_name(self): + # result tested with a default h5py file + self.assertRaises(KeyError, lambda: self.h5_image["foo"]) + + def test_wrong_path(self): + # result tested with a default h5py file + self.assertRaises(KeyError, lambda: self.h5_image["foo/foo"]) + + def test_single_frame(self): + data = numpy.arange(2 * 3) + data.shape = 2, 3 + fabio_image = fabio.edfimage.edfimage(data=data) + h5_image = fabioh5.File(fabio_image=fabio_image) + + dataset = h5_image["/scan_0/instrument/detector_0/data"] + self.assertEqual(dataset.h5py_class, h5py.Dataset) + self.assertTrue(isinstance(dataset[()], numpy.ndarray)) + self.assertEqual(dataset.dtype.kind, "i") + self.assertEqual(dataset.shape, (2, 3)) + self.assertEqual(dataset[...][0, 0], 0) + self.assertEqual(dataset.attrs["interpretation"], "image") + + def test_multi_frames(self): + data = numpy.arange(2 * 3) + data.shape = 2, 3 + fabio_image = fabio.edfimage.edfimage(data=data) + fabio_image.append_frame(data=data) + h5_image = fabioh5.File(fabio_image=fabio_image) + + dataset = h5_image["/scan_0/instrument/detector_0/data"] + self.assertEqual(dataset.h5py_class, h5py.Dataset) + self.assertTrue(isinstance(dataset[()], numpy.ndarray)) + self.assertEqual(dataset.dtype.kind, "i") + self.assertEqual(dataset.shape, (2, 2, 3)) + self.assertEqual(dataset[...][0, 0, 0], 0) + self.assertEqual(dataset.attrs["interpretation"], "image") + + def test_heterogeneous_frames(self): + """Frames containing 2 images with different sizes and a cube""" + data1 = numpy.arange(2 * 3) + data1.shape = 2, 3 + data2 = numpy.arange(2 * 5) + data2.shape = 2, 5 + data3 = numpy.arange(2 * 5 * 1) + data3.shape = 2, 5, 1 + fabio_image = fabio.edfimage.edfimage(data=data1) + fabio_image.append_frame(data=data2) + fabio_image.append_frame(data=data3) + h5_image = fabioh5.File(fabio_image=fabio_image) + + dataset = h5_image["/scan_0/instrument/detector_0/data"] + self.assertEqual(dataset.h5py_class, h5py.Dataset) + self.assertTrue(isinstance(dataset[()], numpy.ndarray)) + self.assertEqual(dataset.dtype.kind, "i") + self.assertEqual(dataset.shape, (3, 2, 5, 1)) + self.assertEqual(dataset[...][0, 0, 0], 0) + self.assertEqual(dataset.attrs["interpretation"], "image") + + def test_single_3d_frame(self): + """Image source contains a cube""" + data = numpy.arange(2 * 3 * 4) + data.shape = 2, 3, 4 + # Do not provide the data to the constructor to avoid slicing of the + # data. In this way the result stay a cube, and not a multi-frame + fabio_image = fabio.edfimage.edfimage() + fabio_image.data = data + h5_image = fabioh5.File(fabio_image=fabio_image) + + dataset = h5_image["/scan_0/instrument/detector_0/data"] + self.assertEqual(dataset.h5py_class, h5py.Dataset) + self.assertTrue(isinstance(dataset[()], numpy.ndarray)) + self.assertEqual(dataset.dtype.kind, "i") + self.assertEqual(dataset.shape, (2, 3, 4)) + self.assertEqual(dataset[...][0, 0, 0], 0) + self.assertEqual(dataset.attrs["interpretation"], "image") + + def test_metadata_int(self): + dataset = self.h5_image["/scan_0/instrument/detector_0/others/integer"] + self.assertEqual(dataset.h5py_class, h5py.Dataset) + self.assertEqual(dataset[()], -100) + self.assertEqual(dataset.dtype.kind, "i") + self.assertEqual(dataset.shape, (1,)) + + def test_metadata_float(self): + dataset = self.h5_image["/scan_0/instrument/detector_0/others/float"] + self.assertEqual(dataset.h5py_class, h5py.Dataset) + self.assertEqual(dataset[()], 1.0) + self.assertEqual(dataset.dtype.kind, "f") + self.assertEqual(dataset.shape, (1,)) + + def test_metadata_string(self): + dataset = self.h5_image["/scan_0/instrument/detector_0/others/string"] + self.assertEqual(dataset.h5py_class, h5py.Dataset) + self.assertEqual(dataset[()], numpy.string_("hi!")) + self.assertEqual(dataset.dtype.type, numpy.string_) + self.assertEqual(dataset.shape, (1,)) + + def test_metadata_list_integer(self): + dataset = self.h5_image["/scan_0/instrument/detector_0/others/list_integer"] + self.assertEqual(dataset.h5py_class, h5py.Dataset) + self.assertEqual(dataset.dtype.kind, "u") + self.assertEqual(dataset.shape, (1, 3)) + self.assertEqual(dataset[0, 0], 100) + self.assertEqual(dataset[0, 1], 50) + + def test_metadata_list_float(self): + dataset = self.h5_image["/scan_0/instrument/detector_0/others/list_float"] + self.assertEqual(dataset.h5py_class, h5py.Dataset) + self.assertEqual(dataset.dtype.kind, "f") + self.assertEqual(dataset.shape, (1, 3)) + self.assertEqual(dataset[0, 0], 1.0) + self.assertEqual(dataset[0, 1], 2.0) + + def test_metadata_list_looks_like_list(self): + dataset = self.h5_image[ + "/scan_0/instrument/detector_0/others/string_looks_like_list" + ] + self.assertEqual(dataset.h5py_class, h5py.Dataset) + self.assertEqual(dataset[()], numpy.string_("2000 hi!")) + self.assertEqual(dataset.dtype.type, numpy.string_) + self.assertEqual(dataset.shape, (1,)) + + def test_float_32(self): + float_list = ["1.2", "1.3", "1.4"] + data = numpy.array([[0, 0], [0, 0]], dtype=numpy.int8) + fabio_image = None + for float_item in float_list: + header = {"float_item": float_item} + if fabio_image is None: + fabio_image = fabio.edfimage.EdfImage(data=data, header=header) + else: + fabio_image.append_frame(data=data, header=header) + h5_image = fabioh5.File(fabio_image=fabio_image) + data = h5_image["/scan_0/instrument/detector_0/others/float_item"] + # There is no equality between items + self.assertEqual(len(data), len(set(data))) + # At worst a float32 + self.assertIn(data.dtype.kind, ["d", "f"]) + self.assertLessEqual(data.dtype.itemsize, 32 / 8) + + def test_float_64(self): + float_list = [ + "1469117129.082226", + "1469117136.684986", + "1469117144.312749", + "1469117151.892507", + "1469117159.474265", + "1469117167.100027", + "1469117174.815799", + "1469117182.437561", + "1469117190.094326", + "1469117197.721089", + ] + data = numpy.array([[0, 0], [0, 0]], dtype=numpy.int8) + fabio_image = None + for float_item in float_list: + header = {"time_of_day": float_item} + if fabio_image is None: + fabio_image = fabio.edfimage.EdfImage(data=data, header=header) + else: + fabio_image.append_frame(data=data, header=header) + h5_image = fabioh5.File(fabio_image=fabio_image) + data = h5_image["/scan_0/instrument/detector_0/others/time_of_day"] + # There is no equality between items + self.assertEqual(len(data), len(set(data))) + # At least a float64 + self.assertIn(data.dtype.kind, ["d", "f"]) + self.assertGreaterEqual(data.dtype.itemsize, 64 / 8) + + def test_mixed_float_size__scalar(self): + # We expect to have a precision of 32 bits + float_list = ["1.2", "1.3001"] + expected_float_result = [1.2, 1.3001] + data = numpy.array([[0, 0], [0, 0]], dtype=numpy.int8) + fabio_image = None + for float_item in float_list: + header = {"float_item": float_item} + if fabio_image is None: + fabio_image = fabio.edfimage.EdfImage(data=data, header=header) + else: + fabio_image.append_frame(data=data, header=header) + h5_image = fabioh5.File(fabio_image=fabio_image) + data = h5_image["/scan_0/instrument/detector_0/others/float_item"] + # At worst a float32 + self.assertIn(data.dtype.kind, ["d", "f"]) + self.assertLessEqual(data.dtype.itemsize, 32 / 8) + for computed, expected in zip(data, expected_float_result): + numpy.testing.assert_almost_equal(computed, expected, 5) + + def test_mixed_float_size__list(self): + # We expect to have a precision of 32 bits + float_list = ["1.2 1.3001"] + expected_float_result = numpy.array([[1.2, 1.3001]]) + data = numpy.array([[0, 0], [0, 0]], dtype=numpy.int8) + fabio_image = None + for float_item in float_list: + header = {"float_item": float_item} + if fabio_image is None: + fabio_image = fabio.edfimage.EdfImage(data=data, header=header) + else: + fabio_image.append_frame(data=data, header=header) + h5_image = fabioh5.File(fabio_image=fabio_image) + data = h5_image["/scan_0/instrument/detector_0/others/float_item"] + # At worst a float32 + self.assertIn(data.dtype.kind, ["d", "f"]) + self.assertLessEqual(data.dtype.itemsize, 32 / 8) + for computed, expected in zip(data, expected_float_result): + numpy.testing.assert_almost_equal(computed, expected, 5) + + def test_mixed_float_size__list_of_list(self): + # We expect to have a precision of 32 bits + float_list = ["1.2 1.3001", "1.3001 1.3001"] + expected_float_result = numpy.array([[1.2, 1.3001], [1.3001, 1.3001]]) + data = numpy.array([[0, 0], [0, 0]], dtype=numpy.int8) + fabio_image = None + for float_item in float_list: + header = {"float_item": float_item} + if fabio_image is None: + fabio_image = fabio.edfimage.EdfImage(data=data, header=header) + else: + fabio_image.append_frame(data=data, header=header) + h5_image = fabioh5.File(fabio_image=fabio_image) + data = h5_image["/scan_0/instrument/detector_0/others/float_item"] + # At worst a float32 + self.assertIn(data.dtype.kind, ["d", "f"]) + self.assertLessEqual(data.dtype.itemsize, 32 / 8) + for computed, expected in zip(data, expected_float_result): + numpy.testing.assert_almost_equal(computed, expected, 5) + + def test_ub_matrix(self): + """Data from mediapix.edf""" + header = {} + header["UB_mne"] = "UB0 UB1 UB2 UB3 UB4 UB5 UB6 UB7 UB8" + header[ + "UB_pos" + ] = "1.99593e-16 2.73682e-16 -1.54 -1.08894 1.08894 1.6083e-16 1.08894 1.08894 9.28619e-17" + header["sample_mne"] = "U0 U1 U2 U3 U4 U5" + header["sample_pos"] = "4.08 4.08 4.08 90 90 90" + data = numpy.array([[0, 0], [0, 0]], dtype=numpy.int8) + fabio_image = fabio.edfimage.EdfImage(data=data, header=header) + h5_image = fabioh5.File(fabio_image=fabio_image) + sample = h5_image["/scan_0/sample"] + self.assertIsNotNone(sample) + self.assertEqual(sample.attrs["NXclass"], "NXsample") + + d = sample["unit_cell_abc"] + expected = numpy.array([4.08, 4.08, 4.08]) + self.assertIsNotNone(d) + self.assertEqual(d.shape, (3,)) + self.assertIn(d.dtype.kind, ["d", "f"]) + numpy.testing.assert_array_almost_equal(d[...], expected) + + d = sample["unit_cell_alphabetagamma"] + expected = numpy.array([90.0, 90.0, 90.0]) + self.assertIsNotNone(d) + self.assertEqual(d.shape, (3,)) + self.assertIn(d.dtype.kind, ["d", "f"]) + numpy.testing.assert_array_almost_equal(d[...], expected) + + d = sample["ub_matrix"] + expected = numpy.array( + [ + [ + [1.99593e-16, 2.73682e-16, -1.54], + [-1.08894, 1.08894, 1.6083e-16], + [1.08894, 1.08894, 9.28619e-17], + ] + ] + ) + self.assertIsNotNone(d) + self.assertEqual(d.shape, (1, 3, 3)) + self.assertIn(d.dtype.kind, ["d", "f"]) + numpy.testing.assert_array_almost_equal(d[...], expected) + + def test_interpretation_mca_edf(self): + """EDF files with two or more headers starting with "MCA" + must have @interpretation = "spectrum" an the data.""" + header = { + "Title": "zapimage samy -4.975 -5.095 80 500 samz -4.091 -4.171 70 0", + "MCA a": -23.812, + "MCA b": 2.7107, + "MCA c": 8.1164e-06, + } + + data = numpy.array([[0, 0], [0, 0]], dtype=numpy.int8) + fabio_image = fabio.edfimage.EdfImage(data=data, header=header) + h5_image = fabioh5.File(fabio_image=fabio_image) + + data_dataset = h5_image["/scan_0/measurement/image_0/data"] + self.assertEqual(data_dataset.attrs["interpretation"], "spectrum") + + data_dataset = h5_image["/scan_0/instrument/detector_0/data"] + self.assertEqual(data_dataset.attrs["interpretation"], "spectrum") + + data_dataset = h5_image["/scan_0/measurement/image_0/info/data"] + self.assertEqual(data_dataset.attrs["interpretation"], "spectrum") + + def test_get_api(self): + result = self.h5_image.get("scan_0", getclass=True, getlink=True) + self.assertIs(result, h5py.HardLink) + result = self.h5_image.get("scan_0", getclass=False, getlink=True) + self.assertIsInstance(result, h5py.HardLink) + result = self.h5_image.get("scan_0", getclass=True, getlink=False) + self.assertIs(result, h5py.Group) + result = self.h5_image.get("scan_0", getclass=False, getlink=False) + self.assertIsInstance(result, commonh5.Group) + + def test_detector_link(self): + detector1 = self.h5_image["/scan_0/instrument/detector_0"] + detector2 = self.h5_image["/scan_0/measurement/image_0/info"] + self.assertIsNot(detector1, detector2) + self.assertEqual(list(detector1.items()), list(detector2.items())) + self.assertEqual( + self.h5_image.get(detector2.name, getlink=True).path, detector1.name + ) + + def test_detector_data_link(self): + data1 = self.h5_image["/scan_0/instrument/detector_0/data"] + data2 = self.h5_image["/scan_0/measurement/image_0/data"] + self.assertIsNot(data1, data2) + self.assertIs(data1._get_data(), data2._get_data()) + self.assertEqual(self.h5_image.get(data2.name, getlink=True).path, data1.name) + + def test_dirty_header(self): + """Test that it does not fail""" + try: + header = {} + header["foo"] = b"abc" + data = numpy.array([[0, 0], [0, 0]], dtype=numpy.int8) + fabio_image = fabio.edfimage.edfimage(data=data, header=header) + header = {} + header["foo"] = b"a\x90bc\xFE" + fabio_image.append_frame(data=data, header=header) + except Exception as e: + _logger.error(e.args[0]) + _logger.debug("Backtrace", exc_info=True) + self.skipTest("fabio do not allow to create the resource") + + h5_image = fabioh5.File(fabio_image=fabio_image) + scan_header_path = "/scan_0/instrument/file/scan_header" + self.assertIn(scan_header_path, h5_image) + data = h5_image[scan_header_path] + self.assertIsInstance(data[...], numpy.ndarray) + + def test_unicode_header(self): + """Test that it does not fail""" + try: + header = {} + header["foo"] = b"abc" + data = numpy.array([[0, 0], [0, 0]], dtype=numpy.int8) + fabio_image = fabio.edfimage.edfimage(data=data, header=header) + header = {} + header["foo"] = "abc\u2764" + fabio_image.append_frame(data=data, header=header) + except Exception as e: + _logger.error(e.args[0]) + _logger.debug("Backtrace", exc_info=True) + self.skipTest("fabio do not allow to create the resource") + + h5_image = fabioh5.File(fabio_image=fabio_image) + scan_header_path = "/scan_0/instrument/file/scan_header" + self.assertIn(scan_header_path, h5_image) + data = h5_image[scan_header_path] + self.assertIsInstance(data[...], numpy.ndarray) + + +class TestFabioH5MultiFrames(unittest.TestCase): + @classmethod + def setUpClass(cls): + names = ["A", "B", "C", "D"] + values = [["32000", "-10", "5.0", "1"], ["-32000", "-10", "5.0", "1"]] + + fabio_file = None + + for i in range(10): + header = { + "image_id": "%d" % i, + "integer": "-100", + "float": "1.0", + "string": "hi!", + "list_integer": "100 50 0", + "list_float": "1.0 2.0 3.5", + "string_looks_like_list": "2000 hi!", + "motor_mne": " ".join(names), + "motor_pos": " ".join(values[i % len(values)]), + "counter_mne": " ".join(names), + "counter_pos": " ".join(values[i % len(values)]), + } + for iname, name in enumerate(names): + header[name] = values[i % len(values)][iname] + + data = numpy.array([[i, 11], [12, 13], [14, 15]], dtype=numpy.int64) + if fabio_file is None: + fabio_file = fabio.edfimage.EdfImage(data=data, header=header) + else: + fabio_file.append_frame(data=data, header=header) + + cls.fabio_file = fabio_file + cls.fabioh5 = fabioh5.File(fabio_image=fabio_file) + + def test_others(self): + others = self.fabioh5["/scan_0/instrument/detector_0/others"] + dataset = others["A"] + self.assertGreaterEqual(dataset.dtype.itemsize, 1) + self.assertEqual(dataset.dtype.kind, "i") + dataset = others["B"] + self.assertGreaterEqual(dataset.dtype.itemsize, 1) + self.assertEqual(dataset.dtype.kind, "i") + dataset = others["C"] + self.assertGreaterEqual(dataset.dtype.itemsize, 1) + self.assertEqual(dataset.dtype.kind, "f") + dataset = others["D"] + self.assertGreaterEqual(dataset.dtype.itemsize, 1) + self.assertEqual(dataset.dtype.kind, "u") + + def test_positioners(self): + counters = self.fabioh5["/scan_0/instrument/positioners"] + # At least 32 bits, no unsigned values + dataset = counters["A"] + self.assertGreaterEqual(dataset.dtype.itemsize, 4) + self.assertEqual(dataset.dtype.kind, "i") + dataset = counters["B"] + self.assertGreaterEqual(dataset.dtype.itemsize, 4) + self.assertEqual(dataset.dtype.kind, "i") + dataset = counters["C"] + self.assertGreaterEqual(dataset.dtype.itemsize, 4) + self.assertEqual(dataset.dtype.kind, "f") + dataset = counters["D"] + self.assertGreaterEqual(dataset.dtype.itemsize, 4) + self.assertEqual(dataset.dtype.kind, "i") + + def test_counters(self): + counters = self.fabioh5["/scan_0/measurement"] + # At least 32 bits, no unsigned values + dataset = counters["A"] + self.assertGreaterEqual(dataset.dtype.itemsize, 4) + self.assertEqual(dataset.dtype.kind, "i") + dataset = counters["B"] + self.assertGreaterEqual(dataset.dtype.itemsize, 4) + self.assertEqual(dataset.dtype.kind, "i") + dataset = counters["C"] + self.assertGreaterEqual(dataset.dtype.itemsize, 4) + self.assertEqual(dataset.dtype.kind, "f") + dataset = counters["D"] + self.assertGreaterEqual(dataset.dtype.itemsize, 4) + self.assertEqual(dataset.dtype.kind, "i") + + +class TestFabioH5WithEdf(unittest.TestCase): + @classmethod + def setUpClass(cls): + cls.tmp_directory = tempfile.mkdtemp() + + cls.edf_filename = os.path.join(cls.tmp_directory, "test.edf") + + header = { + "integer": "-100", + "float": "1.0", + "string": "hi!", + "list_integer": "100 50 0", + "list_float": "1.0 2.0 3.5", + "string_looks_like_list": "2000 hi!", + } + data = numpy.array([[10, 11], [12, 13], [14, 15]], dtype=numpy.int64) + fabio_image = fabio.edfimage.edfimage(data, header) + fabio_image.write(cls.edf_filename) + + cls.fabio_image = fabio.open(cls.edf_filename) + cls.h5_image = fabioh5.File(fabio_image=cls.fabio_image) + + @classmethod + def tearDownClass(cls): + cls.fabio_image = None + cls.h5_image = None + shutil.rmtree(cls.tmp_directory) + + def test_reserved_format_metadata(self): + if fabio.hexversion < 327920: # 0.5.0 final + self.skipTest("fabio >= 0.5.0 final is needed") + + # The EDF contains reserved keys in the header + self.assertIn("HeaderID", self.fabio_image.header) + # We do not expose them in FabioH5 + self.assertNotIn("/scan_0/instrument/detector_0/others/HeaderID", self.h5_image) + + +class _TestableFrameData(fabioh5.FrameData): + """Allow to test if the full data is reached.""" + + def _create_data(self): + raise RuntimeError("Not supposed to be called") + + +class TestFabioH5WithFileSeries(unittest.TestCase): + @classmethod + def setUpClass(cls): + cls.tmp_directory = tempfile.mkdtemp() + + cls.edf_filenames = [] + + for i in range(10): + filename = os.path.join(cls.tmp_directory, "test_%04d.edf" % i) + cls.edf_filenames.append(filename) + + header = { + "image_id": "%d" % i, + "integer": "-100", + "float": "1.0", + "string": "hi!", + "list_integer": "100 50 0", + "list_float": "1.0 2.0 3.5", + "string_looks_like_list": "2000 hi!", + } + data = numpy.array([[i, 11], [12, 13], [14, 15]], dtype=numpy.int64) + fabio_image = fabio.edfimage.edfimage(data, header) + fabio_image.write(filename) + + @classmethod + def tearDownClass(cls): + shutil.rmtree(cls.tmp_directory) + + def _testH5Image(self, h5_image): + # test data + dataset = h5_image["/scan_0/instrument/detector_0/data"] + self.assertEqual(dataset.h5py_class, h5py.Dataset) + self.assertTrue(isinstance(dataset[()], numpy.ndarray)) + self.assertEqual(dataset.dtype.kind, "i") + self.assertEqual(dataset.shape, (10, 3, 2)) + self.assertEqual(list(dataset[:, 0, 0]), list(range(10))) + self.assertEqual(dataset.attrs["interpretation"], "image") + # test metatdata + dataset = h5_image["/scan_0/instrument/detector_0/others/image_id"] + self.assertEqual(list(dataset[...]), list(range(10))) + + def testFileList(self): + h5_image = fabioh5.File(file_series=self.edf_filenames) + self._testH5Image(h5_image) + + def testFileSeries(self): + file_series = fabio.file_series.file_series(self.edf_filenames) + h5_image = fabioh5.File(file_series=file_series) + self._testH5Image(h5_image) + + def testFrameDataCache(self): + file_series = fabio.file_series.file_series(self.edf_filenames) + reader = fabioh5.FabioReader(file_series=file_series) + frameData = _TestableFrameData("foo", reader) + self.assertEqual(frameData.dtype.kind, "i") + self.assertEqual(frameData.shape, (10, 3, 2)) |