Repository: arviz-devs/arviz

Issue:
to_netcdf fails with error writing PyMC3 trace containing pm.Data as observed
**Describe the bug**
If one creates a model that has an observed RV, and the observations for that RV are a `pm.Data` object, and one tries to invoke `to_netcdf()` on the resulting arviz `InferenceData` object, you get an error in `ensure_dtype_not_object()`.  Inspection of the backtrace shows that the `InferenceData` object has the *name of the `pm.Data()`* in the observation array, instead of the data that populates the `Data` object.
Note that trying to save a *prior predictive trace* alone does *not* trigger this bug. As far as I can tell, it must be a sample from the posterior.
**To Reproduce**
See attached jupyter notebook for a minimal case.


**Additional context**
`arviz` 0.4.0
`pymc3` from git
MacOS (but I think that's irrelevant)
[arviz-to_netcdf-bug.ipynb.txt](https://github.com/arviz-devs/arviz/files/3233360/arviz-to_netcdf-bug.ipynb.txt)




Discussion:
Interesting. It should be xarray.
It occurs to me, as I was saying on Slack, that this might be a *symptom* of an underlying bug.  In particular, should these `Data` objects be expanded by `to_pymc3()`? So maybe it's not `to_netcdf()` that needs fixing.
There should not be anything left from pymc in idata

```

    @requires("trace")
    def posterior_to_xarray(self):
        """Convert the posterior to an xarray dataset."""
        var_names = self.pymc3.util.get_default_varnames(  # pylint: disable=no-member
            self.trace.varnames, include_transformed=False
        )
        data = {}
        for var_name in var_names:
            data[var_name] = np.array(self.trace.get_values(var_name, combine=False, squeeze=False))
        return dict_to_dataset(data, library=self.pymc3, coords=self.coords, dims=self.dims)

    @requires("trace")
    def sample_stats_to_xarray(self):
        """Extract sample_stats from PyMC3 trace."""
        rename_key = {"model_logp": "lp"}
        data = {}
        for stat in self.trace.stat_names:
            name = rename_key.get(stat, stat)
            data[name] = np.array(self.trace.get_sampler_stats(stat, combine=False))
        log_likelihood, dims = self._extract_log_likelihood()
        if log_likelihood is not None:
            data["log_likelihood"] = log_likelihood
            dims = {"log_likelihood": dims}
        else:
            dims = None

        return dict_to_dataset(data, library=self.pymc3, dims=dims, coords=self.coords)
```
~Nope, I couldn't reproduce this on Windows.~ I will update my PyMC3 and try again
Yes I could reproduce this.

This fails:

    np.array(obs)

This works

    np.asarray(obs.get_value())

Resolving patch:
diff --git a/arviz/data/io_pymc3.py b/arviz/data/io_pymc3.py
--- a/arviz/data/io_pymc3.py
+++ b/arviz/data/io_pymc3.py
@@ -114,6 +114,8 @@ def observed_data_to_xarray(self):
             dims = self.dims
         observed_data = {}
         for name, vals in observations.items():
+            if hasattr(vals, "get_value"):
+                vals = vals.get_value()
             vals = np.atleast_1d(vals)
             val_dims = dims.get(name)
             val_dims, coords = generate_dims_coords(


Test patch: