Skip to content

Preserve input attrs through reproject() and merge()#1446

Merged
brendancol merged 2 commits intomainfrom
metadata-attrs-reproject-merge
May 4, 2026
Merged

Preserve input attrs through reproject() and merge()#1446
brendancol merged 2 commits intomainfrom
metadata-attrs-reproject-merge

Conversation

@brendancol
Copy link
Copy Markdown
Contributor

Summary

  • reproject() and merge() now merge input attrs forward instead of building output attrs from scratch, so units, long_name, scale_factor, add_offset, _FillValue, and similar metadata survive the transform.
  • Stale grid attrs (transform, res, crs_wkt) are popped before the new crs/nodata are written, since they describe the old grid and would mislead downstream consumers.
  • merge() falls back its output name to rasters[0].name before 'merged', matching the pattern reproject() already uses.

Test plan

  • New TestMetadataPreservation covers units, scale_factor/add_offset, long_name, stale transform, stale res, stale crs_wkt, and the crs override for reproject().
  • Same class covers first-raster attr preservation, stale-transform drop, and the name fallback for merge().
  • pytest xrspatial/tests/test_reproject.py -x -> 146 passed.

Closes #1445

Both public APIs in xrspatial.reproject built `out_attrs` from scratch,
dropping units, long_name, scale_factor, add_offset, _FillValue, and any
custom metadata the caller had attached. Merge input attrs forward and
override only what the operation actually changes.

Pop attrs that are stale after the transform (transform, res, crs_wkt)
since carrying them through would be actively wrong.

merge() now also falls back name to rasters[0].name before 'merged',
matching how reproject() falls back to raster.name.

Closes #1445
@github-actions github-actions Bot added the performance PR touches performance-sensitive code label May 4, 2026
@brendancol
Copy link
Copy Markdown
Contributor Author

@copilot resolve the merge conflicts in this pull request

… tests

Co-authored-by: brendancol <433221+brendancol@users.noreply.github.com>
Copy link
Copy Markdown
Contributor

Copilot AI commented May 4, 2026

@copilot resolve the merge conflicts in this pull request

Merge conflicts resolved in commit 3138066. The conflict in test_reproject.py was between TestMetadataPreservation (from this PR) and the new TestDaskDtypeParity, TestMergeDaskParity, and TestCupyReprojectParity classes from main — both sections are now included. All 149 tests pass.

@brendancol brendancol merged commit 79daedb into main May 4, 2026
1 check was pending
brendancol added a commit that referenced this pull request May 4, 2026
Three small follow-ups to PR #1446 in `xrspatial/reproject/__init__.py`:

- `reproject()` and `merge()` re-emit `attrs['transform']` and
  `attrs['res']` for the new output grid instead of dropping them. The
  transform uses the rasterio 6-tuple convention
  `(res_x, 0.0, left, 0.0, -res_y, top)`. The geotiff reader does not
  itself write these attrs, so there is no in-repo convention to match
  and the rasterio form is used as the default.
- `merge()` uses `_find_spatial_dims` instead of assuming the last two
  dims are spatial, both when collecting per-raster shapes and when
  building the output coords.
- Both functions copy the resolved nodata value into `_FillValue` when
  the input set `_FillValue`. Inputs that did not set `_FillValue` get
  no `_FillValue` on output.

Tests in `TestMetadataPreservation` cover the fresh transform/res
values, absence-of-input behaviour, `_find_spatial_dims` use with
lat/lon dims, and `_FillValue` round-trip for both functions.
@brendancol brendancol deleted the metadata-attrs-reproject-merge branch May 5, 2026 03:45
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

performance PR touches performance-sensitive code

Projects

None yet

Development

Successfully merging this pull request may close these issues.

reproject and merge silently drop input DataArray attrs

2 participants