Part of a Data Solution
- Explore →
Postal Codes Solution
Every worldwide postal-code dataset in one bundle — the ultimate global reference for precise postal codes.
Premium
You're viewing a free sample
Get the complete dataset — all rows and files — delivered instantly after checkout, with lifetime access to the latest version.
- Secure checkout via Stripe
- Instant download after payment
- Lifetime access to the latest version
- Creative Commons Attribution 4.0 — GeoNames (postal codes, postal towns, coordinates, most kommun names) license
API Access
Access dataset files directly from scripts, code, or AI agents.
Browse dataset files
API Access
Access dataset files directly from scripts, code, or AI agents.
Each file has a stable URL (r-link) that you can use directly in scripts, apps, or AI agents. These URLs are permanent and safe to hardcode.
Start with these files — they give you everything you need to understand and access the dataset.
- 1. Fetch datapackage.yaml to inspect schema and resources
- 2. Download data resources listed in datapackage.yaml
- 3. Read README.md for full context
Data Files
postal-codes-se-sample
| Field | Type | Description | Constraints | Title |
|---|---|---|---|---|
| country_code | string | ISO 3166-1 alpha-2 country code — always SE | { "pattern": "^SE$", "required": true } | Country Code |
| postal_code | string | 5-digit Swedish postal code in NNN NN display format (space significant). Read via this descriptor or pass dtype=str. | { "pattern": "^\\d{3} \\d{2}$", "required": true } | Postal Code |
| place_name | string | Postort (postal town) | { "required": true } | Place Name |
| admin_name1 | string | Län (county) | { "required": true } | Administrative Name 1 |
| admin_code1 | string | ISO 3166-2:SE county code, SE- prefix stripped | { "required": true } | Administrative Code 1 |
| admin_name2 | string | Kommun (municipality). Source-supplied for most rows; where the source left it blank, resolved from evidence already in the dataset or a corrections table — see README. | { "required": true } | Administrative Name 2 |
| admin_code2 | string | Reserved — Sweden has no official municipality-level ISO code, and none is populated for this build. | Administrative Code 2 | |
| admin_name3 | string | Reserved — not populated for Sweden (postort occupies place_name, the finest tier this source reaches). | Administrative Name 3 | |
| admin_code3 | string | Reserved — not populated for Sweden. | Administrative Code 3 | |
| latitude | number | WGS84 latitude, decimal degrees, 5 dp — postal-code centroid, not building-level | Latitude | |
| longitude | number | WGS84 longitude, decimal degrees, 5 dp — postal-code centroid, not building-level | Longitude | |
| accuracy | string | Coordinate granularity tier — always AREA for this dataset (postal-code centroid, not GeoNames' numeric 1-6 scale) | Accuracy | |
| alternative_city_name | string | Alternate postort spelling/name where the source supplies one | Alternative City Name |
Download
Download sample CSVAbout
- Last updated
- 11 October 2026
- Total rows
- 100
- Format
- CSV
- File size
- 6.87 kB
About this dataset
Sweden (SE): migration notes
Internal record of the P5 migration from the prototype build to the producer: the discrepancies found, their causes, and who decided what. This is a dated record (2026-10-11), so the numbers are as of the migration and not kept current. It is not shipped in the zip.
- Issue: datopian/postal-codes#41
- Commit: the producer commit on this branch
- Parity verdict:
unexplained(gate: blocked), accepted under the owner's under-1% rule: 29 rows added (0.15%), 0 changed cells, 0 rows lost - Producer:
custom, refresh disabled
What made the live file, verified
The live se.csv was never built by the scripts that sat in this directory (a GeoNames passthrough that would have regressed it). It came from the prototype's countries/SWE build in the fedex-agents-prototype repo: scrape_postal.py (Phase 1 download from the postalcodes.info mirror of GeoNames, Phase 2 kommun resolution), scrape_admin.py (Wikipedia), run_qa.py (spelling repair, checks) and build_postal_codes_format.py (12 columns to 13). Re-run on 2026-10-11 from its saved Phase 1 data (--phase2-only, then QA, then the converter) it reproduces the live se.csv byte for byte. Those scripts stay in that repo as the record; they import that repo's own models, so they are not copied here.
Sources
| Input | URL | Notes |
|---|---|---|
| GeoNames postal export | https://download.geonames.org/export/zip/SE.zip | CC BY 4.0. postalcodes.info is a re-export of the same file, so Phase 1 is a direct column mapping |
| Wikipedia, Counties of Sweden | https://en.wikipedia.org/w/api.php?action=parse&page=Counties_of_Sweden | CC BY-SA 4.0. Only the 21 län names and ISO codes are used |
| Wikipedia, List of municipalities of Sweden | https://en.wikipedia.org/w/api.php?action=parse&page=List_of_municipalities_of_Sweden | CC BY-SA 4.0. Only the 290 kommun names and their län are used |
scripts/kommun_corrections.csv | committed reference table | 41 rules, each with its own evidence string (32 cite Wikipedia), copied unchanged from the prototype |
Parity against the live zip (2026-10-11)
Rows: 18,858 live and 18,887 fresh. 29 only in fresh, 0 only in live, 0 changed cells in the 18,858 shared rows. The producer, fed the live GeoNames and Wikipedia pages today, gives every existing row exactly as it is in the live file.
Cause: GeoNames added 29 postal codes since the live build (upstream drift). For example 147 35 Tumba, 125 49 Ävsjö, 163 49 Spånga, 925 32 Tärnaby, 982 61 Svappavaara, 837 73 Duved. The earlier comparison in this directory (diff_provenance.py) had already recorded exactly 29 codes in GeoNames and not in the postalcodes.info scrape. 28 resolve to a real kommun (many are cities whose postort and kommun share a name, such as Göteborg).
One new row carries an upstream typo. GeoNames spells postal code 216 26 "Mlamö" (Malmö). The kommun was blank, so the postort stands in for it (the documented fallback), and the typo lands in admin_name2 too. A correction rule in kommun_corrections.csv (kommun Malmö) would fix the kommun; left for the owner, since it changes the file beyond a faithful port.
Decisions
| Decision | By | Basis |
|---|---|---|
| Port the prototype build into one fetching producer | Owner, 2026-10-11 ("work on those that are available") | Plan D1: go back to the original source |
| Read GeoNames directly instead of the postalcodes.info mirror | Agent: port choice | The mirror is the same export; the mirror is a scraped third-party site, GeoNames is the source |
| Accept 29 added rows (0.15%) | Owner, 2026-10-11 ("if they differ by less than 1%, then ok"); standing rule for traced upstream drift | Traced to GeoNames above |
| Keep the corrections table as committed reference data | Precedent: es po_box_codes.csv (user, 2026-10-03) | Every rule carries its evidence |
Drop additionalInfo and the län-conflict notes | Agent: a faithful port | They had no column in the 13-column format; the conversion dropped them before |
Drop the old in-repo scripts, including diff_provenance.py | P5 rule | They did not make the live file |
| LF line endings; README and ATTRIBUTION kept from the repo | Standing rule / agent | The repo copies were corrected in #38 and credit Wikipedia for these facts |
Transforms carried over
- län from the source name and ISO code; a numeric code is derived from the name; a blank län comes from a unanimous 2-digit prefix.
- A matching correction rule sets län and kommun first. Otherwise a blank kommun is resolved by: the postort's unanimous kommun in the same län, then the postort being a kommun of the län, then the län's only kommun (Gotland), then the 3-digit prefix's unanimous or 80% majority kommun, then the postort itself. Malung is renamed Malung-Sälen.
- Spelling variants within a län are folded to the majority spelling and kept as an alias (
alternative_city_name, joined with " | "). - Checks (
ProducerError): 21 län present; at least 90% of the kommuner covered; ISO län codes only; no duplicate(postal_code, place_name); at most 5 decimals; under 1% of GeoNames rows unusable.
Open questions
- The "Mlamö" row above.
- The 2026-08-24 "CLOSED" entry in
.licensing-notes.mdis superseded by the 2026-10-09 one: the live data does use Wikipedia for these facts. - R2 is untouched. The public sample in R2 is an older build (
accuracy4.0, blank kommun); publishing replaces it.
Provenance
Written 2026-10-11 from the prototype re-run, the producer run on the saved Phase 1 data (identical to live apart from line endings), scripts/parity.py se (reads the live zip, writes nothing) and the Frictionless validation of the built zip.