{"id":13688974,"url":"https://github.com/mdbartos/pysheds","last_synced_at":"2025-08-13T10:55:33.559Z","repository":{"id":43669620,"uuid":"88182854","full_name":"mdbartos/pysheds","owner":"mdbartos","description":":earth_americas: Simple and fast watershed delineation in python.","archived":false,"fork":false,"pushed_at":"2024-07-26T19:56:46.000Z","size":15213,"stargazers_count":806,"open_issues_count":92,"forks_count":215,"subscribers_count":28,"default_branch":"master","last_synced_at":"2025-08-10T00:38:38.490Z","etag":null,"topics":["accumulation","catchments","digital-elevation-model","flow-direction","gis","hydrology"],"latest_commit_sha":null,"homepage":"","language":"Python","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"gpl-3.0","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/mdbartos.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null}},"created_at":"2017-04-13T16:02:37.000Z","updated_at":"2025-08-07T08:57:26.000Z","dependencies_parsed_at":"2023-12-11T22:03:43.849Z","dependency_job_id":"474bbc6e-d11e-4f97-97b5-1ba758048b72","html_url":"https://github.com/mdbartos/pysheds","commit_stats":{"total_commits":416,"total_committers":11,"mean_commits":37.81818181818182,"dds":"0.14903846153846156","last_synced_commit":"4030e60e1555b7b639de1ce2eeda50a7df919fd5"},"previous_names":[],"tags_count":9,"template":false,"template_full_name":null,"purl":"pkg:github/mdbartos/pysheds","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/mdbartos%2Fpysheds","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/mdbartos%2Fpysheds/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/mdbartos%2Fpysheds/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/mdbartos%2Fpysheds/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/mdbartos","download_url":"https://codeload.github.com/mdbartos/pysheds/tar.gz/refs/heads/master","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/mdbartos%2Fpysheds/sbom","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":269793947,"owners_count":24476730,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","status":"online","status_checked_at":"2025-08-10T02:00:08.965Z","response_time":71,"last_error":null,"robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":true,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["accumulation","catchments","digital-elevation-model","flow-direction","gis","hydrology"],"created_at":"2024-08-02T15:01:29.385Z","updated_at":"2025-08-13T10:55:33.483Z","avatar_url":"https://github.com/mdbartos.png","language":"Python","funding_links":[],"categories":["Python","Access and Monitoring of Resources","Natural Resources"],"sub_categories":["Water","Water Supply and Quality"],"readme":"# pysheds [![Build Status](https://github.com/mdbartos/pysheds/actions/workflows/python-package.yml/badge.svg)](https://github.com/mdbartos/pysheds/actions) [![Coverage Status](https://coveralls.io/repos/github/mdbartos/pysheds/badge.svg?branch=master\u0026service=github)](https://coveralls.io/github/mdbartos/pysheds?branch=master) [![Python Versions](https://img.shields.io/pypi/pyversions/pysheds)](https://pypi.python.org/pypi/pysheds)\n🌎 Simple and fast watershed delineation in python.\n\n## Documentation\n\nRead the docs [here 📖](https://mdbartos.github.io/pysheds).\n\n## Media\n\n*Hatari Labs* - [Elevation model conditioning and stream network delineation with python and pysheds](https://www.hatarilabs.com/ih-en/elevation-model-conditioning-and-stream-network-delimitation-with-python-and-pysheds-tutorial) \u003csup\u003e:uk:\u003c/sup\u003e\n\n*Hatari Labs* - [Watershed and stream network delineation with python and pysheds](https://www.hatarilabs.com/ih-en/watershed-and-stream-network-delimitation-with-python-and-pysheds-tutorial) \u003csup\u003e:uk:\u003c/sup\u003e\n\n*Gidahatari* - [Delimitación de límite de cuenca y red hidrica con python y pysheds](http://gidahatari.com/ih-es/delimitacion-de-limite-de-cuenca-y-red-hidrica-con-python-y-pysheds-tutorial) \u003csup\u003e:es:\u003c/sup\u003e\n\n*Earth Science Information Partners* - [Pysheds: a fast, open-source digital elevation model processing library](https://www.esipfed.org/student-fellow-blog/pysheds-a-fast-open-source-digital-elevation-model-processing-library) \u003csup\u003e:uk:\u003c/sup\u003e\n\n## Example usage\n\nExample data used in this tutorial are linked below:\n\n  - Elevation: [elevation.tiff](https://pysheds.s3.us-east-2.amazonaws.com/data/elevation.tiff)\n  - Terrain: [impervious_area.zip](https://pysheds.s3.us-east-2.amazonaws.com/data/impervious_area.zip)\n  - Soil Polygons: [soils.zip](https://pysheds.s3.us-east-2.amazonaws.com/data/soils.zip)\n  \nAdditional DEM datasets are available via the [USGS HydroSHEDS](https://www.hydrosheds.org/) project.\n\n### Read DEM data\n\n```python\n# Read elevation raster\n# ----------------------------\nfrom pysheds.grid import Grid\n\ngrid = Grid.from_raster('elevation.tiff')\ndem = grid.read_raster('elevation.tiff')\n```\n\n\u003cdetails\u003e\n\u003csummary\u003ePlotting code...\u003c/summary\u003e\n\u003cp\u003e\n\n```python\nimport numpy as np\nimport matplotlib.pyplot as plt\nfrom matplotlib import colors\nimport seaborn as sns\n\nfig, ax = plt.subplots(figsize=(8,6))\nfig.patch.set_alpha(0)\n\nplt.imshow(dem, extent=grid.extent, cmap='terrain', zorder=1)\nplt.colorbar(label='Elevation (m)')\nplt.grid(zorder=0)\nplt.title('Digital elevation map', size=14)\nplt.xlabel('Longitude')\nplt.ylabel('Latitude')\nplt.tight_layout()\n```\n\n\u003c/p\u003e\n\u003c/details\u003e\n\n![Example 1](https://pysheds.s3.us-east-2.amazonaws.com/img/dem.png)\n\n### Condition the elevation data\n\n```python\n# Condition DEM\n# ----------------------\n# Fill pits in DEM\npit_filled_dem = grid.fill_pits(dem)\n\n# Fill depressions in DEM\nflooded_dem = grid.fill_depressions(pit_filled_dem)\n    \n# Resolve flats in DEM\ninflated_dem = grid.resolve_flats(flooded_dem)\n```\n\n### Elevation to flow direction\n\n```python\n# Determine D8 flow directions from DEM\n# ----------------------\n# Specify directional mapping\ndirmap = (64, 128, 1, 2, 4, 8, 16, 32)\n    \n# Compute flow directions\n# -------------------------------------\nfdir = grid.flowdir(inflated_dem, dirmap=dirmap)\n```\n\n\u003cdetails\u003e\n\u003csummary\u003ePlotting code...\u003c/summary\u003e\n\u003cp\u003e\n\n```python\nfig = plt.figure(figsize=(8,6))\nfig.patch.set_alpha(0)\n\nplt.imshow(fdir, extent=grid.extent, cmap='viridis', zorder=2)\nboundaries = ([0] + sorted(list(dirmap)))\nplt.colorbar(boundaries= boundaries,\n             values=sorted(dirmap))\nplt.xlabel('Longitude')\nplt.ylabel('Latitude')\nplt.title('Flow direction grid', size=14)\nplt.grid(zorder=-1)\nplt.tight_layout()\n```\n\n\u003c/p\u003e\n\u003c/details\u003e\n\n![Example 2](https://pysheds.s3.us-east-2.amazonaws.com/img/fdir.png)\n\n### Compute accumulation from flow direction\n\n```python\n# Calculate flow accumulation\n# --------------------------\nacc = grid.accumulation(fdir, dirmap=dirmap)\n```\n\n\u003cdetails\u003e\n\u003csummary\u003ePlotting code...\u003c/summary\u003e\n\u003cp\u003e\n\n```python\nfig, ax = plt.subplots(figsize=(8,6))\nfig.patch.set_alpha(0)\nplt.grid('on', zorder=0)\nim = ax.imshow(acc, extent=grid.extent, zorder=2,\n               cmap='cubehelix',\n               norm=colors.LogNorm(1, acc.max()),\n               interpolation='bilinear')\nplt.colorbar(im, ax=ax, label='Upstream Cells')\nplt.title('Flow Accumulation', size=14)\nplt.xlabel('Longitude')\nplt.ylabel('Latitude')\nplt.tight_layout()\n```\n\n\u003c/p\u003e\n\u003c/details\u003e\n\n![Example 4](https://pysheds.s3.us-east-2.amazonaws.com/img/acc.png)\n\n\n### Delineate catchment from flow direction\n\n```python\n# Delineate a catchment\n# ---------------------\n# Specify pour point\nx, y = -97.294, 32.737\n\n# Snap pour point to high accumulation cell\nx_snap, y_snap = grid.snap_to_mask(acc \u003e 1000, (x, y))\n\n# Delineate the catchment\ncatch = grid.catchment(x=x_snap, y=y_snap, fdir=fdir, dirmap=dirmap, \n                       xytype='coordinate')\n\n# Crop and plot the catchment\n# ---------------------------\n# Clip the bounding box to the catchment\ngrid.clip_to(catch)\nclipped_catch = grid.view(catch)\n```\n\n\u003cdetails\u003e\n\u003csummary\u003ePlotting code...\u003c/summary\u003e\n\u003cp\u003e\n\n```python\n# Plot the catchment\nfig, ax = plt.subplots(figsize=(8,6))\nfig.patch.set_alpha(0)\n\nplt.grid('on', zorder=0)\nim = ax.imshow(np.where(clipped_catch, clipped_catch, np.nan), extent=grid.extent,\n               zorder=1, cmap='Greys_r')\nplt.xlabel('Longitude')\nplt.ylabel('Latitude')\nplt.title('Delineated Catchment', size=14)\n```\n\n\u003c/p\u003e\n\u003c/details\u003e\n\n![Example 3](https://pysheds.s3.us-east-2.amazonaws.com/img/catch.png)\n\n### Extract the river network\n\n```python\n# Extract river network\n# ---------------------\nbranches = grid.extract_river_network(fdir, acc \u003e 50, dirmap=dirmap)\n```\n\n\u003cdetails\u003e\n\u003csummary\u003ePlotting code...\u003c/summary\u003e\n\u003cp\u003e\n\n```python\nsns.set_palette('husl')\nfig, ax = plt.subplots(figsize=(8.5,6.5))\n\nplt.xlim(grid.bbox[0], grid.bbox[2])\nplt.ylim(grid.bbox[1], grid.bbox[3])\nax.set_aspect('equal')\n\nfor branch in branches['features']:\n    line = np.asarray(branch['geometry']['coordinates'])\n    plt.plot(line[:, 0], line[:, 1])\n    \n_ = plt.title('D8 channels', size=14)\n```\n\n\u003c/p\u003e\n\u003c/details\u003e\n\n![Example 6](https://pysheds.s3.us-east-2.amazonaws.com/img/river.png)\n\n### Compute flow distance from flow direction\n\n```python\n# Calculate distance to outlet from each cell\n# -------------------------------------------\ndist = grid.distance_to_outlet(x=x_snap, y=y_snap, fdir=fdir, dirmap=dirmap,\n                               xytype='coordinate')\n```\n\n\u003cdetails\u003e\n\u003csummary\u003ePlotting code...\u003c/summary\u003e\n\u003cp\u003e\n\n```python\nfig, ax = plt.subplots(figsize=(8,6))\nfig.patch.set_alpha(0)\nplt.grid('on', zorder=0)\nim = ax.imshow(dist, extent=grid.extent, zorder=2,\n               cmap='cubehelix_r')\nplt.colorbar(im, ax=ax, label='Distance to outlet (cells)')\nplt.xlabel('Longitude')\nplt.ylabel('Latitude')\nplt.title('Flow Distance', size=14)\n```\n\n\u003c/p\u003e\n\u003c/details\u003e\n\n![Example 5](https://pysheds.s3.us-east-2.amazonaws.com/img/dist.png)\n\n### Add land cover data\n\n```python\n# Combine with land cover data\n# ---------------------\nterrain = grid.read_raster('impervious_area.tiff', window=grid.bbox,\n                           window_crs=grid.crs, nodata=0)\n# Reproject data to grid's coordinate reference system\nprojected_terrain = terrain.to_crs(grid.crs)\n# View data in catchment's spatial extent\ncatchment_terrain = grid.view(projected_terrain, nodata=np.nan)\n```\n\n\u003cdetails\u003e\n\u003csummary\u003ePlotting code...\u003c/summary\u003e\n\u003cp\u003e\n\n```python\nfig, ax = plt.subplots(figsize=(8,6))\nfig.patch.set_alpha(0)\nplt.grid('on', zorder=0)\nim = ax.imshow(catchment_terrain, extent=grid.extent, zorder=2,\n               cmap='bone')\nplt.colorbar(im, ax=ax, label='Percent impervious area')\nplt.xlabel('Longitude')\nplt.ylabel('Latitude')\nplt.title('Percent impervious area', size=14)\n```\n\n\u003c/p\u003e\n\u003c/details\u003e\n\n![Example 7](https://pysheds.s3.us-east-2.amazonaws.com/img/terrain.png)\n\n### Add vector data\n\n```python\n# Convert catchment raster to vector and combine with soils shapefile\n# ---------------------\n# Read soils shapefile\nimport pandas as pd\nimport geopandas as gpd\nfrom shapely import geometry, ops\nsoils = gpd.read_file('soils.shp')\nsoil_id = 'MUKEY'\n# Convert catchment raster to vector geometry and find intersection\nshapes = grid.polygonize()\ncatchment_polygon = ops.unary_union([geometry.shape(shape)\n                                     for shape, value in shapes])\nsoils = soils[soils.intersects(catchment_polygon)]\ncatchment_soils = gpd.GeoDataFrame(soils[soil_id], \n                                   geometry=soils.intersection(catchment_polygon))\n# Convert soil types to simple integer values\nsoil_types = np.unique(catchment_soils[soil_id])\nsoil_types = pd.Series(np.arange(soil_types.size), index=soil_types)\ncatchment_soils[soil_id] = catchment_soils[soil_id].map(soil_types)\n```\n\n\u003cdetails\u003e\n\u003csummary\u003ePlotting code...\u003c/summary\u003e\n\u003cp\u003e\n\n```python\nfig, ax = plt.subplots(figsize=(8, 6))\ncatchment_soils.plot(ax=ax, column=soil_id, categorical=True, cmap='terrain',\n                     linewidth=0.5, edgecolor='k', alpha=1, aspect='equal')\nax.set_xlim(grid.bbox[0], grid.bbox[2])\nax.set_ylim(grid.bbox[1], grid.bbox[3])\nplt.xlabel('Longitude')\nplt.ylabel('Latitude')\nax.set_title('Soil types (vector)', size=14)\n```\n\n\u003c/p\u003e\n\u003c/details\u003e\n\n![Example 8](https://pysheds.s3.us-east-2.amazonaws.com/img/poly.png)\n\n### Convert from vector to raster\n\n```python\nsoil_polygons = zip(catchment_soils.geometry.values, catchment_soils[soil_id].values)\nsoil_raster = grid.rasterize(soil_polygons, fill=np.nan)\n```\n\n\u003cdetails\u003e\n\u003csummary\u003ePlotting code...\u003c/summary\u003e\n\u003cp\u003e\n\n```python\nfig, ax = plt.subplots(figsize=(8, 6))\nplt.imshow(soil_raster, cmap='terrain', extent=grid.extent, zorder=1)\nboundaries = np.unique(soil_raster[~np.isnan(soil_raster)]).astype(int)\nplt.colorbar(boundaries=boundaries,\n             values=boundaries)\nax.set_xlim(grid.bbox[0], grid.bbox[2])\nax.set_ylim(grid.bbox[1], grid.bbox[3])\nplt.xlabel('Longitude')\nplt.ylabel('Latitude')\nax.set_title('Soil types (raster)', size=14)\n```\n\n\u003c/p\u003e\n\u003c/details\u003e\n\n![Example 9](https://pysheds.s3.us-east-2.amazonaws.com/img/rasterize.png)\n\n## Features\n\n- Hydrologic Functions:\n  - `flowdir` : Generate a flow direction grid from a given digital elevation dataset.\n  - `catchment` : Delineate the watershed for a given pour point (x, y).\n  - `accumulation` : Compute the number of cells upstream of each cell; if weights are\n                given, compute the sum of weighted cells upstream of each cell.\n  - `distance_to_outlet` : Compute the (weighted) distance from each cell to a given\n                      pour point, moving downstream.\n  - `distance_to_ridge` : Compute the (weighted) distance from each cell to its originating\n                    drainage divide, moving upstream.\n  - `compute_hand` : Compute the height above nearest drainage (HAND).\n  - `stream_order` : Compute the (strahler) stream order.\n  - `extract_river_network` : Extract river segments from a catchment and return a geojson\n                        object.\n  - `extract_profiles` : Extract river segments and return a list of channel indices along with a dictionary describing connectivity.\n  - `cell_dh` : Compute the drop in elevation from each cell to its downstream neighbor.\n  - `cell_distances` : Compute the distance from each cell to its downstream neighbor.\n  - `cell_slopes` : Compute the slope between each cell and its downstream neighbor.\n  - `fill_pits` : Fill single-celled pits in a digital elevation dataset.\n  - `fill_depressions` : Fill multi-celled depressions in a digital elevation dataset.\n  - `resolve_flats` : Remove flats from a digital elevation dataset.\n  - `detect_pits` : Detect single-celled pits in a digital elevation dataset.\n  - `detect_depressions` : Detect multi-celled depressions in a digital elevation dataset.\n  - `detect_flats` : Detect flats in a digital elevation dataset.\n- Viewing Functions:\n  - `view` : Returns a \"view\" of a dataset defined by the grid's viewfinder.\n  - `clip_to` : Clip the viewfinder to the smallest area containing all non-\n          null gridcells for a provided dataset.\n  - `nearest_cell` : Returns the index (column, row) of the cell closest\n                to a given geographical coordinate (x, y).\n  - `snap_to_mask` : Snaps a set of points to the nearest nonzero cell in a boolean mask;\n                useful for finding pour points from an accumulation raster.\n- I/O Functions:\n  - `read_ascii`: Reads ascii gridded data.\n  - `read_raster`: Reads raster gridded data.\n  - `from_ascii` : Instantiates a grid from an ascii file.\n  - `from_raster` : Instantiates a grid from a raster file or Raster object.\n  - `to_ascii`: Write grids to delimited ascii files.\n  - `to_raster`: Write grids to raster files (e.g. geotiff).\n\n`pysheds` supports both D8 and D-infinity routing schemes.\n\n## Installation\n\n`pysheds` currently only supports Python 3.\n\n### Using pip\n\nYou can install `pysheds` using pip:\n\n```bash\n$ pip install pysheds\n```\n\n### Using anaconda\n\nFirst, add conda forge to your channels, if you have not already done so:\n\n```bash\n$ conda config --add channels conda-forge\n```\n\nThen, install pysheds:\n\n```bash\n$ conda install pysheds\n```\n### Installing from source\n\nFor the bleeding-edge version, you can install pysheds from this github repository.\n\n```bash\n$ git clone https://github.com/mdbartos/pysheds.git\n$ cd pysheds\n$ python setup.py install\n```\n\nor\n\n```bash\n$ git clone https://github.com/mdbartos/pysheds.git\n$ cd pysheds\n$ pip install .\n```\n\n# Performance\nPerformance benchmarks on a 2015 MacBook Pro (M: million, K: thousand):\n\n| Function                | Routing | Number of cells          | Run time |\n| ----------------------- | ------- | ------------------------ | -------- |\n| `flowdir`               | D8      |  36M                     | 1.14 [s] |\n| `flowdir`               | DINF    |  36M                     | 7.01 [s] |\n| `flowdir`               | MFD     |  36M                     | 4.21 [s] |\n| `accumulation`          | D8      |  36M                     | 3.44 [s] |\n| `accumulation`          | DINF    |  36M                     | 14.9 [s] |\n| `accumulation`          | MFD     |  36M                     | 32.5 [s] |\n| `catchment`             | D8      |  9.76M                   | 2.19 [s] |\n| `catchment`             | DINF    |  9.76M                   | 3.5  [s] |\n| `catchment`             | MFD     |  9.76M                   | 17.1 [s] |\n| `distance_to_outlet`    | D8      |  9.76M                   | 2.98 [s] |\n| `distance_to_outlet`    | DINF    |  9.76M                   | 5.49 [s] |\n| `distance_to_outlet`    | MFD     |  9.76M                   | 13.1 [s] |\n| `distance_to_ridge`     | D8      |  36M                     | 4.53 [s] |\n| `distance_to_ridge`     | DINF    |  36M                     | 14.5 [s] |\n| `distance_to_ridge`     | MFD     |  36M                     | 31.3 [s] |\n| `hand`                  | D8      |  36M total, 730K channel | 12.3 [s] |\n| `hand`                  | DINF    |  36M total, 770K channel | 15.8 [s] |\n| `hand`                  | MFD     |  36M total, 770K channel | 29.8 [s] |\n| `stream_order`          | D8      |  36M total, 1M channel   | 3.99 [s] |\n| `extract_river_network` | D8      |  36M total, 345K channel | 4.07 [s] |\n| `extract_profiles`      | D8      |  36M total, 345K channel | 2.89 [s] |\n| `detect_pits`           | N/A     |  36M                     | 1.80 [s] |\n| `detect_flats`          | N/A     |  36M                     | 1.84 [s] |\n| `fill_pits`             | N/A     |  36M                     | 2.52 [s] |\n| `fill_depressions`      | N/A     |  36M                     | 27.1 [s] |\n| `resolve_flats`         | N/A     |  36M                     | 9.56 [s] |\n| `cell_dh`               | D8      |  36M                     | 2.34 [s] |\n| `cell_dh`               | DINF    |  36M                     | 4.92 [s] |\n| `cell_dh`               | MFD     |  36M                     | 30.1 [s] |\n| `cell_distances`        | D8      |  36M                     | 1.11 [s] |\n| `cell_distances`        | DINF    |  36M                     | 2.16 [s] |\n| `cell_distances`        | MFD     |  36M                     | 26.8 [s] |\n| `cell_slopes`           | D8      |  36M                     | 4.01 [s] |\n| `cell_slopes`           | DINF    |  36M                     | 10.2 [s] |\n| `cell_slopes`           | MFD     |  36M                     | 58.7 [s] |\n\nSpeed tests were run on a conditioned DEM from the HYDROSHEDS DEM repository\n(linked above as `elevation.tiff`).\n\n# Citing\n\nIf you have used this codebase in a publication and wish to cite it, consider citing the zenodo repository:\n\n```bibtex\n@misc{bartos_2020,\n    title  = {pysheds: simple and fast watershed delineation in python},\n    author = {Bartos, Matt},\n    url    = {https://github.com/mdbartos/pysheds},\n    year   = {2020},\n    doi    = {10.5281/zenodo.3822494}\n}\n```\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fmdbartos%2Fpysheds","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fmdbartos%2Fpysheds","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fmdbartos%2Fpysheds/lists"}