Première rédaction de cet article le 24 septembre 2017
Dernière mise à jour le 9 octobre 2020
Petit service juste pour s'amuser : mettre l'ensemble des codes postaux français dans le DNS avec pour chaque code, la ou les communes concernées, leur longitude et leur latitude.
À quoi ça sert ? Pas à grand'chose, je voulais juste
illustrer l'utilisation de deux types d'enregistrements DNS
peu connus, LOC
(RFC 1876) et URI
(RFC 7553). (Au passage, si vous lisez que le DNS sert à
traduire des noms en adresses IP, allez lire autre chose :
c'est faux, ou, en tout cas, très réducteur.) Et traiter un peu de
JSON en prévision de la prochaine
sortie du nouveau RFC sur JSON, le RFC 8259.. Voyons
d'abord le résultat avec le traditionnel client DNS
dig :
% dig +short +nodnssec TXT 34000.cp.bortzmeyer.fr "MONTPELLIER"
L'enregistrement TXT
permet d'indiquer
le nom de la ville concernée. Parfois, il y en a plusieurs :
% dig +short +nodnssec TXT 52100.cp.bortzmeyer.fr "HALLIGNICOURT" "VALCOURT" "CHANCENAY" "SAPIGNICOURT" "ST DIZIER" "PERTHES" "ST EULIEN" "BETTANCOURT LA FERREE" "LANEUVILLE AU PONT" "VILLIERS EN LIEU" "MOESLAINS"
Le même domaine cp.bortzmeyer.fr
contient
également la position de la ville (ou plus probablement celle du
bureau de poste principal), avec le type LOC
,
normalisé dans le RFC 1876) :
% dig +short +nodnssec LOC 34000.cp.bortzmeyer.fr 43 36 47.108 N 3 52 9.113 E 0.00m 1m 10000m 10m
Nous voyons ici que Montpellier est à 43°
36' 47'' de latitude Nord et 3° 52' 9'' de
longitude Est.
Si vous voulez voir tout de suite où ça se trouve, vous avez
également un URI
(type d'enregistrement DNS
normalisé dans le RFC 7553) qui pointe vers
OpenStreetMap (merci à OpenStreetMap de
permettre de fabriquer des URL simples) :
% dig +short +nodnssec URI 52100.cp.bortzmeyer.fr 10 1 "http://www.openstreetmap.org/?mlat=48.646559&mlon=4.912187&zoom=12"
(L'enregistrement URI étant relativement récent, il ne faut pas utiliser un dig trop vieux. Par exemple, avec la version 9.8.3, on n'a pas de résultat avec cette commande.) Enfin, vous pouvez aussi retrouver les codes postaux à partir du nom de la ville :
% dig +short +nodnssec TXT ROUEN.cp.bortzmeyer.fr "76100" "76000"
Mais il y a quelques pièges : la base utilisée n'a que des caractères ASCII donc il faudra écrire « epernay » et pas le nom correct. Et pour Paris, il faudra ajouter un tiret et l'arrondissement, par exemple « paris-16 ».
Ce n'est pas très joli avec dig ? Pas convivial ? Vous pouvez aussi essayer un DNS Looking Glass. Par exemple, toutes les données pour 73370, la localisation de 73700, les les noms associés à 97434 ou bien le(s) code(s) postal(aux) de Beaugency.
Comment est-ce que ce service a été réalisé ? Je suis parti d'un fichier JSON contenant les informations nécessaires, un petit programme Python le transforme en fichier de zone DNS (section 5 du RFC 1035). Que du très simple. Le plus dur était certainement de trouver les données. En France, il y a une tradition régalienne de ne pas donner les informations au citoyen. L'État préfère les garder pour lui, ce qui obligeait à des contorsions compliquées. Le mouvement « données ouvertes » a heureusement changé les choses, même si c'est encore loin d'être parfait.
La source que j'ai utilisée est la « Base officielle des codes postaux » (trouvée via data.gouv.fr). Je ne dis pas que cette base est meilleure que les autres, mais son côté « officiel » me permet de répondre « c'est pas ma faute » si quelqu'un y trouve une erreur ou une approximation. J'ai utilisé la version GeoJSON du fichier. Elle n'est pas parfaite. Ainsi il y a un certain nombre de fautes d'orthographe comme Marolles-sous-Lignières écrit MAROLLES SOUS LIGNIERES, sans l'accent (les tirets et les apostrophes manquent également). D'autre part, certaines communes, notamment en Polynésie française, n'ont pas d'information de localisation. Ici, à Fakarava :
% dig +short +nodnssec LOC 98764.cp.bortzmeyer.fr %
Dernier problème, la liste n'est pas à jour. La commune de Meaulne-Vitray (code postal 03360), créée le 1er janvier 2017, n'apparait pas encore dans la liste, téléchargée le 24 septembre 2017. (Et elle n'est pas la seule.)
D'autres sources possibles de données avaient été considérées (et merci à Sabine Blanc, Olivier Macchioni, Pascal Corpet, Laurent Penou, Adrien Clerc, Ainiton et tous les autre qui m'ont fait d'excellentes suggestions) :
http://www.aito.fr/maps_ville.sql
est une
excellente base MySQL, où les noms sont
bien orthographiés, mais qui est vieille de nombreuses
années. D'autre part, elle semble incomplète
(Lille n'y a qu'un seul code postal alors
qu'il en existe plusieurs en pratique).http://www.galichon.com/codesgeo/
permet de
trouver codes postaux et positions géographiques, et sa base (à
jour ? correcte ?) est téléchargeable (au format
Microsoft Excel).Si vous voulez proposer d'autres bases, n'oubliez pas de regarder ces points :
Ce service utilise les codes postaux, mais il existe aussi les COG, dits « codes INSEE », qui sont également disponibles. Ce sera pour un autre service.
Un peu de technique pour finir. Le script lancé par cron tous les mois fait :
wget -O laposte_hexasmal.geojson 'https://datanova.legroupe.laposte.fr/explore/dataset/laposte_hexasmal/download/?format=geojson' ./laposte2dns.py laposte_hexasmal.geojson > cp.zone ods-signer sign bortzmeyer.fr
La première commande télécharge le fichier au format JSON. La
seconde (le script laposte2dns.py
) convertit le JSON
en fichier de zone DNS qui ressemble donc à :
10130.cp IN TXT "MAROLLES SOUS LIGNIERES" IN LOC 48 3 7.201 N 3 55 56.876 E 0 IN URI 10 1 "http://www.openstreetmap.org/?mlat=48.052000&mlon=3.932466&zoom=12" 10170.cp IN TXT "LES GRANDES CHAPELLES" IN LOC 48 29 29.856 N 3 56 0.604 E 0 IN URI 10 1 "http://www.openstreetmap.org/?mlat=48.491627&mlon=3.933501&zoom=12" 10110.cp IN TXT "MERREY SUR ARCE" IN LOC 48 6 57.679 N 4 25 51.357 E 0 IN URI 10 1 "http://www.openstreetmap.org/?mlat=48.116022&mlon=4.430933&zoom=12" ...
Le fichier ainsi produit (dans les onze mégaoctets) est chargé depuis le fichier de zone
principal de bortzmeyer.fr
, via une directive
d'inclusion :
; Codes Postaux $INCLUDE /etc/nsd/primary/cp.incl
Enfin, la troisième commande utilise OpenDNSSEC pour signer la zone, et recharger le serveur de noms.
Un tel service dans le DNS existe déjà pour le
Royaume-Uni, via le domaine
find.me.uk
:
% dig +short DY76JP.find.me.uk LOC 52 26 46.924 N 2 13 5.686 W 0.00m 0.00m 0.00m 0.00m
(Ou bien, avec le
Looking Glass.) Un travail similaire a été fait pour la
Suisse avec
zipdns.ch
. Par exemple :
% dig +short LOC 1204.zipdns.ch 46 12 14.214 N 6 8 47.064 E 1.00m 1m 10000m 10m
Ce qui est plus joli avec le Looking
Glass. Pour l'Allemagne, c'est en
cours (il n'y a pas encore la position physique)) sur zipde.jpmens.net
. Essayons avec
Ratisbonne :
% dig +short TXT 93047.zipde.jpmens.net "Regensburg"
Il y a un œuf de Pâques dans
ce service, faisant référence à une célèbre blague allemande.
Et il y a enfin un service similaire pour les codes IATA à trois lettres des
aéroports (souvent utilisés pour nommer les routeurs dans l'Internet, ce qui aide à
interpréter les traceroutes)
en air.jpmens.net
:
% dig +short ORY.air.jpmens.net LOC 48 43 24.000 N 2 22 46.000 E 89.00m 1m 10000m 10m
Une requête TXT vous en dira plus :
% dig +short ORY.air.jpmens.net TXT "u:https://en.wikipedia.org/wiki/Orly_Airport_(Paris)" "cc:FR; m:Paris; t:large, n:Paris-Orly Airport"
Là aussi, vous pouvez préferer le
Looking Glass. Ce service est documenté
dans un intéressant article. (Un service analogue utilisant
les UN/LOCODE existe en
locode.sha256.net
mais semble expérimental.)
Et pour rire, une quetsion difficile à la fin : faut-il indiquer la latitude ou la longitude en premier ? (ISO 6709 dit qu'on met la latitude avant).
Version PDF de cette page (mais vous pouvez aussi imprimer depuis votre navigateur, il y a une feuille de style prévue pour cela)
Source XML de cette page (cette page est distribuée sous les termes de la licence GFDL)