Catch-all DNS, VirtualHost et on fait mumuse avec les noms de sous-domaines
Salut lecteur,
Un bail que je n’ai rien écrit sur ce blog, la faute à un petit projet perso qui me prend un peu de temps chez moi, semble-t-il.
L’idée
Ceci dit, je voulais laisser une trace de cette manip’ qui consiste à autoriser n’importe quel nom de sous-domaine d’un domaine que vous possédez, exemple le fameux « mon_domaine.com » en ayant la possibilité d’envoyer vers un site ou un autre (au sens, un VirtualHost/DocumentRoot ou un autre) suivant le nom de sous-domaine appelé, la liste de ces sous-domaines étant potentiellement illimitée.
Bon, OK, pour la formulation, c’est pas forcément limpide. Un exemple concret : mon_domaine.com est une société qui propose un service web personnalisé pour ses clients. Le gérant de la chose décide de mettre en place les sous-domaines suivants :
- www.mon_domaine.com
- demo.mon_domaine.com ; même mieux : une liste de plusieurs instances de démo : demo1, demo2 etc
- une série infinie de clientXXX.mon_domaine.com, exemples : http://client.mon_domaine.com, http://autreclient.mon_domaine.com
On voudrait que le « www » renvoie vers le site « commerçant », que les « demoX » renvoient vers le service en mode démo (chacun étant une instance différente, une base de données différente, par exemple) et que chaque « clientXXX » pointe vers le vrai outil, dont le code est commun pour tous les clients, là aussi avec une peut-être une base de donnée différente par client.
Pourquoi ne pas juste passer un paramètre dans l’URL pour indiquer le client ? car dans mon cas, je préférais faire des sous-domaines différents, ça enlève un tas d’épines du pied en ce qui concerne la gestion des sessions, gestion qui est liée au nom complet du domaine, pas à ce qu’il y a après le « .com », comme un http://….com/?client=xxx
On a toujours la possibilité de faire n’importe quelle crassouillerie pour avoir un script d’index[.php] qui dirige vers tel ou tel code/outil suivant l’URL appelée. Pourquoi pas. Mais lorsque l’un des outils est par exemple un outil dont on ne veut pas modifier l’index[.php], ça peut poser problème. Exemple, le « www » est un wordpress, le reste un outil maison. Je ne veux pas avoir à jouer avec le htaccess du WordPress, ce genre de choses. Bref, je scinde les mondes avant et je limite les risques de passage de l’un à l’autre.
Bon, ça y est ? le contexte est clair ?
Voici la solution que je trouve la plus élégante.
Côté DNS : catch-all
Si le gérant de votre nom de domaine le permet, créez d’abord un enregistrement DNS type A ou CNAME nommé « * » et pointant vers votre serveur. Exemple : « *.mon_domaine.com CNAME mon_domaine.com
« .
Tous ne le permettent sûrement pas. Je sais au moins que OVH le tolère, il suffit de mettre « * » comme nom de sous-domaine.
Ensuite, on peut tester avec la commande « host/nslookup nimportequoi.mon_domaine.com
« .
Côté Apache : identification du sous-domaine demandé
Avec la manip’ DNS, on est sûr que nimportequoi.mon_domaine.com renvoie bien vers le serveur. Reste à trier au niveau Apache (plutôt qu’au niveau code derrière, comme j’ai expliqué plus haut).
Déjà pour être sûr que ça marche, une conf simpliste consiste à créer un unique VirtualHost comme ceci :
ServerName mon_domaine.com ServerAlias *.mon_domaine.com ServerAdmin webmaster@mon_domaine.com ... DocumentRoot /quelque/part/ ...
Avec ça, vous pouvez appeler http://peu_importe.mon_domaine.com ou http://www.mon_domaine.com et atterrir sur le même VirtualHost/DocumentRoot, le même « site ».
Ensuite, on améliore pour scinder les 3 jeux de sous-domaines. Supprimez le VirtualHost d’avant et mettez :
ServerName www.mon_domaine.com ServerAdmin webmaster@mon_domaine.com ... DocumentRoot /quelque/part/le/site/www/ ... ServerAlias demo*.mon_domaine.com ServerAdmin webmaster@mon_domaine.com ... DocumentRoot /quelque/part/le/code/des/sites/de/demo/ ... ServerName mon_domaine.com ServerAlias *.mon_domaine.com ServerAdmin webmaster@mon_domaine.com ... DocumentRoot /quelque/part/le/code/des/sites/de/production/ ...
Bah voilà, c’est tout, les 3 répertoires mentionnés dans les DocumentRoot sont indépendants.
Il ne resterait plus que dans l’outil, à récupérer le nom du sous-domaine (exemple à partir de $_SERVER['SERVER_NAME']
en PHP) et faire le traitement adéquat.
En espérant que ça serve à quelqu’un,
A la prochaine !
L’article Catch-all DNS, VirtualHost et on fait mumuse avec les noms de sous-domaines est apparu en premier sur Le blog de Michauko.