The short answer

Documenting CRS assumptions means writing down — in a place that travels with the data — exactly what spatial reference each layer is in, how it got there, and what was assumed along the way. At minimum that is: the EPSG code and datum, horizontal units, vertical datum and units for any elevation data, the transformation used to bring the layer into the project (with its accuracy), and whether each step was an assign or a reproject. Done well, another analyst can reconstruct your coordinate chain and judge whether your measurements are trustworthy; done poorly, every downstream number is unverifiable.

Why a CRS needs documenting at all

An EPSG code alone is not the whole story. A layer "in EPSG:4326" still leaves open which datum realisation (WGS 84 has several, and ETRS89 has drifted from it by ~80 cm since 1989), what transformation was applied to align it with other data, and — for heights — which vertical datum. These are the assumptions that determine whether two layers agree to the centimetre or differ by metres. Software records the declared CRS but almost never records the choices a human made: which transformation pipeline was selected, why a layer was assigned rather than reprojected, what the source actually was. Those choices are the part worth documenting.

The minimum fields to record per layer

Treat this as a row in a table, one per layer:

  • Layer name and role (source, intermediate, deliverable).
  • Source CRS — EPSG code and datum, as received. Note "unknown" honestly when it is unknown.
  • Current/project CRS — EPSG code and datum after any processing.
  • Operation to reach itassigned (label changed, coordinates untouched) or reprojected (coordinates recomputed), and the date.
  • Datum transformation — the PROJ operation/pipeline and grid-shift files used, plus stated accuracy in metres.
  • Horizontal units — degrees, metres, US survey feet (the survey-foot vs international-foot distinction matters in US state plane work).
  • Vertical datum and units — ellipsoidal vs orthometric, the geoid model (EGM2008, a national geoid) or tidal datum, and units.
  • Area of use — confirmation the CRS's valid extent covers the data.
  • Provenance — source dataset, version/date, and the contact or download URL.

Where the documentation should live

Put it in two places, because they serve different readers.

Machine-readable, embedded with the data — so the engine and the next tool read it correctly:

  • Shapefile: a correct .prj (WKT). Remember shapefiles store no EPSG code, only WKT, so verify GDAL resolves it: gdalsrsinfo -o epsg layer.prj.
  • GeoPackage: the gpkg_spatial_ref_sys table plus per-layer SRS; richer than a .prj and a better default container.
  • PostGIS: the spatial_ref_sys table and each geometry column's SRID; verify with Find_SRID() and ST_SRID().
  • GeoTIFF: embedded CRS in the header, readable via gdalinfo.

Human-readable, travelling with the deliverable — so a reviewer understands the choices:

  • An ISO 19115 / 19139 metadata record is the formal standard and supports a reference-system section; QGIS can author and export it. The OGC/INSPIRE world expects this for published data.
  • For internal work, a README.md or a crs_log.csv in the project folder, or a metadata table in the database, is often enough — provided it is kept current and stored beside the data.

Worked example: capturing the transformation

Suppose you receive parcels on NAD27 (EPSG:4267) and must work in NAD83 / UTM 14N (EPSG:26914). Before reprojecting, inspect the operation PROJ will use:

projinfo -s EPSG:4267 -t EPSG:26914 -o PROJ --summary

The output names the candidate operations and their accuracy. A NADCON5 grid-based operation might offer ~0.1 m accuracy; a fallback 3-parameter shift might offer only ~5 m. Pin the chosen one in QGIS (Settings ▸ Options ▸ Transformations, or per-layer in the reprojection dialog) and then record exactly what you used:

parcels:
  source_crs: EPSG:4267 (NAD27)
  target_crs: EPSG:26914 (NAD83 / UTM 14N)
  operation: NADCON5 (US grid), via PROJ pipeline
  stated_accuracy_m: 0.1
  step: reprojected 2026-06-15
  units_horizontal: metre

A reviewer can now rerun projinfo and reproduce your numbers. Without the operation and accuracy, a 5 m fallback could have been used and nobody would know.

Documenting vertical assumptions

Heights are where undocumented assumptions do the most damage, because the horizontal CRS is silent about them. State explicitly whether elevations are ellipsoidal (e.g. heights above the WGS 84 ellipsoid) or orthometric (above a geoid such as EGM2008 or a national datum like NAVD88), the units, and any geoid grid applied. The undulation between ellipsoid and geoid reaches tens of metres, so "DEM in metres, EGM2008 orthometric heights" and "DEM in metres, ellipsoidal heights" are different datasets that look identical in a viewer.

Common pitfalls and why they happen

  • Documenting the declared CRS but not the true CRS. People copy the .prj into the notes without verifying the coordinates actually match it, propagating a wrong declaration into the record.
  • Recording "WGS 84" with no transformation. Hides whether a datum shift was skipped (a null transform), which can leave a metre-scale offset undocumented.
  • Storing the docs away from the data. A perfect metadata file on someone's laptop does not travel with the GeoPackage you ship.
  • Omitting whether a step was assign or reproject. Without it, a reviewer cannot tell whether geometry was preserved or recomputed.
  • Ignoring the area of use. A CRS used outside its valid extent can carry large, silent distortion that the EPSG code alone does not flag.

QA and validation

  • Verify the embedded CRS resolves to the code you recorded (gdalsrsinfo -o epsg).
  • Reproject one control point with the documented operation and confirm it lands on its known coordinates within the stated accuracy.
  • Confirm the documentation ships inside the deliverable container or alongside it, not only in a private location.
  • For elevation deliverables, confirm the vertical datum line is present and specific.

Bathyl perspective

Every dataset we hand over carries a one-page CRS record: per-layer source CRS, project CRS, the exact transformation and its accuracy, units, and vertical datum. It costs minutes to write and saves the next team the hour-long forensic exercise of reverse-engineering what we assumed.

Related reading

Sources