Skip to content

Update open_dataset backend to ensure compatibility with new explicit index model #7150

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 9 commits into from
Oct 12, 2022
2 changes: 2 additions & 0 deletions doc/whats-new.rst
Original file line number Diff line number Diff line change
Expand Up @@ -47,6 +47,8 @@ Bug fixes
:py:meth:`DataArray.to_index` for multi-index levels (convert to single index).
(:issue:`6836`, :pull:`7105`)
By `Benoît Bovy <https://github.com/benbovy>`_.
- Support for open_dataset backends that return datasets containing multi-indexes (:issue:`7139`, :pull:`7150`)
By `Lukas Bindreiter <https://github.com/lukasbindreiter>`_.

Documentation
~~~~~~~~~~~~~
Expand Down
2 changes: 1 addition & 1 deletion xarray/backends/api.py
Original file line number Diff line number Diff line change
Expand Up @@ -234,7 +234,7 @@ def _get_mtime(filename_or_obj):

def _protect_dataset_variables_inplace(dataset, cache):
for name, variable in dataset.variables.items():
if name not in variable.dims:
if name not in dataset._indexes:
# no need to protect IndexVariable objects
data = indexing.CopyOnWriteArray(variable._data)
if cache:
Expand Down
19 changes: 19 additions & 0 deletions xarray/tests/test_backends_api.py
Original file line number Diff line number Diff line change
Expand Up @@ -48,6 +48,25 @@ def open_dataset(
assert_identical(expected, actual)


def test_multiindex() -> None:
# GH7139
# Check that we properly handle backends that change index variables
dataset = xr.Dataset(coords={"coord1": ["A", "B"], "coord2": [1, 2]})
dataset = dataset.stack(z=["coord1", "coord2"])

class MultiindexBackend(xr.backends.BackendEntrypoint):
def open_dataset(
self,
filename_or_obj,
drop_variables=None,
**kwargs,
) -> xr.Dataset:
return dataset.copy(deep=True)

loaded = xr.open_dataset("fake_filename", engine=MultiindexBackend)
assert_identical(dataset, loaded)


class PassThroughBackendEntrypoint(xr.backends.BackendEntrypoint):
"""Access an object passed to the `open_dataset` method."""

Expand Down