Coordinates and srid 4326/25832
Find the coordinates in the response, choose between WGS84 and ETRS89/UTM32 with srid, reverse geocode in both systems, and convert yourself with pyproj or proj4.
Every access address has an access point: the coordinate of the entrance to the building. The API can return it in two coordinate systems, and you choose with the srid parameter. It is the same parameter as in DAWA.
The two systems
srid | System | Unit | Order | Example (Aarhus C) |
|---|---|---|---|---|
4326 (default) | WGS84, longitude and latitude | degrees | longitude, latitude | [10.20285443, 56.14811374] |
25832 | ETRS89 / UTM zone 32N | metres | east, north | [574730.16, 6223215.94] |
WGS84 is what GPS, Google Maps, Leaflet and most web maps use. ETRS89/UTM32 is the official Danish system, used by municipalities, GIS tools and the Danish Agency for Climate Data's map data. The advantage of UTM is that the coordinates are metres: the distance between two points is plain Pythagoras.
srid only accepts 4326 and 25832. Any other value gives 400 with type QueryParameterFormatError and the text "srid skal være 4326 (WGS84) eller 25832 (ETRS89/UTM32)".
Where the coordinates are in the response
| Response | Field |
|---|---|
/adgangsadresser, /adgangsadresser/{id}, /adgangsadresser/reverse (nested) | adgangspunkt.koordinater |
/adresser, /adresser/{id}, /adresser/reverse (nested) | adgangsadresse.adgangspunkt.koordinater |
struktur=mini | x, y |
struktur=flad | wgs84koordinat_længde, wgs84koordinat_bredde, etrs89koordinat_øst, etrs89koordinat_nord (always both systems) |
format=csv | wgs84koordinat_længde, wgs84koordinat_bredde, etrs89koordinat_øst, etrs89koordinat_nord (always both systems) |
format=geojson | geometry.coordinates (the system is stated in crs) |
/autocomplete | data.x, data.y |
koordinater is a list of two numbers, and the order is always [x, y]: longitude before latitude, or east before north. An adresse (unit) has no coordinate of its own. A flat on the 3rd floor has its access address's point.
/autocomplete follows srid too: with srid=25832, data.x and data.y are UTM metres instead of degrees.
Fetch the same address in both systems:
import os import requests API = "https://api.danadresse.dk" headers = {"X-Api-Key": os.environ["DANADRESSE_API_KEY"]} adresse_id = "0a3f50ae-b4ee-32b8-e044-0003ba298018" for srid, name in ((4326, "WGS84"), (25832, "ETRS89/UTM32")): r = requests.get(f"{API}/adresser/{adresse_id}", params={"srid": srid}, headers=headers, timeout=10) r.raise_for_status() x, y = r.json()["adgangsadresse"]["adgangspunkt"]["koordinater"] print(f"{name:13} x={x} y={y}")
WGS84 x=11.35623868 y=55.40464424 ETRS89/UTM32 x=649189.55 y=6142347.15
Axis order: the most common bug
The API gives [longitude, latitude], like GeoJSON. Many map libraries want it the other way round:
| Library | Expects |
|---|---|
| GeoJSON, OpenLayers, Mapbox GL, Turf | [longitude, latitude] |
Leaflet L.marker(), L.latLng() | [latitude, longitude] |
| Google Maps | { lat: latitude, lng: longitude } |
const [lon, lat] = adresse.adgangsadresse.adgangspunkt.koordinater; L.marker([lat, lon]).addTo(map); // Leaflet: latitude first
If your markers land in the Arabian Sea instead of Denmark, the axes are swapped.
Reverse geocoding with srid
/adgangsadresser/reverse and /adresser/reverse find the nearest address to a point. x and y are read in the system given by srid, and the response comes back in the same system:
curl -s "https://api.danadresse.dk/adgangsadresser/reverse?x=12.5683&y=55.6761" \ -H "X-Api-Key: $DANADRESSE_API_KEY"
With UTM coordinates you must set srid=25832:
curl -s "https://api.danadresse.dk/adgangsadresser/reverse?x=574730.16&y=6223215.94&srid=25832" \ -H "X-Api-Key: $DANADRESSE_API_KEY"
If you forget srid=25832 for UTM coordinates, or swap x and y, there is no address nearby and you get 404 with "title": "No address within range". See No results?
The same applies to cirkel= and polygon= on /adresser and /adgangsadresser: the coordinates are read in the system given by srid. The radius in cirkel is always metres.
Convert yourself
If you have coordinates in one system and need the other, convert locally instead of making extra calls. In Python with pyproj (pip install pyproj):
from pyproj import Transformer # always_xy=True means (longitude, latitude) in and (east, north) out, as in the API. to_utm = Transformer.from_crs("EPSG:4326", "EPSG:25832", always_xy=True) to_wgs84 = Transformer.from_crs("EPSG:25832", "EPSG:4326", always_xy=True) east, north = to_utm.transform(10.20285443, 56.14811374) print(f"UTM32: {east:.2f} {north:.2f}") lon, lat = to_wgs84.transform(east, north) print(f"WGS84: {lon:.8f} {lat:.8f}")
Without always_xy=True pyproj follows the EPSG definition of 4326, which is latitude before longitude. That is a classic source of swapped axes.
In JavaScript with proj4 (npm install proj4):
import proj4 from "proj4"; proj4.defs("EPSG:25832", "+proj=utm +zone=32 +ellps=GRS80 +towgs84=0,0,0,0,0,0,0 +units=m +no_defs"); // proj4 always uses [longitude, latitude] / [east, north]. const [east, north] = proj4("EPSG:4326", "EPSG:25832", [10.20285443, 56.14811374]); console.log(`UTM32: ${east.toFixed(2)} ${north.toFixed(2)}`); const [lon, lat] = proj4("EPSG:25832", "EPSG:4326", [east, north]); console.log(`WGS84: ${lon.toFixed(8)} ${lat.toFixed(8)}`);
Precision and height
- WGS84 coordinates have 8 decimals (about a millimetre). UTM coordinates have 2 decimals (a centimetre). There is no need to round them before storing.
adgangspunkt.nøjagtighedtells you how well the point is determined:Ais placed precisely on the base map,Bis calculated, andUis uncertain.adgangspunkt.højdeis the terrain height in metres at the access point, when known.
Next steps
Related guides
Markdown source Spotted an error? Tell us API-reference (Swagger)