def test_incompatible_attributes(self): invalid_vars = [ Variable(['t'], pd.date_range('2000-01-01', periods=3), {'units': 'foobar'}), Variable(['t'], pd.to_timedelta(['1 day']), {'units': 'foobar'}), Variable(['t'], [0, 1, 2], {'add_offset': 0}, {'add_offset': 2}), Variable(['t'], [0, 1, 2], {'_FillValue': 0}, {'_FillValue': 2}), ] for var in invalid_vars: with self.assertRaises(ValueError): conventions.encode_cf_variable(var)
def test_incompatible_attributes(self): invalid_vars = [ Variable(['t'], pd.date_range('2000-01-01', periods=3), {'units': 'foobar'}), Variable(['t'], pd.to_timedelta(['1 day']), {'units': 'foobar'}), Variable(['t'], [0, 1, 2], {'add_offset': 0}, {'add_offset': 2}), Variable(['t'], [0, 1, 2], {'_FillValue': 0}, {'_FillValue': 2}), ] for var in invalid_vars: with pytest.raises(ValueError): conventions.encode_cf_variable(var)
def test_incompatible_attributes(self): invalid_vars = [ Variable(["t"], pd.date_range("2000-01-01", periods=3), {"units": "foobar"}), Variable(["t"], pd.to_timedelta(["1 day"]), {"units": "foobar"}), Variable(["t"], [0, 1, 2], {"add_offset": 0}, {"add_offset": 2}), Variable(["t"], [0, 1, 2], {"_FillValue": 0}, {"_FillValue": 2}), ] for var in invalid_vars: with pytest.raises(ValueError): conventions.encode_cf_variable(var)
def to_raster(self, xarray_dataarray, tags, windowed, lock, compute, **kwargs): """ This method writes to the raster on disk. xarray_dataarray: xarray.DataArray The input data array to write to disk. tags: dict, optional A dictionary of tags to write to the raster. windowed: bool If True and the data array is not a dask array, it will write the data to disk using rasterio windows. lock: boolean or Lock, optional Lock to use to write data using dask. If not supplied, it will use a single process. compute: bool If True (default) and data is a dask array, then compute and save the data immediately. If False, return a dask Delayed object. Call ".compute()" on the Delayed object to compute the result later. Call ``dask.compute(delayed1, delayed2)`` to save multiple delayed files at once. **kwargs Keyword arguments to pass into writing the raster. """ dtype = kwargs["dtype"] # generate initial output file with rasterio.open(self.raster_path, "w", **kwargs) as rds: _write_metatata_to_raster(rds, xarray_dataarray, tags) if not (lock and is_dask_collection(xarray_dataarray.data)): # write data to raster immmediately if not dask array if windowed: window_iter = rds.block_windows(1) else: window_iter = [(None, None)] for _, window in window_iter: if window is not None: out_data = xarray_dataarray.rio.isel_window(window) else: out_data = xarray_dataarray data = encode_cf_variable(out_data).values.astype(dtype) if data.ndim == 2: rds.write(data, 1, window=window) else: rds.write(data, window=window) if lock and is_dask_collection(xarray_dataarray.data): return dask.array.store( encode_cf_variable(xarray_dataarray).data.astype(dtype), self, lock=lock, compute=compute, ) return None
def test_string_object_warning(self): original = Variable( ('x',), np.array([u'foo', u'bar'], dtype=object)).chunk() with pytest.warns(SerializationWarning, match='dask array with dtype=object'): encoded = conventions.encode_cf_variable(original) assert_identical(original, encoded)
def test_string_object_warning(self): original = Variable(('x', ), np.array([u'foo', u'bar'], dtype=object)).chunk() with pytest.warns(SerializationWarning, match='dask array with dtype=object'): encoded = conventions.encode_cf_variable(original) assert_identical(original, encoded)
def test_string_object_warning(self): original = Variable(("x", ), np.array(["foo", "bar"], dtype=object)).chunk() with pytest.warns(SerializationWarning, match="dask array with dtype=object"): encoded = conventions.encode_cf_variable(original) assert_identical(original, encoded)
def test_encode_decode_roundtrip_cftime(freq): initial_time = cftime_range("0001", periods=1) times = initial_time.append( cftime_range("0001", periods=2, freq=freq) + timedelta(days=291000 * 365)) variable = Variable(["time"], times) encoded = conventions.encode_cf_variable(variable) decoded = conventions.decode_cf_variable("time", encoded, use_cftime=True) assert_equal(variable, decoded)
def test_encode_decode_roundtrip_datetime64(freq): # See GH 4045. Prior to GH 4684 this test would fail for frequencies of # "S", "L", "U", and "N". initial_time = pd.date_range("1678-01-01", periods=1) times = initial_time.append(pd.date_range("1968", periods=2, freq=freq)) variable = Variable(["time"], times) encoded = conventions.encode_cf_variable(variable) decoded = conventions.decode_cf_variable("time", encoded) assert_equal(variable, decoded)
def test_CFMaskCoder_encode_missing_fill_values_conflict(data, encoding): original = xr.Variable(("x", ), data, encoding=encoding) encoded = encode_cf_variable(original) assert encoded.dtype == encoded.attrs["missing_value"].dtype assert encoded.dtype == encoded.attrs["_FillValue"].dtype with pytest.warns(variables.SerializationWarning): roundtripped = decode_cf_variable("foo", encoded) assert_identical(roundtripped, original)
def test_decode_encode_roundtrip_with_non_lowercase_letters(calendar): # See GH 5093. times = [0, 1] units = "days since 2000-01-01" attrs = {"calendar": calendar, "units": units} variable = Variable(["time"], times, attrs) decoded = conventions.decode_cf_variable("time", variable) encoded = conventions.encode_cf_variable(decoded) # Previously this would erroneously be an array of cftime.datetime # objects. We check here that it is decoded properly to np.datetime64. assert np.issubdtype(decoded.dtype, np.datetime64) # Use assert_identical to ensure that the calendar attribute maintained its # original form throughout the roundtripping process, uppercase letters and # all. assert_identical(variable, encoded)
def test_missing_fillvalue(self): v = Variable(['x'], np.array([np.nan, 1, 2, 3])) v.encoding = {'dtype': 'int16'} with self.assertWarns('floating point data as an integer'): conventions.encode_cf_variable(v)
def test_missing_fillvalue(self): v = Variable(['x'], np.array([np.nan, 1, 2, 3])) v.encoding = {'dtype': 'int16'} with pytest.warns(Warning, match='floating point data as an integer'): conventions.encode_cf_variable(v)
def test_missing_fillvalue(self) -> None: v = Variable(["x"], np.array([np.nan, 1, 2, 3])) v.encoding = {"dtype": "int16"} with pytest.warns(Warning, match="floating point data as an integer"): conventions.encode_cf_variable(v)
def to_raster(self, xarray_dataarray, tags, windowed, lock, compute, **kwargs): """ This method writes to the raster on disk. xarray_dataarray: xarray.DataArray The input data array to write to disk. tags: dict, optional A dictionary of tags to write to the raster. windowed: bool If True and the data array is not a dask array, it will write the data to disk using rasterio windows. lock: boolean or Lock, optional Lock to use to write data using dask. If not supplied, it will use a single process. compute: bool If True (default) and data is a dask array, then compute and save the data immediately. If False, return a dask Delayed object. Call ".compute()" on the Delayed object to compute the result later. Call ``dask.compute(delayed1, delayed2)`` to save multiple delayed files at once. dtype: np.dtype Numpy-compliant dtype used to save raster. If data is not already represented by this dtype in memory it is recast. dtype='complex_int16' is a special case to write in-memory np.complex64 to CInt16. **kwargs Keyword arguments to pass into writing the raster. """ kwargs["dtype"], numpy_dtype = _get_dtypes( kwargs["dtype"], xarray_dataarray.encoding.get("rasterio_dtype"), xarray_dataarray.encoding.get("dtype", str(xarray_dataarray.dtype)), ) if kwargs["nodata"] is not None: # Ensure dtype of output data matches the expected dtype. # This check is added here as the dtype of the data is # converted right before writing. kwargs["nodata"] = _ensure_nodata_dtype(kwargs["nodata"], numpy_dtype) with rasterio.open(self.raster_path, "w", **kwargs) as rds: _write_metatata_to_raster(rds, xarray_dataarray, tags) if not (lock and is_dask_collection(xarray_dataarray.data)): # write data to raster immmediately if not dask array if windowed: window_iter = rds.block_windows(1) else: window_iter = [(None, None)] for _, window in window_iter: if window is not None: out_data = xarray_dataarray.rio.isel_window(window) else: out_data = xarray_dataarray data = encode_cf_variable(out_data).values.astype(numpy_dtype) if data.ndim == 2: rds.write(data, 1, window=window) else: rds.write(data, window=window) if lock and is_dask_collection(xarray_dataarray.data): return dask.array.store( encode_cf_variable(xarray_dataarray).data.astype(numpy_dtype), self, lock=lock, compute=compute, ) return None