#!/usr/bin/env python
# -*- coding: utf-8 -*-
# Copyright (c) 2018-2020 Satpy developers
#
# This file is part of satpy.
#
# satpy is free software: you can redistribute it and/or modify it under the
# terms of the GNU General Public License as published by the Free Software
# Foundation, either version 3 of the License, or (at your option) any later
# version.
#
# satpy is distributed in the hope that it will be useful, but WITHOUT ANY
# WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR
# A PARTICULAR PURPOSE. See the GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License along with
# satpy. If not, see <http://www.gnu.org/licenses/>.
"""Tests for the mitiff writer.
Based on the test for geotiff writer
"""
import datetime as dt
import logging
import os
import unittest
import numpy as np
from PIL import Image
logger = logging.getLogger()
[docs]
class TestMITIFFWriter(unittest.TestCase):
"""Test the MITIFF Writer class."""
[docs]
def setUp(self):
"""Create temporary directory to save files to."""
import tempfile
self.base_dir = tempfile.mkdtemp()
[docs]
def tearDown(self):
"""Remove the temporary directory created for a test."""
try:
import shutil
shutil.rmtree(self.base_dir, ignore_errors=True)
except OSError:
pass
[docs]
def _get_test_datasets(self):
"""Create a datasets list."""
import dask.array as da
import xarray as xr
from pyproj import CRS
from pyresample.geometry import AreaDefinition
area_def = AreaDefinition(
"test",
"test",
"test",
CRS("+proj=stere +datum=WGS84 +ellps=WGS84 +lon_0=0. +lat_0=90 +lat_ts=60 +units=km"),
100,
200,
(-1000., -1500., 1000., 1500.),
)
ds1 = xr.DataArray(
da.zeros((100, 200), chunks=50),
dims=("y", "x"),
attrs={"name": "1",
"start_time": dt.datetime.utcnow(),
"platform_name": "TEST_PLATFORM_NAME",
"sensor": "TEST_SENSOR_NAME",
"area": area_def,
"prerequisites": ["1"],
"calibration": "reflectance",
"metadata_requirements": {
"order": ["1"],
"config": {
"1": {"alias": "1-VIS0.63",
"calibration": "reflectance",
"min-val": "0",
"max-val": "100"},
},
"translate": {"1": "1",
},
"file_pattern": "1_{start_time:%Y%m%d_%H%M%S}.mitiff"
}}
)
ds2 = xr.DataArray(
da.zeros((100, 200), chunks=50),
dims=("y", "x"),
attrs={"name": "4",
"start_time": dt.datetime.utcnow(),
"platform_name": "TEST_PLATFORM_NAME",
"sensor": "TEST_SENSOR_NAME",
"area": area_def,
"prerequisites": ["4"],
"calibration": "brightness_temperature",
"metadata_requirements": {
"order": ["4"],
"config": {
"4": {"alias": "4-IR10.8",
"calibration": "brightness_temperature",
"min-val": "-150",
"max-val": "50"},
},
"translate": {"4": "4",
},
"file_pattern": "4_{start_time:%Y%m%d_%H%M%S}.mitiff"}
}
)
return [ds1, ds2]
[docs]
def _get_test_datasets_sensor_set(self):
"""Create a datasets list."""
import dask.array as da
import xarray as xr
from pyproj import CRS
from pyresample.geometry import AreaDefinition
area_def = AreaDefinition(
"test",
"test",
"test",
CRS("+proj=stere +datum=WGS84 +ellps=WGS84 +lon_0=0. +lat_0=90 +lat_ts=60 +units=km"),
100,
200,
(-1000., -1500., 1000., 1500.),
)
ds1 = xr.DataArray(
da.zeros((100, 200), chunks=50),
dims=("y", "x"),
attrs={"name": "1",
"start_time": dt.datetime.utcnow(),
"platform_name": "TEST_PLATFORM_NAME",
"sensor": {"TEST_SENSOR_NAME"},
"area": area_def,
"prerequisites": ["1"],
"calibration": "reflectance",
"metadata_requirements": {
"order": ["1"],
"config": {
"1": {"alias": "1-VIS0.63",
"calibration": "reflectance",
"min-val": "0",
"max-val": "100"},
},
"translate": {"1": "1",
},
"file_pattern": "1_{start_time:%Y%m%d_%H%M%S}.mitiff"
}}
)
ds2 = xr.DataArray(
da.zeros((100, 200), chunks=50),
dims=("y", "x"),
attrs={"name": "4",
"start_time": dt.datetime.utcnow(),
"platform_name": "TEST_PLATFORM_NAME",
"sensor": {"TEST_SENSOR_NAME"},
"area": area_def,
"prerequisites": ["4"],
"calibration": "brightness_temperature",
"metadata_requirements": {
"order": ["4"],
"config": {
"4": {"alias": "4-IR10.8",
"calibration": "brightness_temperature",
"min-val": "-150",
"max-val": "50"},
},
"translate": {"4": "4",
},
"file_pattern": "4_{start_time:%Y%m%d_%H%M%S}.mitiff"}
}
)
return [ds1, ds2]
[docs]
def _get_test_dataset(self, bands=3):
"""Create a single test dataset."""
import dask.array as da
import xarray as xr
from pyproj import CRS
from pyresample.geometry import AreaDefinition
area_def = AreaDefinition(
"test",
"test",
"test",
CRS("+proj=stere +datum=WGS84 +ellps=WGS84 +lon_0=0. +lat_0=90 +lat_ts=60 +units=km"),
100,
200,
(-1000., -1500., 1000., 1500.),
)
ds1 = xr.DataArray(
da.zeros((bands, 100, 200), chunks=50),
dims=("bands", "y", "x"),
attrs={"name": "test",
"start_time": dt.datetime.utcnow(),
"platform_name": "TEST_PLATFORM_NAME",
"sensor": "TEST_SENSOR_NAME",
"area": area_def,
"prerequisites": ["1", "2", "3"]}
)
return ds1
[docs]
def _get_test_one_dataset(self):
"""Create a single test dataset."""
import dask.array as da
import xarray as xr
from pyproj import CRS
from pyresample.geometry import AreaDefinition
area_def = AreaDefinition(
"test",
"test",
"test",
CRS("+proj=geos +datum=WGS84 +ellps=WGS84 +lon_0=0. h=36000. +units=km"),
100,
200,
(-1000., -1500., 1000., 1500.),
)
ds1 = xr.DataArray(
da.zeros((100, 200), chunks=50),
dims=("y", "x"),
attrs={"name": "test",
"start_time": dt.datetime.utcnow(),
"platform_name": "TEST_PLATFORM_NAME",
"sensor": "avhrr",
"area": area_def,
"prerequisites": [10.8]}
)
return ds1
[docs]
def _get_test_one_dataset_sensor_set(self):
"""Create a single test dataset."""
import dask.array as da
import xarray as xr
from pyproj import CRS
from pyresample.geometry import AreaDefinition
area_def = AreaDefinition(
"test",
"test",
"test",
CRS("+proj=geos +datum=WGS84 +ellps=WGS84 +lon_0=0. h=36000. +units=km"),
100,
200,
(-1000., -1500., 1000., 1500.),
)
ds1 = xr.DataArray(
da.zeros((100, 200), chunks=50),
dims=("y", "x"),
attrs={"name": "test",
"start_time": dt.datetime.utcnow(),
"platform_name": "TEST_PLATFORM_NAME",
"sensor": {"avhrr"},
"area": area_def,
"prerequisites": [10.8]}
)
return ds1
[docs]
def _get_test_dataset_with_bad_values(self, bands=3):
"""Create a single test dataset."""
import xarray as xr
from pyproj import CRS
from pyresample.geometry import AreaDefinition
area_def = AreaDefinition(
"test",
"test",
"test",
CRS("+proj=stere +datum=WGS84 +ellps=WGS84 +lon_0=0. +lat_0=90 +lat_ts=60 +units=km"),
100,
200,
(-1000., -1500., 1000., 1500.),
)
data = np.arange(-210, 790, 100).reshape((2, 5)) * 0.95
data /= 5.605
data[0, 0] = np.nan # need a nan value
data[0, 1] = 0. # Need a 0 value
rgb_data = np.stack([data, data, data])
ds1 = xr.DataArray(rgb_data,
dims=("bands", "y", "x"),
attrs={"name": "test",
"start_time": dt.datetime.utcnow(),
"platform_name": "TEST_PLATFORM_NAME",
"sensor": "TEST_SENSOR_NAME",
"area": area_def,
"prerequisites": ["1", "2", "3"]})
return ds1
[docs]
def _get_test_dataset_calibration(self, bands=6):
"""Create a single test dataset."""
import dask.array as da
import xarray as xr
from pyproj import CRS
from pyresample.geometry import AreaDefinition
from satpy.scene import Scene
from satpy.tests.utils import make_dsq
area_def = AreaDefinition(
"test",
"test",
"test",
CRS("+proj=stere +datum=WGS84 +ellps=WGS84 +lon_0=0. +lat_0=90 +lat_ts=60 +units=km"),
100,
200,
(-1000., -1500., 1000., 1500.),
)
prereqs = [
make_dsq(name="1", calibration="reflectance"),
make_dsq(name="2", calibration="reflectance"),
make_dsq(name="3", calibration="brightness_temperature"),
make_dsq(name="4", calibration="brightness_temperature"),
make_dsq(name="5", calibration="brightness_temperature"),
make_dsq(name="6", calibration="reflectance")
]
scene = Scene()
scene["1"] = xr.DataArray(da.zeros((100, 200), chunks=50),
dims=("y", "x"),
attrs={"calibration": "reflectance"})
scene["2"] = xr.DataArray(da.zeros((100, 200), chunks=50),
dims=("y", "x"),
attrs={"calibration": "reflectance"})
scene["3"] = xr.DataArray(da.zeros((100, 200), chunks=50),
dims=("y", "x"),
attrs={"calibration": "brightness_temperature"})
scene["4"] = xr.DataArray(da.zeros((100, 200), chunks=50),
dims=("y", "x"),
attrs={"calibration": "brightness_temperature"})
scene["5"] = xr.DataArray(da.zeros((100, 200), chunks=50),
dims=("y", "x"),
attrs={"calibration": "brightness_temperature"})
scene["6"] = xr.DataArray(da.zeros((100, 200), chunks=50),
dims=("y", "x"),
attrs={"calibration": "reflectance"})
data = xr.concat(scene, "bands", coords="minimal")
bands = []
calibration = []
for p in scene:
calibration.append(p.attrs["calibration"])
bands.append(p.attrs["name"])
data["bands"] = list(bands)
new_attrs = {"name": "datasets",
"start_time": dt.datetime.utcnow(),
"platform_name": "TEST_PLATFORM_NAME",
"sensor": "test-sensor",
"area": area_def,
"prerequisites": prereqs,
"metadata_requirements": {
"order": ["1", "2", "3", "4", "5", "6"],
"config": {
"1": {"alias": "1-VIS0.63",
"calibration": "reflectance",
"min-val": "0",
"max-val": "100"},
"2": {"alias": "2-VIS0.86",
"calibration": "reflectance",
"min-val": "0",
"max-val": "100"},
"3": {"alias": "3(3B)-IR3.7",
"calibration": "brightness_temperature",
"min-val": "-150",
"max-val": "50"},
"4": {"alias": "4-IR10.8",
"calibration": "brightness_temperature",
"min-val": "-150",
"max-val": "50"},
"5": {"alias": "5-IR11.5",
"calibration": "brightness_temperature",
"min-val": "-150",
"max-val": "50"},
"6": {"alias": "6(3A)-VIS1.6",
"calibration": "reflectance",
"min-val": "0",
"max-val": "100"}
},
"translate": {"1": "1",
"2": "2",
"3": "3",
"4": "4",
"5": "5",
"6": "6"
},
"file_pattern": "test-dataset-{start_time:%Y%m%d%H%M%S}.mitiff"
}
}
ds1 = xr.DataArray(data=data.data, attrs=new_attrs,
dims=data.dims, coords=data.coords)
return ds1
[docs]
def _get_test_dataset_calibration_one_dataset(self, bands=1):
"""Create a single test dataset."""
import dask.array as da
import xarray as xr
from pyproj import CRS
from pyresample.geometry import AreaDefinition
from satpy.scene import Scene
from satpy.tests.utils import make_dsq
area_def = AreaDefinition(
"test",
"test",
"test",
CRS("+proj=stere +datum=WGS84 +ellps=WGS84 +lon_0=0. +lat_0=90 +lat_ts=60 +units=km"),
100,
200,
(-1000., -1500., 1000., 1500.),
)
prereqs = [make_dsq(name="4", calibration="brightness_temperature")]
scene = Scene()
scene["4"] = xr.DataArray(da.zeros((100, 200), chunks=50),
dims=("y", "x"),
attrs={"calibration": "brightness_temperature"})
data = scene["4"]
calibration = []
for p in scene:
calibration.append(p.attrs["calibration"])
new_attrs = {"name": "datasets",
"start_time": dt.datetime.utcnow(),
"platform_name": "TEST_PLATFORM_NAME",
"sensor": "test-sensor",
"area": area_def,
"prerequisites": prereqs,
"metadata_requirements": {
"order": ["4"],
"config": {
"4": {"alias": "BT",
"calibration": "brightness_temperature",
"min-val": "-150",
"max-val": "50"},
},
"translate": {"4": "4",
},
"file_pattern": "test-dataset-{start_time:%Y%m%d%H%M%S}.mitiff"
}
}
ds1 = xr.DataArray(data=data.data, attrs=new_attrs,
dims=data.dims, coords=data.coords)
return ds1
[docs]
def _get_test_dataset_three_bands_two_prereq(self, bands=3):
"""Create a single test dataset."""
import dask.array as da
import xarray as xr
from pyproj import CRS
from pyresample.geometry import AreaDefinition
from satpy.tests.utils import make_dsq
area_def = AreaDefinition(
"test",
"test",
"test",
CRS("+proj=stere +datum=WGS84 +ellps=WGS84 +lon_0=0. +lat_0=90 +lat_ts=60 +units=km"),
100,
200,
(-1000., -1500., 1000., 1500.),
)
ds1 = xr.DataArray(
da.zeros((bands, 100, 200), chunks=50),
coords=[["R", "G", "B"], list(range(100)), list(range(200))],
dims=("bands", "y", "x"),
attrs={"name": "test",
"start_time": dt.datetime.utcnow(),
"platform_name": "TEST_PLATFORM_NAME",
"sensor": "TEST_SENSOR_NAME",
"area": area_def,
"prerequisites": [make_dsq(name="1", calibration="reflectance"),
make_dsq(name="2", calibration="reflectance")]}
)
return ds1
[docs]
def _get_test_dataset_three_bands_prereq(self, bands=3):
"""Create a single test dataset."""
import dask.array as da
import xarray as xr
from pyproj import CRS
from pyresample.geometry import AreaDefinition
from satpy.tests.utils import make_dsq
area_def = AreaDefinition(
"test",
"test",
"test",
CRS("+proj=stere +datum=WGS84 +ellps=WGS84 +lon_0=0. +lat_0=90 +lat_ts=60 +units=km"),
100,
200,
(-1000., -1500., 1000., 1500.),
)
ds1 = xr.DataArray(
da.zeros((bands, 100, 200), chunks=50),
coords=[["R", "G", "B"], list(range(100)), list(range(200))],
dims=("bands", "y", "x"),
attrs={"name": "test",
"start_time": dt.datetime.utcnow(),
"platform_name": "TEST_PLATFORM_NAME",
"sensor": "TEST_SENSOR_NAME",
"area": area_def,
"prerequisites": [make_dsq(wavelength=0.6, modifiers=("sunz_corrected",)),
make_dsq(wavelength=0.8, modifiers=("sunz_corrected",)),
10.8]})
return ds1
[docs]
def _read_back_mitiff_and_check(self, filename, expected, test_shape=(100, 200)):
pillow_tif = Image.open(filename)
for frame_no in range(pillow_tif.n_frames):
pillow_tif.seek(frame_no)
np.testing.assert_allclose(np.asarray(pillow_tif.getdata()).reshape(test_shape),
expected[frame_no], atol=1.e-6, rtol=0)
[docs]
def _imagedescription_from_mitiff(self, filename):
pillow_tif = Image.open(filename)
IMAGEDESCRIPTION = 270
imgdesc = (pillow_tif.tag_v2.get(IMAGEDESCRIPTION)).split("\n")
return imgdesc
[docs]
def test_init(self):
"""Test creating the writer with no arguments."""
from satpy.writers.mitiff import MITIFFWriter
MITIFFWriter()
[docs]
def test_simple_write(self):
"""Test basic writer operation."""
from satpy.writers.mitiff import MITIFFWriter
dataset = self._get_test_dataset()
w = MITIFFWriter(base_dir=self.base_dir)
w.save_dataset(dataset)
[docs]
def test_save_datasets(self):
"""Test basic writer operation save_datasets."""
from satpy.writers.mitiff import MITIFFWriter
expected = [np.full((100, 200), 0)]
dataset = self._get_test_datasets()
w = MITIFFWriter(base_dir=self.base_dir)
w.save_datasets(dataset)
filename = (dataset[0].attrs["metadata_requirements"]["file_pattern"]).format(
start_time=dataset[0].attrs["start_time"])
self._read_back_mitiff_and_check(os.path.join(self.base_dir, filename), expected)
[docs]
def test_save_datasets_sensor_set(self):
"""Test basic writer operation save_datasets."""
from satpy.writers.mitiff import MITIFFWriter
expected = [np.full((100, 200), 0)]
dataset = self._get_test_datasets_sensor_set()
w = MITIFFWriter(base_dir=self.base_dir)
w.save_datasets(dataset)
filename = (dataset[0].attrs["metadata_requirements"]["file_pattern"]).format(
start_time=dataset[0].attrs["start_time"])
self._read_back_mitiff_and_check(os.path.join(self.base_dir, filename), expected)
[docs]
def test_save_one_dataset(self):
"""Test basic writer operation with one dataset ie. no bands."""
from satpy.writers.mitiff import MITIFFWriter
dataset = self._get_test_one_dataset()
w = MITIFFWriter(base_dir=self.base_dir)
w.save_dataset(dataset)
imgdesc = self._imagedescription_from_mitiff(os.path.join(self.base_dir, os.listdir(self.base_dir)[0]))
for key in imgdesc:
if "In this file" in key:
assert key == " Channels: 1 In this file: 1"
[docs]
def test_save_one_dataset_sensor_set(self):
"""Test basic writer operation with one dataset ie. no bands."""
from satpy.writers.mitiff import MITIFFWriter
dataset = self._get_test_one_dataset_sensor_set()
w = MITIFFWriter(base_dir=self.base_dir)
w.save_dataset(dataset)
imgdesc = self._imagedescription_from_mitiff(os.path.join(self.base_dir, os.listdir(self.base_dir)[0]))
for key in imgdesc:
if "In this file" in key:
assert key == " Channels: 1 In this file: 1"
[docs]
def test_save_dataset_with_calibration(self):
"""Test writer operation with calibration."""
from satpy.writers.mitiff import MITIFFWriter
expected_ir = np.full((100, 200), 255)
expected_vis = np.full((100, 200), 0)
expected = np.stack([expected_vis, expected_vis, expected_ir, expected_ir, expected_ir, expected_vis])
expected_key_channel = ["Table_calibration: 1-VIS0.63, Reflectance(Albedo), [%], 8, [ 0.00 0.39 0.78 1.18 1.57 "
"1.96 2.35 2.75 3.14 3.53 3.92 4.31 4.71 5.10 5.49 5.88 6.27 6.67 7.06 7.45 7.84 8.24 "
"8.63 9.02 9.41 9.80 10.20 10.59 10.98 11.37 11.76 12.16 12.55 12.94 13.33 13.73 14.12 "
"14.51 14.90 15.29 15.69 16.08 16.47 16.86 17.25 17.65 18.04 18.43 18.82 19.22 19.61 "
"20.00 20.39 20.78 21.18 21.57 21.96 22.35 22.75 23.14 23.53 23.92 24.31 24.71 25.10 "
"25.49 25.88 26.27 26.67 27.06 27.45 27.84 28.24 28.63 29.02 29.41 29.80 30.20 30.59 "
"30.98 31.37 31.76 32.16 32.55 32.94 33.33 33.73 34.12 34.51 34.90 35.29 35.69 36.08 "
"36.47 36.86 37.25 37.65 38.04 38.43 38.82 39.22 39.61 40.00 40.39 40.78 41.18 41.57 "
"41.96 42.35 42.75 43.14 43.53 43.92 44.31 44.71 45.10 45.49 45.88 46.27 46.67 47.06 "
"47.45 47.84 48.24 48.63 49.02 49.41 49.80 50.20 50.59 50.98 51.37 51.76 52.16 52.55 "
"52.94 53.33 53.73 54.12 54.51 54.90 55.29 55.69 56.08 56.47 56.86 57.25 57.65 58.04 "
"58.43 58.82 59.22 59.61 60.00 60.39 60.78 61.18 61.57 61.96 62.35 62.75 63.14 63.53 "
"63.92 64.31 64.71 65.10 65.49 65.88 66.27 66.67 67.06 67.45 67.84 68.24 68.63 69.02 "
"69.41 69.80 70.20 70.59 70.98 71.37 71.76 72.16 72.55 72.94 73.33 73.73 74.12 74.51 "
"74.90 75.29 75.69 76.08 76.47 76.86 77.25 77.65 78.04 78.43 78.82 79.22 79.61 80.00 "
"80.39 80.78 81.18 81.57 81.96 82.35 82.75 83.14 83.53 83.92 84.31 84.71 85.10 85.49 "
"85.88 86.27 86.67 87.06 87.45 87.84 88.24 88.63 89.02 89.41 89.80 90.20 90.59 90.98 "
"91.37 91.76 92.16 92.55 92.94 93.33 93.73 94.12 94.51 94.90 95.29 95.69 96.08 96.47 "
"96.86 97.25 97.65 98.04 98.43 98.82 99.22 99.61 100.00 ]",
"Table_calibration: 2-VIS0.86, Reflectance(Albedo), [%], 8, [ 0.00 0.39 0.78 1.18 1.57 "
"1.96 2.35 2.75 3.14 3.53 3.92 4.31 4.71 5.10 5.49 5.88 6.27 6.67 7.06 7.45 7.84 8.24 "
"8.63 9.02 9.41 9.80 10.20 10.59 10.98 11.37 11.76 12.16 12.55 12.94 13.33 13.73 14.12 "
"14.51 14.90 15.29 15.69 16.08 16.47 16.86 17.25 17.65 18.04 18.43 18.82 19.22 19.61 "
"20.00 20.39 20.78 21.18 21.57 21.96 22.35 22.75 23.14 23.53 23.92 24.31 24.71 25.10 "
"25.49 25.88 26.27 26.67 27.06 27.45 27.84 28.24 28.63 29.02 29.41 29.80 30.20 30.59 "
"30.98 31.37 31.76 32.16 32.55 32.94 33.33 33.73 34.12 34.51 34.90 35.29 35.69 36.08 "
"36.47 36.86 37.25 37.65 38.04 38.43 38.82 39.22 39.61 40.00 40.39 40.78 41.18 41.57 "
"41.96 42.35 42.75 43.14 43.53 43.92 44.31 44.71 45.10 45.49 45.88 46.27 46.67 47.06 "
"47.45 47.84 48.24 48.63 49.02 49.41 49.80 50.20 50.59 50.98 51.37 51.76 52.16 52.55 "
"52.94 53.33 53.73 54.12 54.51 54.90 55.29 55.69 56.08 56.47 56.86 57.25 57.65 58.04 "
"58.43 58.82 59.22 59.61 60.00 60.39 60.78 61.18 61.57 61.96 62.35 62.75 63.14 63.53 "
"63.92 64.31 64.71 65.10 65.49 65.88 66.27 66.67 67.06 67.45 67.84 68.24 68.63 69.02 "
"69.41 69.80 70.20 70.59 70.98 71.37 71.76 72.16 72.55 72.94 73.33 73.73 74.12 74.51 "
"74.90 75.29 75.69 76.08 76.47 76.86 77.25 77.65 78.04 78.43 78.82 79.22 79.61 80.00 "
"80.39 80.78 81.18 81.57 81.96 82.35 82.75 83.14 83.53 83.92 84.31 84.71 85.10 85.49 "
"85.88 86.27 86.67 87.06 87.45 87.84 88.24 88.63 89.02 89.41 89.80 90.20 90.59 90.98 "
"91.37 91.76 92.16 92.55 92.94 93.33 93.73 94.12 94.51 94.90 95.29 95.69 96.08 96.47 "
"96.86 97.25 97.65 98.04 98.43 98.82 99.22 99.61 100.00 ]",
u"Table_calibration: 3(3B)-IR3.7, BT, °[C], 8, [ 50.00 49.22 48.43 47.65 46.86 46.08 "
"45.29 44.51 43.73 42.94 42.16 41.37 40.59 39.80 39.02 38.24 37.45 36.67 35.88 35.10 "
"34.31 33.53 32.75 31.96 31.18 30.39 29.61 28.82 28.04 27.25 26.47 25.69 24.90 24.12 "
"23.33 22.55 21.76 20.98 20.20 19.41 18.63 17.84 17.06 16.27 15.49 14.71 13.92 13.14 "
"12.35 11.57 10.78 10.00 9.22 8.43 7.65 6.86 6.08 5.29 4.51 3.73 2.94 2.16 1.37 0.59 "
"-0.20 -0.98 -1.76 -2.55 -3.33 -4.12 -4.90 -5.69 -6.47 -7.25 -8.04 -8.82 -9.61 -10.39 "
"-11.18 -11.96 -12.75 -13.53 -14.31 -15.10 -15.88 -16.67 -17.45 -18.24 -19.02 -19.80 "
"-20.59 -21.37 -22.16 -22.94 -23.73 -24.51 -25.29 -26.08 -26.86 -27.65 -28.43 -29.22 "
"-30.00 -30.78 -31.57 -32.35 -33.14 -33.92 -34.71 -35.49 -36.27 -37.06 -37.84 -38.63 "
"-39.41 -40.20 -40.98 -41.76 -42.55 -43.33 -44.12 -44.90 -45.69 -46.47 -47.25 -48.04 "
"-48.82 -49.61 -50.39 -51.18 -51.96 -52.75 -53.53 -54.31 -55.10 -55.88 -56.67 -57.45 "
"-58.24 -59.02 -59.80 -60.59 -61.37 -62.16 -62.94 -63.73 -64.51 -65.29 -66.08 -66.86 "
"-67.65 -68.43 -69.22 -70.00 -70.78 -71.57 -72.35 -73.14 -73.92 -74.71 -75.49 -76.27 "
"-77.06 -77.84 -78.63 -79.41 -80.20 -80.98 -81.76 -82.55 -83.33 -84.12 -84.90 -85.69 "
"-86.47 -87.25 -88.04 -88.82 -89.61 -90.39 -91.18 -91.96 -92.75 -93.53 -94.31 -95.10 "
"-95.88 -96.67 -97.45 -98.24 -99.02 -99.80 -100.59 -101.37 -102.16 -102.94 -103.73 "
"-104.51 -105.29 -106.08 -106.86 -107.65 -108.43 -109.22 -110.00 -110.78 -111.57 "
"-112.35 -113.14 -113.92 -114.71 -115.49 -116.27 -117.06 -117.84 -118.63 -119.41 "
"-120.20 -120.98 -121.76 -122.55 -123.33 -124.12 -124.90 -125.69 -126.47 -127.25 "
"-128.04 -128.82 -129.61 -130.39 -131.18 -131.96 -132.75 -133.53 -134.31 -135.10 "
"-135.88 -136.67 -137.45 -138.24 -139.02 -139.80 -140.59 -141.37 -142.16 -142.94 "
"-143.73 -144.51 -145.29 -146.08 -146.86 -147.65 -148.43 -149.22 -150.00 ]",
u"Table_calibration: 4-IR10.8, BT, °[C], 8, [ 50.00 49.22 48.43 47.65 46.86 46.08 "
"45.29 "
"44.51 43.73 42.94 42.16 41.37 40.59 39.80 39.02 38.24 37.45 36.67 35.88 35.10 34.31 "
"33.53 32.75 31.96 31.18 30.39 29.61 28.82 28.04 27.25 26.47 25.69 24.90 24.12 23.33 "
"22.55 21.76 20.98 20.20 19.41 18.63 17.84 17.06 16.27 15.49 14.71 13.92 13.14 12.35 "
"11.57 10.78 10.00 9.22 8.43 7.65 6.86 6.08 5.29 4.51 3.73 2.94 2.16 1.37 0.59 -0.20 "
"-0.98 -1.76 -2.55 -3.33 -4.12 -4.90 -5.69 -6.47 -7.25 -8.04 -8.82 -9.61 -10.39 -11.18 "
"-11.96 -12.75 -13.53 -14.31 -15.10 -15.88 -16.67 -17.45 -18.24 -19.02 -19.80 -20.59 "
"-21.37 -22.16 -22.94 -23.73 -24.51 -25.29 -26.08 -26.86 -27.65 -28.43 -29.22 -30.00 "
"-30.78 -31.57 -32.35 -33.14 -33.92 -34.71 -35.49 -36.27 -37.06 -37.84 -38.63 -39.41 "
"-40.20 -40.98 -41.76 -42.55 -43.33 -44.12 -44.90 -45.69 -46.47 -47.25 -48.04 -48.82 "
"-49.61 -50.39 -51.18 -51.96 -52.75 -53.53 -54.31 -55.10 -55.88 -56.67 -57.45 -58.24 "
"-59.02 -59.80 -60.59 -61.37 -62.16 -62.94 -63.73 -64.51 -65.29 -66.08 -66.86 -67.65 "
"-68.43 -69.22 -70.00 -70.78 -71.57 -72.35 -73.14 -73.92 -74.71 -75.49 -76.27 -77.06 "
"-77.84 -78.63 -79.41 -80.20 -80.98 -81.76 -82.55 -83.33 -84.12 -84.90 -85.69 -86.47 "
"-87.25 -88.04 -88.82 -89.61 -90.39 -91.18 -91.96 -92.75 -93.53 -94.31 -95.10 -95.88 "
"-96.67 -97.45 -98.24 -99.02 -99.80 -100.59 -101.37 -102.16 -102.94 -103.73 -104.51 "
"-105.29 -106.08 -106.86 -107.65 -108.43 -109.22 -110.00 -110.78 -111.57 -112.35 "
"-113.14 -113.92 -114.71 -115.49 -116.27 -117.06 -117.84 -118.63 -119.41 -120.20 "
"-120.98 -121.76 -122.55 -123.33 -124.12 -124.90 -125.69 -126.47 -127.25 -128.04 "
"-128.82 -129.61 -130.39 -131.18 -131.96 -132.75 -133.53 -134.31 -135.10 -135.88 "
"-136.67 -137.45 -138.24 -139.02 -139.80 -140.59 -141.37 -142.16 -142.94 -143.73 "
"-144.51 -145.29 -146.08 -146.86 -147.65 -148.43 -149.22 -150.00 ]",
u"Table_calibration: 5-IR11.5, BT, °[C], 8, [ 50.00 49.22 48.43 47.65 46.86 46.08 "
"45.29 "
"44.51 43.73 42.94 42.16 41.37 40.59 39.80 39.02 38.24 37.45 36.67 35.88 35.10 34.31 "
"33.53 32.75 31.96 31.18 30.39 29.61 28.82 28.04 27.25 26.47 25.69 24.90 24.12 23.33 "
"22.55 21.76 20.98 20.20 19.41 18.63 17.84 17.06 16.27 15.49 14.71 13.92 13.14 12.35 "
"11.57 10.78 10.00 9.22 8.43 7.65 6.86 6.08 5.29 4.51 3.73 2.94 2.16 1.37 0.59 -0.20 "
"-0.98 -1.76 -2.55 -3.33 -4.12 -4.90 -5.69 -6.47 -7.25 -8.04 -8.82 -9.61 -10.39 -11.18 "
"-11.96 -12.75 -13.53 -14.31 -15.10 -15.88 -16.67 -17.45 -18.24 -19.02 -19.80 -20.59 "
"-21.37 -22.16 -22.94 -23.73 -24.51 -25.29 -26.08 -26.86 -27.65 -28.43 -29.22 -30.00 "
"-30.78 -31.57 -32.35 -33.14 -33.92 -34.71 -35.49 -36.27 -37.06 -37.84 -38.63 -39.41 "
"-40.20 -40.98 -41.76 -42.55 -43.33 -44.12 -44.90 -45.69 -46.47 -47.25 -48.04 -48.82 "
"-49.61 -50.39 -51.18 -51.96 -52.75 -53.53 -54.31 -55.10 -55.88 -56.67 -57.45 -58.24 "
"-59.02 -59.80 -60.59 -61.37 -62.16 -62.94 -63.73 -64.51 -65.29 -66.08 -66.86 -67.65 "
"-68.43 -69.22 -70.00 -70.78 -71.57 -72.35 -73.14 -73.92 -74.71 -75.49 -76.27 -77.06 "
"-77.84 -78.63 -79.41 -80.20 -80.98 -81.76 -82.55 -83.33 -84.12 -84.90 -85.69 -86.47 "
"-87.25 -88.04 -88.82 -89.61 -90.39 -91.18 -91.96 -92.75 -93.53 -94.31 -95.10 -95.88 "
"-96.67 -97.45 -98.24 -99.02 -99.80 -100.59 -101.37 -102.16 -102.94 -103.73 -104.51 "
"-105.29 -106.08 -106.86 -107.65 -108.43 -109.22 -110.00 -110.78 -111.57 -112.35 "
"-113.14 -113.92 -114.71 -115.49 -116.27 -117.06 -117.84 -118.63 -119.41 -120.20 "
"-120.98 -121.76 -122.55 -123.33 -124.12 -124.90 -125.69 -126.47 -127.25 -128.04 "
"-128.82 -129.61 -130.39 -131.18 -131.96 -132.75 -133.53 -134.31 -135.10 -135.88 "
"-136.67 -137.45 -138.24 -139.02 -139.80 -140.59 -141.37 -142.16 -142.94 -143.73 "
"-144.51 -145.29 -146.08 -146.86 -147.65 -148.43 -149.22 -150.00 ]",
"Table_calibration: 6(3A)-VIS1.6, Reflectance(Albedo), [%], 8, [ 0.00 0.39 0.78 1.18 "
"1.57 1.96 2.35 2.75 3.14 3.53 3.92 4.31 4.71 5.10 5.49 5.88 6.27 6.67 7.06 7.45 7.84 "
"8.24 8.63 9.02 9.41 9.80 10.20 10.59 10.98 11.37 11.76 12.16 12.55 12.94 13.33 13.73 "
"14.12 14.51 14.90 15.29 15.69 16.08 16.47 16.86 17.25 17.65 18.04 18.43 18.82 19.22 "
"19.61 20.00 20.39 20.78 21.18 21.57 21.96 22.35 22.75 23.14 23.53 23.92 24.31 24.71 "
"25.10 25.49 25.88 26.27 26.67 27.06 27.45 27.84 28.24 28.63 29.02 29.41 29.80 30.20 "
"30.59 30.98 31.37 31.76 32.16 32.55 32.94 33.33 33.73 34.12 34.51 34.90 35.29 35.69 "
"36.08 36.47 36.86 37.25 37.65 38.04 38.43 38.82 39.22 39.61 40.00 40.39 40.78 41.18 "
"41.57 41.96 42.35 42.75 43.14 43.53 43.92 44.31 44.71 45.10 45.49 45.88 46.27 46.67 "
"47.06 47.45 47.84 48.24 48.63 49.02 49.41 49.80 50.20 50.59 50.98 51.37 51.76 52.16 "
"52.55 52.94 53.33 53.73 54.12 54.51 54.90 55.29 55.69 56.08 56.47 56.86 57.25 57.65 "
"58.04 58.43 58.82 59.22 59.61 60.00 60.39 60.78 61.18 61.57 61.96 62.35 62.75 63.14 "
"63.53 63.92 64.31 64.71 65.10 65.49 65.88 66.27 66.67 67.06 67.45 67.84 68.24 68.63 "
"69.02 69.41 69.80 70.20 70.59 70.98 71.37 71.76 72.16 72.55 72.94 73.33 73.73 74.12 "
"74.51 74.90 75.29 75.69 76.08 76.47 76.86 77.25 77.65 78.04 78.43 78.82 79.22 79.61 "
"80.00 80.39 80.78 81.18 81.57 81.96 82.35 82.75 83.14 83.53 83.92 84.31 84.71 85.10 "
"85.49 85.88 86.27 86.67 87.06 87.45 87.84 88.24 88.63 89.02 89.41 89.80 90.20 90.59 "
"90.98 91.37 91.76 92.16 92.55 92.94 93.33 93.73 94.12 94.51 94.90 95.29 95.69 96.08 "
"96.47 96.86 97.25 97.65 98.04 98.43 98.82 99.22 99.61 100.00 ]"]
dataset = self._get_test_dataset_calibration()
w = MITIFFWriter(filename=dataset.attrs["metadata_requirements"]["file_pattern"], base_dir=self.base_dir)
w.save_dataset(dataset)
filename = (dataset.attrs["metadata_requirements"]["file_pattern"]).format(
start_time=dataset.attrs["start_time"])
imgdesc = self._imagedescription_from_mitiff(os.path.join(self.base_dir, filename))
found_table_calibration = False
number_of_calibrations = 0
for key in imgdesc:
if "Table_calibration" in key:
found_table_calibration = True
if "1-VIS0.63" in key:
assert key == expected_key_channel[0]
number_of_calibrations += 1
elif "2-VIS0.86" in key:
assert key == expected_key_channel[1]
number_of_calibrations += 1
elif "3(3B)-IR3.7" in key:
assert key == expected_key_channel[2]
number_of_calibrations += 1
elif "4-IR10.8" in key:
assert key == expected_key_channel[3]
number_of_calibrations += 1
elif "5-IR11.5" in key:
assert key == expected_key_channel[4]
number_of_calibrations += 1
elif "6(3A)-VIS1.6" in key:
assert key == expected_key_channel[5]
number_of_calibrations += 1
else:
self.fail("Not a valid channel description i the given key.")
assert found_table_calibration, "Table_calibration is not found in the imagedescription."
assert number_of_calibrations == 6
pillow_tif = Image.open(os.path.join(self.base_dir, filename))
assert pillow_tif.n_frames == 6
self._read_back_mitiff_and_check(os.path.join(self.base_dir, filename), expected)
[docs]
def test_save_dataset_with_calibration_one_dataset(self):
"""Test saving if mitiff as dataset with only one channel."""
from satpy.writers.mitiff import MITIFFWriter
expected = [np.full((100, 200), 255)]
expected_key_channel = [u"Table_calibration: BT, BT, °[C], 8, [ 50.00 49.22 48.43 47.65 46.86 46.08 45.29 "
"44.51 43.73 42.94 42.16 41.37 40.59 39.80 39.02 38.24 37.45 36.67 35.88 35.10 34.31 "
"33.53 32.75 31.96 31.18 30.39 29.61 28.82 28.04 27.25 26.47 25.69 24.90 24.12 23.33 "
"22.55 21.76 20.98 20.20 19.41 18.63 17.84 17.06 16.27 15.49 14.71 13.92 13.14 12.35 "
"11.57 10.78 10.00 9.22 8.43 7.65 6.86 6.08 5.29 4.51 3.73 2.94 2.16 1.37 0.59 -0.20 "
"-0.98 -1.76 -2.55 -3.33 -4.12 -4.90 -5.69 -6.47 -7.25 -8.04 -8.82 -9.61 -10.39 -11.18 "
"-11.96 -12.75 -13.53 -14.31 -15.10 -15.88 -16.67 -17.45 -18.24 -19.02 -19.80 -20.59 "
"-21.37 -22.16 -22.94 -23.73 -24.51 -25.29 -26.08 -26.86 -27.65 -28.43 -29.22 -30.00 "
"-30.78 -31.57 -32.35 -33.14 -33.92 -34.71 -35.49 -36.27 -37.06 -37.84 -38.63 -39.41 "
"-40.20 -40.98 -41.76 -42.55 -43.33 -44.12 -44.90 -45.69 -46.47 -47.25 -48.04 -48.82 "
"-49.61 -50.39 -51.18 -51.96 -52.75 -53.53 -54.31 -55.10 -55.88 -56.67 -57.45 -58.24 "
"-59.02 -59.80 -60.59 -61.37 -62.16 -62.94 -63.73 -64.51 -65.29 -66.08 -66.86 -67.65 "
"-68.43 -69.22 -70.00 -70.78 -71.57 -72.35 -73.14 -73.92 -74.71 -75.49 -76.27 -77.06 "
"-77.84 -78.63 -79.41 -80.20 -80.98 -81.76 -82.55 -83.33 -84.12 -84.90 -85.69 -86.47 "
"-87.25 -88.04 -88.82 -89.61 -90.39 -91.18 -91.96 -92.75 -93.53 -94.31 -95.10 -95.88 "
"-96.67 -97.45 -98.24 -99.02 -99.80 -100.59 -101.37 -102.16 -102.94 -103.73 -104.51 "
"-105.29 -106.08 -106.86 -107.65 -108.43 -109.22 -110.00 -110.78 -111.57 -112.35 "
"-113.14 -113.92 -114.71 -115.49 -116.27 -117.06 -117.84 -118.63 -119.41 -120.20 "
"-120.98 -121.76 -122.55 -123.33 -124.12 -124.90 -125.69 -126.47 -127.25 -128.04 "
"-128.82 -129.61 -130.39 -131.18 -131.96 -132.75 -133.53 -134.31 -135.10 -135.88 "
"-136.67 -137.45 -138.24 -139.02 -139.80 -140.59 -141.37 -142.16 -142.94 -143.73 "
"-144.51 -145.29 -146.08 -146.86 -147.65 -148.43 -149.22 -150.00 ]", ]
dataset = self._get_test_dataset_calibration_one_dataset()
w = MITIFFWriter(filename=dataset.attrs["metadata_requirements"]["file_pattern"], base_dir=self.base_dir)
w.save_dataset(dataset)
filename = (dataset.attrs["metadata_requirements"]["file_pattern"]).format(
start_time=dataset.attrs["start_time"])
imgdesc = self._imagedescription_from_mitiff(os.path.join(self.base_dir, filename))
found_table_calibration = False
number_of_calibrations = 0
for key in imgdesc:
if "Table_calibration" in key:
found_table_calibration = True
if "BT" in key:
assert key == expected_key_channel[0]
number_of_calibrations += 1
assert found_table_calibration, "Expected table_calibration is not found in the imagedescription."
assert number_of_calibrations == 1
self._read_back_mitiff_and_check(os.path.join(self.base_dir, filename), expected)
[docs]
def test_save_dataset_with_bad_value(self):
"""Test writer operation with bad values."""
from satpy.writers.mitiff import MITIFFWriter
_expected = np.array([[0, 4, 1, 37, 73],
[110, 146, 183, 219, 255]])
expected = [_expected, _expected, _expected]
dataset = self._get_test_dataset_with_bad_values()
w = MITIFFWriter(base_dir=self.base_dir)
w.save_dataset(dataset)
filename = "{:s}_{:%Y%m%d_%H%M%S}.mitiff".format(dataset.attrs["name"],
dataset.attrs["start_time"])
self._read_back_mitiff_and_check(os.path.join(self.base_dir, filename), expected, test_shape=(2, 5))
[docs]
def test_convert_proj4_string(self):
"""Test conversion of geolocations."""
import dask.array as da
import xarray as xr
from pyresample.geometry import AreaDefinition
from satpy.writers.mitiff import MITIFFWriter
checks = [{"epsg": "EPSG:32631",
"proj4": (" Proj string: +proj=etmerc +lat_0=0 +lon_0=3 +k=0.9996 "
"+ellps=WGS84 +datum=WGS84 +units=km +x_0=501020.000000 "
"+y_0=1515.000000\n")},
{"epsg": "EPSG:32632",
"proj4": (" Proj string: +proj=etmerc +lat_0=0 +lon_0=9 +k=0.9996 "
"+ellps=WGS84 +datum=WGS84 +units=km +x_0=501020.000000 "
"+y_0=1515.000000\n")},
{"epsg": "EPSG:32633",
"proj4": (" Proj string: +proj=etmerc +lat_0=0 +lon_0=15 +k=0.9996 "
"+ellps=WGS84 +datum=WGS84 +units=km +x_0=501020.000000 "
"+y_0=1515.000000\n")},
{"epsg": "EPSG:32634",
"proj4": (" Proj string: +proj=etmerc +lat_0=0 +lon_0=21 +k=0.9996 "
"+ellps=WGS84 +datum=WGS84 +units=km +x_0=501020.000000 "
"+y_0=1515.000000\n")},
{"epsg": "EPSG:32635",
"proj4": (" Proj string: +proj=etmerc +lat_0=0 +lon_0=27 +k=0.9996 "
"+ellps=WGS84 +datum=WGS84 +units=km +x_0=501020.000000 "
"+y_0=1515.000000\n")}]
for check in checks:
area_def = AreaDefinition(
"test",
"test",
"test",
check["epsg"],
100,
200,
(-1000., -1500., 1000., 1500.),
)
ds1 = xr.DataArray(
da.zeros((10, 20), chunks=20),
dims=("y", "x"),
attrs={"area": area_def}
)
w = MITIFFWriter(filename="dummy.tif", base_dir=self.base_dir)
proj4_string = w._add_proj4_string(ds1, ds1)
assert proj4_string == check["proj4"]
[docs]
def test_correction_proj4_string(self):
"""Test correction of proj4 lower left coordinate."""
import dask.array as da
import xarray as xr
from pyresample.geometry import AreaDefinition
from satpy.writers.mitiff import MITIFFWriter
area_def = AreaDefinition(
"test",
"test",
"test",
"+proj=merc",
100,
200,
(-1000., -1500., 1000., 1500.),
)
ds1 = xr.DataArray(
da.zeros((10, 20), chunks=20),
dims=("y", "x"),
attrs={"area": area_def}
)
default_expected_correction = (20.0, 15.0)
w = MITIFFWriter(filename="dummy.tif", base_dir=self.base_dir)
mitiff_pixel_adjustment = True
correction = w._set_correction_size(ds1, mitiff_pixel_adjustment)
assert correction == default_expected_correction
mitiff_pixel_adjustment = False
new_expected_correction = (0, 0)
w = MITIFFWriter(filename="dummy.tif", base_dir=self.base_dir)
correction = w._set_correction_size(ds1, mitiff_pixel_adjustment)
assert correction == new_expected_correction
[docs]
def test_save_dataset_palette(self):
"""Test writer operation as palette."""
from satpy.writers.mitiff import MITIFFWriter
expected = [np.full((100, 200), 0)]
exp_c = [0, 3, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
1, 4, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
2, 5, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0]
color_map = (0, 1, 2, 3, 4, 5)
pal_desc = ["test", "test2"]
unit = "Test"
dataset = self._get_test_one_dataset()
palette = {"palette": True,
"palette_color_map": color_map,
"palette_description": pal_desc,
"palette_unit": unit,
"palette_channel_name": dataset.attrs["name"]}
w = MITIFFWriter(base_dir=self.base_dir)
w.save_dataset(dataset, **palette)
filename = "{:s}_{:%Y%m%d_%H%M%S}.mitiff".format(dataset.attrs["name"],
dataset.attrs["start_time"])
pillow_tif = Image.open(os.path.join(self.base_dir, filename))
# Need to check PHOTOMETRIC is 3, ie palette
assert pillow_tif.tag_v2.get(262) == 3
# Check the colormap of the palette image
palette = pillow_tif.palette
colormap = list((palette.getdata())[1])
assert colormap == exp_c
imgdesc = self._imagedescription_from_mitiff(os.path.join(self.base_dir, filename))
found_color_info = False
unit_name_found = False
name_length_found = False
name_length = 0
names = []
unit_name = None
for key in imgdesc:
if name_length_found and name_length > len(names):
names.append(key)
continue
elif unit_name_found:
name_length = int(key)
name_length_found = True
unit_name_found = False
elif found_color_info:
unit_name = key
unit_name_found = True
found_color_info = False
elif "COLOR INFO:" in key:
found_color_info = True
# Check the name of the palette description
assert name_length == 2
# Check the name and unit name of the palette
assert unit_name == " Test"
# Check the palette description of the palette
assert names == [" test", " test2"]
self._read_back_mitiff_and_check(os.path.join(self.base_dir, filename), expected)
[docs]
def test_simple_write_two_bands(self):
"""Test basic writer operation with 3 bands from 2 prerequisites."""
from satpy.writers.mitiff import MITIFFWriter
dataset = self._get_test_dataset_three_bands_two_prereq()
w = MITIFFWriter(base_dir=self.base_dir)
w.save_dataset(dataset)
[docs]
def test_get_test_dataset_three_bands_prereq(self):
"""Test basic writer operation with 3 bands with DataQuery prerequisites with missing name."""
from satpy.writers.mitiff import MITIFFWriter
dataset = self._get_test_dataset_three_bands_prereq()
w = MITIFFWriter(base_dir=self.base_dir)
w.save_dataset(dataset)
filename = "{:s}_{:%Y%m%d_%H%M%S}.mitiff".format(dataset.attrs["name"],
dataset.attrs["start_time"])
imgdesc = self._imagedescription_from_mitiff(os.path.join(self.base_dir, filename))
for element in imgdesc:
if " Channels:" in element:
assert element == " Channels: 3 In this file: 1 2 3"
[docs]
def test_save_dataset_with_calibration_error_one_dataset(self):
"""Test saving if mitiff as dataset with only one channel with invalid calibration."""
import sys
from satpy.tests.utils import make_dsq
from satpy.writers.mitiff import MITIFFWriter
logger.level = logging.DEBUG
dataset = self._get_test_dataset_calibration_one_dataset()
prereqs = [make_dsq(name="4", calibration="not_valid_calibration_name")]
dataset.attrs["prerequisites"] = prereqs
w = MITIFFWriter(filename=dataset.attrs["metadata_requirements"]["file_pattern"], base_dir=self.base_dir)
_reverse_offset = 0.
_reverse_scale = 1.
_decimals = 2
stream_handler = logging.StreamHandler(sys.stdout)
logger.addHandler(stream_handler)
try:
with self.assertLogs(logger) as lc:
w._add_calibration_datasets(4, dataset, _reverse_offset, _reverse_scale, _decimals)
for _op in lc.output:
assert "Unknown calib type. Must be Radiance, Reflectance or BT." in _op
finally:
logger.removeHandler(stream_handler)
[docs]
def test_save_dataset_with_missing_palette(self):
"""Test saving if mitiff missing palette."""
import sys
from satpy.writers.mitiff import MITIFFWriter
stream_handler = logging.StreamHandler(sys.stdout)
logger.addHandler(stream_handler)
logger.setLevel(logging.DEBUG)
dataset = self._get_test_one_dataset()
pal_desc = ["test", "test2"]
unit = "Test"
palette = {"palette": True,
"palette_description": pal_desc,
"palette_unit": unit,
"palette_channel_name": dataset.attrs["name"]}
w = MITIFFWriter(base_dir=self.base_dir)
tiffinfo = {}
tiffinfo[270] = "Just dummy image desc".encode("utf-8")
filename = "{:s}_{:%Y%m%d_%H%M%S}.mitiff".format(dataset.attrs["name"],
dataset.attrs["start_time"])
try:
with self.assertLogs(logger, logging.ERROR) as lc:
w._save_as_palette(dataset.compute(), os.path.join(self.base_dir, filename), tiffinfo, **palette)
for _op in lc.output:
assert "In a mitiff palette image a color map must be provided: palette_color_map is missing." in _op
finally:
logger.removeHandler(stream_handler)