Merging geospatial data in JS
npm install spatialmergeA (relatively) fast library for spatial joining and merging data in JavaScript.
The library is largely influenced by the geopandas merge and sjoin methods. Just as geopandas, spatialmerge utilizes a static spatial index provided by Flatbush (R-tree) to narrow down the number of features to test for intersection.
``js
import { merge, sjoin } from 'spatialmerge'
// join the properties of a spatial dataset (GeoJSON FeatureCollection) with a
// non-spatial dataset (e.g. contents of a CSV file parsed using d3-dsv)
// based on a common variable
const resultsMerge = merge(countryShapes, countryNames, { on: 'iso_a3' })
// join the properties of two spatial datasets (GeoJSON FeatureCollections)
const mergeSjoin = sjoin(citiesPoints, countryShapes)
`
Working examples, and an in-depth explanation of the two functions can be found in the user guide notebook.
shell
npm install spatialmerge
or
yarn add spatialmerge
`For vanilla HTML in modern browsers, import
spatialmerge from Skypack:`html
`For legacy environments, you can load
spatialmerge’s UMD bundle from an npm-based CDN such as jsDelivr; a spatialmerge global is exported:`html
`User Guide
The User Guide is hosted as an interactive ObservableHQ notebook
https://observablehq.com/@chrispahm/hello-spatialmerge
API reference
##### spatialmerge.merge(leftFC, rightFC_or_arrayOfObjects, options = { on: \, mutate: false }] )
Join the attributes of a GeoJSON FeatureCollection with an array of objects or another GeoJSON FeatureCollection based on a common variable (object key).
Parameters:
- leftFC: \ , required
- rightFC_or_arrayOfObjects: \ OR \ , required
- options: \
- on: \, required
The key to join the two collections on.
- mutate: \, default: false
Allows GeoJSON input to be mutated (significant performance increase if true)
##### spatialmerge.sjoin(leftFC, rightFC[, options = { how: 'inner', op: 'intersects', matches: 'all', lsuffix: 'left', rsuffix: 'right' }])
Spatial join of two GeoJSON FeatureCollections.
See the User Guide for details.
Parameters:
- leftFC, rightFC: \ , required
- options: \
- how: \, default: 'inner'
The type of join:
- ‘left’: use keys from left_df; retain only left_df geometry column
- ‘right’: use keys from right_df; retain only right_df geometry column
- ‘inner’: use intersection of keys from both dfs; retain only left_df geometry column
- op: \, default: 'intersects'
Binary predicate. Internally uses the corresponding turf.js modules.
- 'intersects'
- 'contains'
- 'within'
- 'crosses'
- 'overlaps'
- matches: \, default: 'all'
Whether to output all results of the join operation, or only the first.
- 'all'
- 'first'
- lsuffix: \, default: 'left'
Suffix to apply to overlapping column names (left GeoJSON).
- rsuffix: \, default: 'right'
Suffix to apply to overlapping column names (right GeoJSON).
- inclLeftIndex: \, default: false
Whether to include the left index as a property value in the resulting GeoJSON FeatureCollection.
Performance
Spatially merging datasets is (almost) always a computationally intensive task. If you plan to use
spatialmerge` on the client side or in a Node.js / Deno server, be sure to wrap it in a WebWorker or worker_thread to avoid blocking the Rendering / Event Loop. Resources:
- https://www.smashingmagazine.com/2021/06/web-workers-2021/
- https://github.com/GoogleChromeLabs/comlink
- https://github.com/josdejong/workerpool
- Fix tests for sjoin including large files, potentially using git-lfs
- Example using WebWorker
- Performance comparison with @turf/tag and geopandas
Contribution is highly appreciated 👍
Please open an issue in case of questions / bug reports or a pull request if you implemented a new feature / bug fix.
In the latter case, please make sure to run npm test (and adapt test/test.js to your changes) and / or update the README 🙂
MIT @Christoph Pahmeyer