Skip to content
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

Feat pyproj crs #1737

Merged
merged 28 commits into from
Apr 26, 2023
Merged

Feat pyproj crs #1737

merged 28 commits into from
Apr 26, 2023

Conversation

aleaf
Copy link
Contributor

@aleaf aleaf commented Mar 1, 2023

This pull request seeks to refactor coordinate reference system (CRS) handling in Flopy to exclusively use the pyproj.CRS coordinate reference system manager object. Basically, this means that a single crs argument can be used to specify a CRS is any recognized format (EPSG code, proj string, well-known text etc) and pyproj.CRS will detect the format and the CRS if it can, and create an object instance accordingly that can then be passed to other functions and methods that need a CRS. This means that we no longer have to manage multiple options for CRS input, and it also greatly simplifies comparison of CRS from different inputs. The exception to this is retaining a prjfile argument to the modelgrid and export methods, which allows users to simply supply a path to an ESRI-style projection file, instead of having to open the file themselves to get and then manage the well-known text inside. This may be more convenient for users working with more obscure CRS that don't have an EPSG code, for example. A few notes:

  • this change requires pyproj 2.2.0 or later. If pyproj is not installed, Flopy should still work as-is but without the CRS handling
  • epsg and proj4 arguments are still accepted, but produce a warning that they will be deprecated in Flopy 3.4
  • invalid CRS are no longer accepted (they ultimately produce an error when passed to pyproj.CRS)
  • geographic CRS are no longer accepted because that would imply that the modelgrid object could produce coordinates in lat/long space. In other words, we assume that the model is located in a projected coordinate reference system somewhere that has length units of (most likely) meters or feet
  • with this change, the string representation of the pyproj.CRS object is written to the Name file under a crs key. Usually this is just a simple authority string such as "EPSG: 26916", but this could also be full well-known text string like in a projection file. PROJ strings and EPSG codes are still read from the Name file or usgs.model.reference files as previously.

In addition to simplifying input for users, this should improve the reliability and robustness of exporting data that can be displayed or used in a GIS with other data. It could also enable automatic reprojection of input data from GIS file formats or other models, in Flopy's preprocessing utilities.

@codecov
Copy link

codecov bot commented Mar 1, 2023

Codecov Report

Merging #1737 (dadaa00) into develop (516721d) will decrease coverage by 0.1%.
The diff coverage is 91.4%.

@@            Coverage Diff            @@
##           develop   #1737     +/-   ##
=========================================
- Coverage     72.1%   72.0%   -0.1%     
=========================================
  Files          253     254      +1     
  Lines        56040   55915    -125     
=========================================
- Hits         40420   40302    -118     
+ Misses       15620   15613      -7     
Impacted Files Coverage Δ
flopy/discretization/structuredgrid.py 46.8% <ø> (ø)
flopy/discretization/unstructuredgrid.py 84.9% <ø> (ø)
flopy/discretization/vertexgrid.py 82.6% <ø> (+0.3%) ⬆️
flopy/modflow/mf.py 68.8% <ø> (ø)
flopy/seawat/swt.py 81.3% <ø> (ø)
flopy/utils/mfreadnam.py 34.0% <66.6%> (+0.5%) ⬆️
flopy/discretization/grid.py 77.0% <78.9%> (+1.2%) ⬆️
flopy/utils/crs.py 91.1% <91.1%> (ø)
flopy/export/utils.py 64.8% <92.8%> (-0.5%) ⬇️
flopy/export/netcdf.py 49.2% <98.3%> (+0.4%) ⬆️
... and 5 more

... and 6 files with indirect coverage changes

@aleaf aleaf marked this pull request as ready for review March 1, 2023 19:25
@aleaf aleaf requested a review from mwtoews March 1, 2023 19:25
Copy link
Contributor

@mwtoews mwtoews left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is a good feature, and I've thought of implementing this at one time too. Users of GeoPandas or rasterio know the .crs property, so this is aims to be similar bridge to modern pyproj / PROJ.

However, I'd like to see #1730 merged before a thorough review, as I anticipate several conflicts. Only a few comments from a quick first read are attached.

flopy/discretization/unstructuredgrid.py Outdated Show resolved Hide resolved
flopy/discretization/vertexgrid.py Outdated Show resolved Hide resolved
flopy/export/netcdf.py Show resolved Hide resolved
@aleaf
Copy link
Contributor Author

aleaf commented Mar 2, 2023

@mwtoews thanks for taking an initial look. Agreed that it makes sense to wait for #1730.

@aleaf aleaf force-pushed the feat_pyproj_crs branch 2 times, most recently from 49c159b to 85d660d Compare March 20, 2023 22:26
@aleaf aleaf requested a review from mwtoews March 21, 2023 14:39
@aleaf aleaf force-pushed the feat_pyproj_crs branch from 85d660d to 5c63b52 Compare March 28, 2023 15:48
@aleaf aleaf requested a review from jlarsen-usgs March 30, 2023 14:33
aleaf added 20 commits April 12, 2023 09:02
…to a pyproj.CRS instance attached to the grid classes as a .crs attribute
…to a pyproj.CRS instance attached to the grid classes as a .crs attribute
…efile header under 'crs' key; read 'proj4' key as crs input
…self._modelgrid.set_coord_info() instead of epsg or proj4
…of proj4 (needed for a792e73); fix(Grid.read_usgs_model_reference_file): to handle quoting in usgs.model.reference
…id issues with encoding the degree symbol to ascii; fix the same issue in test_grid.py. Also replace epsg code 4326 in example name files with epsgs for projected CRS (geographic CRS no longer allowed)
* refactor to use pyproj.CRS instead of epsg and proj4 to store CRS information;
* use pyproj.CRS.to_cf() to get Climate and Forecast (CF) grid mapping input for the NetCDF file
* drop support for pyproj versions < 2.2.0
* move contents of _initialize_attributes to __init__() method
* remove tests related to CRS and EpsgReference classes in shapefile_utils (deprecated)
* refactor export tests to use crs instead of epsg/proj4
* remove test_export::test_write_grid_shapefile; better one in test_shapefile_utils.py
* add additional testing for Grid.set_coord_info()
* remove _initialize_attributes() method
* call initialize_geometry() in workflow regardless if model has a crs or not (and set bounds and vbounds attributes in both cases)
@aleaf aleaf force-pushed the feat_pyproj_crs branch from 5c63b52 to 9845290 Compare April 12, 2023 14:08
@aleaf
Copy link
Contributor Author

aleaf commented Apr 12, 2023

@mwtoews any other comments?

@mwtoews
Copy link
Contributor

mwtoews commented Apr 12, 2023

Apologies for the slow delay, but I'll make some time in the next few days to provide more thorough feedback.

Copy link
Contributor

@mwtoews mwtoews left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks for the spare review time, only a few remarks.

flopy/utils/crs.py Outdated Show resolved Hide resolved
autotest/test_export.py Outdated Show resolved Hide resolved
autotest/test_export.py Outdated Show resolved Hide resolved
flopy/utils/crs.py Show resolved Hide resolved
flopy/utils/crs.py Outdated Show resolved Hide resolved
@aleaf
Copy link
Contributor Author

aleaf commented Apr 26, 2023

thanks @mwtoews, I think I've addressed all of your comments. @langevin-usgs @jdhughes-usgs what else needs to happen to get this merged? Thanks.

Copy link
Contributor

@langevin-usgs langevin-usgs left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks for this @aleaf. This looks to be a very nice improvement.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

4 participants