{"id":47963844,"url":"https://github.com/jarmak-personal/vibespatial","last_synced_at":"2026-04-21T00:01:34.476Z","repository":{"id":345008667,"uuid":"1177440963","full_name":"jarmak-personal/vibeSpatial","owner":"jarmak-personal","description":"GPU-first spatial analytics for Python. Drop-in GeoPandas replacement powered by runtime-compiled CUDA kernels","archived":false,"fork":false,"pushed_at":"2026-04-19T20:08:28.000Z","size":16581,"stargazers_count":0,"open_issues_count":0,"forks_count":0,"subscribers_count":0,"default_branch":"main","last_synced_at":"2026-04-19T22:10:51.812Z","etag":null,"topics":["cccl","cuda","geodataframe","geopandas","geospatial","gpu","gpu-computing","nvrtc","python","spatial-analytics"],"latest_commit_sha":null,"homepage":"https://jarmak-personal.github.io/vibeSpatial/","language":"Python","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"apache-2.0","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/jarmak-personal.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,"zenodo":null,"notice":null,"maintainers":null,"copyright":null,"agents":"AGENTS.md","dco":null,"cla":null}},"created_at":"2026-03-10T02:59:18.000Z","updated_at":"2026-04-19T20:08:33.000Z","dependencies_parsed_at":null,"dependency_job_id":"af6f79a5-aa59-4a36-9647-de4e040be8dd","html_url":"https://github.com/jarmak-personal/vibeSpatial","commit_stats":null,"previous_names":["jarmak-personal/vibespatial"],"tags_count":14,"template":false,"template_full_name":null,"purl":"pkg:github/jarmak-personal/vibeSpatial","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/jarmak-personal%2FvibeSpatial","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/jarmak-personal%2FvibeSpatial/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/jarmak-personal%2FvibeSpatial/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/jarmak-personal%2FvibeSpatial/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/jarmak-personal","download_url":"https://codeload.github.com/jarmak-personal/vibeSpatial/tar.gz/refs/heads/main","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/jarmak-personal%2FvibeSpatial/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":286080680,"owners_count":32071013,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2026-04-20T21:26:33.338Z","status":"ssl_error","status_checked_at":"2026-04-20T21:26:22.081Z","response_time":94,"last_error":"SSL_connect returned=1 errno=0 peeraddr=140.82.121.6:443 state=error: unexpected eof while reading","robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":false,"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":["cccl","cuda","geodataframe","geopandas","geospatial","gpu","gpu-computing","nvrtc","python","spatial-analytics"],"created_at":"2026-04-04T10:14:42.562Z","updated_at":"2026-04-21T00:01:34.466Z","avatar_url":"https://github.com/jarmak-personal.png","language":"Python","funding_links":[],"categories":[],"sub_categories":[],"readme":"# vibeSpatial\n\nvibeSpatial is a **GPU-first spatial analytics library** for Python.  Change\none import line and your existing GeoPandas code runs on CUDA — binary\npredicates, buffer, overlay, dissolve, make-valid, spatial joins, and I/O all\ndispatch to GPU kernels automatically, with **explicit, observable** CPU\ncompatibility fallback only when the native GPU path is unavailable or\nunsupported.\n\n\u003e [!WARNING]\n\u003e vibeSpatial is still early, but the public GPU path is now the design center:\n\u003e the April 20, 2026 local GPU health gate reports **95.09% value-weighted\n\u003e GPU acceleration** across tracked public dispatches. [File an issue](https://github.com/jarmak-personal/vibeSpatial/issues)\n\u003e if you hit a fallback, correctness mismatch, or unexpected host transfer.\n\u003e\n\u003e The repository enforces fallback observability: once a workflow is on device,\n\u003e hidden host exits are treated as bugs, and strict-native tests fail if a path\n\u003e materializes to host without first recording an explicit fallback or\n\u003e compatibility boundary. The maintained warmed `10k` public shootout suite\n\u003e under [`benchmarks/shootout/`](benchmarks/shootout/) currently passes with\n\u003e matching fingerprints on local RTX 4090 runs; heavier workflows show clear\n\u003e wins while tiny CPU-shaped workflows are treated as crossover signals rather\n\u003e than benchmark theater.\n\n### Install\n\n```bash\npip install vibespatial              # CPU-only (GeoPandas drop-in)\npip install vibespatial[cu12]        # CUDA 12 GPU acceleration\npip install vibespatial[cu13]        # CUDA 13 GPU acceleration\n```\n\n### Quick start\n\n```python\nimport vibespatial as gpd\n\ngdf = gpd.read_file(\"my_data.gpkg\")\nbuffered = gdf.buffer(100)\njoined = gpd.sjoin(gdf, buffered)\ngdf.to_parquet(\"out.parquet\")\n```\n\n### Real-world example: 7.2 million buildings\n\nLoad every building footprint in Florida, reproject to UTM, find all buildings\nwithin 1 km of a random pick, and export to GeoParquet.  The full script is\nat [`examples/nearby_buildings.py`](examples/nearby_buildings.py).\n\n```python\nimport vibespatial as gpd\n\n# Read 7.2M buildings from Microsoft US Building Footprints\ngdf = gpd.read_file(\"Florida.geojson\")\n\n# Reproject to UTM for metric distances\ngdf_utm = gdf.to_crs(gdf.geometry.estimate_utm_crs())\n\n# Pick a random building and find everything within 1 km\nseed = gdf_utm.geometry.iloc[random.randrange(len(gdf_utm))]\nnearby = gdf_utm[gdf_utm.geometry.dwithin(seed.centroid, 1_000)]\n\n# Export to GeoParquet\nnearby.to_crs(epsg=4326).to_parquet(\"nearby_buildings.parquet\")\n```\n\n**vibeSpatial is a drop-in replacement for GeoPandas.** Here is the only diff:\n\n```diff\n-import geopandas as gpd\n+import vibespatial as gpd\n\n gdf = gpd.read_file(\"Florida.geojson\")\n gdf_utm = gdf.to_crs(gdf.geometry.estimate_utm_crs())\n seed = gdf_utm.geometry.iloc[random.randrange(len(gdf_utm))]\n nearby = gdf_utm[gdf_utm.geometry.dwithin(seed.centroid, 1_000)]\n nearby.to_crs(epsg=4326).to_parquet(\"nearby_buildings.parquet\")\n```\n\n**Performance on 7.2M polygons (GeoPandas CPU baseline vs current public\nvibeSpatial run on local RTX 4090 / i9-13900K):**\n\n| Step | GeoPandas | vibeSpatial | Speedup |\n|---|---|---|---|\n| Read GeoJSON | 57.7 s | 6.7 s | **8.6x** |\n| Reproject to UTM | 8.2 s | 0.1 s | **82x** |\n| Select within 1 km | 0.2 s | 0.2 s | 1.0x |\n| **End-to-end including GeoParquet export** | **66.3 s** | **8.0 s** | **8.3x** |\n\nThe vibeSpatial column is the public\n[`examples/nearby_buildings.py`](examples/nearby_buildings.py) path, not a\nprivate benchmark hook. GeoJSON reading uses GPU byte-classification: NVRTC\nkernels parse JSON structure, detect geometry families, extract coordinates,\nand assemble geometry into owned device buffers. Property payloads are decoded\nthrough a narrowed host seam. Reprojection uses\n[vibeProj](https://github.com/jarmak-personal/vibeProj) fused GPU kernels via\n`transform_buffers()` -- no host round-trip. Spatial queries use\ndevice-resident bounding-box prefilter + GPU distance kernels.\n\n### Current GPU coverage\n\nThe April 20, 2026 local GPU health gate reports **95.09% value-weighted\nGPU acceleration** across tracked public dispatches:\n\n| Surface | GPU work coverage |\n|---|---:|\n| I/O write | 99.88% |\n| Query | 95.51% |\n| I/O read | 94.71% |\n| Other public APIs | 94.48% |\n| Constructive | 85.92% |\n| Overlay | 76.14% |\n| Dissolve | 54.43% |\n\nThe remaining work is concentrated in exact constructive/overlay/dissolve\npaths and uncommon compatibility boundaries. Silent CPU fallback is not an\naccepted success mode.\n\n### Tech stack\n\n| Layer | Technology |\n|---|---|\n| GPU kernels | NVRTC (runtime-compiled CUDA C via `cuda-python`) |\n| GPU primitives | CCCL (`cccl` — scan, sort, reduce, select) |\n| GPU arrays | CuPy (device memory, element-wise ops, prefix sums) |\n| GPU JSON parse | Custom byte-classification kernels (ADR-0038) |\n| GPU projection | [vibeProj](https://github.com/jarmak-personal/vibeProj) |\n| GPU Parquet/Arrow | pylibcudf (WKB decode, GeoArrow codec) |\n| CPU compatibility | GeoPandas API (vendored upstream test suite) |\n| JSON parsing | orjson (property extraction) |\n| File I/O | native GPU/hybrid routes for GeoJSON, Shapefile, FlatGeobuf, GeoJSONSeq, OSM PBF; pyogrio for GDAL compatibility |\n| Packaging | uv, hatchling |\n\nAll GPU kernels are **pure Python** — CUDA C source strings compiled at\nruntime via NVRTC with background warmup (ADR-0034).  Compiled CUBINs are\ncached on disk so the JIT cost is paid only once per install.  No compiled\nextensions, no `nvcc` build step.  The entire suite ships as pure-Python\nwheels:\n\n| Package | Wheel size |\n|---|---|\n| vibespatial | 612 KB |\n| vibeproj | 57 KB |\n| vibespatial-raster | 51 KB |\n| **Total** | **720 KB** |\n\n### Pre-compilation\n\nThe first time a GPU operation runs, CUDA kernels are JIT-compiled in the\nbackground (~2-3 s wall time on 8 threads).  Compiled CUBINs are cached on\ndisk so subsequent process starts are near-instant.  To pre-populate the\ncaches (e.g. in CI or after install):\n\n```python\nfrom vibespatial.cccl_precompile import precompile_all\nprecompile_all()  # compiles all 21 CCCL specs + 61 NVRTC kernels, blocks until done\n```\n\nOr from the command line:\n\n```bash\nuv run python -c \"from vibespatial.cccl_precompile import precompile_all; precompile_all()\"\n```\n\nSee [GPU Kernel Caching](docs/architecture/gpu-kernel-caching.md) for the\nfull design and environment variables.\n\n### Documentation\n\nSee the [documentation](https://vibespatial.github.io/vibeSpatial/) for the\nfull API reference, GPU acceleration guide, and I/O format support matrix.\n\n---\n\n## Contributing\n\n```bash\nuv sync --group dev\nuv run python scripts/check_docs.py --refresh\nuv run python scripts/vendor_geopandas_tests.py\nuv run pytest tests/upstream/geopandas/tests/test_config.py\n```\n\n### Dependency groups\n\n- `dev`: local development and pytest tooling\n- `upstream-optional`: heavier I/O and visualization extras for broader coverage\n- `gpu-optional`: CUDA runtime, CuPy, pylibcudf\n\n### Layout\n\n- `src/vibespatial/`: package code\n- `src/geopandas/`: GeoPandas compatibility shim\n- `tests/`: repo-owned tests\n- `tests/upstream/geopandas/`: vendored upstream GeoPandas test suite\n- `docs/`: architecture docs and ADRs\n- `examples/`: benchmarks and usage examples\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fjarmak-personal%2Fvibespatial","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fjarmak-personal%2Fvibespatial","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fjarmak-personal%2Fvibespatial/lists"}