PostGIS Migration Notes

This project is PostGIS-first for production spatial workflows while still supporting local SpatiaLite fallback when no DATABASE_URL is set.

Current Database Strategy

Runtime selection in landtool/settings.py:

  1. DATABASE_URL (or test DB override) -> GeoDjango PostGIS backend
  2. otherwise -> SpatiaLite fallback

For tests, precedence is:

  1. TEST_DATABASE_URL
  2. TEST_USE_DATABASE_URL=True with DATABASE_URL
  3. local SpatiaLite test DB (db.test.sqlite3)

Default behavior with TEST_DATABASE_URL is Django-managed create/drop test databases. Legacy reuse mode (migrate + flush on existing DB) is only enabled when TEST_REUSE_EXISTING_DB=True.

When using PostGIS with Django-managed create/drop tests, the test connection may need superuser privileges because CREATE EXTENSION postgis is executed in fresh test databases.

Why PostGIS Is Preferred

PostGIS enables native, scalable spatial operations used by this app:

  • viewport grid summaries (centroid bucketing)
  • robust geometry predicates for selection
  • server-side area calculations in projected CRS
  • better performance for larger parcel sets

Required Spatial Tooling

Besides database extensions, upload/export workflows require:

  • ogr2ogr
  • ogrinfo (GeoPackage layer inspection)

Verifying Active Backend

Use:

uv run python manage.py shell

Then inspect:

from django.conf import settings
print(settings.DATABASES["default"]["ENGINE"])

Expected for PostGIS runs:

  • django.contrib.gis.db.backends.postgis

Operational Recommendation

Use PostGIS in shared environments (staging/production) and for any heavy spatial workflow. Reserve SpatiaLite fallback mainly for lightweight local/dev/testing contexts.