URL propres en arborescence virtuelle

Ceci est une archive périmée mais qui reste intéressante, parfois autant pour l’article que les commentaires associés.

Permet d’obtenir une URL synthétisant l’arborescence du site

Problématique

Une belle arborescence de rubriques devrait toujours être représentée par une belle url synthétisant cette arborescence. Et pourtant, même avec les urls propres, il était difficile d’obtenir plus qu’un titre et un identifiant peu parlants dans une barre d’adresse.

Avec un site décomposé de la forme suivante :

/ (Racine)
+ Télé-achat (Secteur)
| + Catégorie cuisine (Rubrique)
|   + Le plus beau presse-agrumes du monde (Article)

Il paraît logique d’avoir des adresses du type
-  http://monsite.exemple/
-  http://monsite.exemple/tele-achat/
-  http://monsite.exemple/tele-achat/categorie-informatique/
-  http://monsite.exemple/tele-achat/categorie-cuisine/le-plus-beau-presse-agrumes-du-monde.html

et bien c’est exactement ce qui vous est proposé ici !

Mais alors, Pierre, comment ça marche ?

C’est très simple Maryse ! Le système se base sur le même principe que les url_propres fournies dans la version officielle de Spip, sauf qu’au lieu de ne stocker que le titre dans le champ url_propre de la base de données, nous allons dorénavant stocker toute l’arborescence « propre ».

Il faudra aussi mettre en place une redirection d’adresse, puisque le répertoire tele-achat n’existe pas sur notre serveur web.

Allez, même pas peur, on va installer et paramétrer d’un coup !

Téléchargez et décompressez l’archive :

url-propres-arbo-v1.8.zip

C’est fait ? Alors c’est parti !

Le fichier propres-arbo.php est à placer dans le répertoire
{monDossierSpip}/ecrire/urls/.

Dans sa configuration par défaut, les urls ne sont pas limitées en longueur, et tous les caractères sont convertis en minuscules.
Si ces règles ne vous conviennent pas, vous pouvez changer la configuration du script via les constantes suivantes :
-  _taille_min_url_propre : la longueur minimale de la totalité de l’url (0 pour ne pas limiter). Si la taille de l’url calculée est plus petite, celle-ci sera remplacée par son type suivi de son identifiant (exemples : rubrique1, article42,...)
-  _taille_max_url_propre : la longueur maximale de la totalité de l’url (0 pour ne pas limiter)
-  _taille_max_champ_url_propre : la longueur maximale d’un niveau de l’url (0 pour ne pas limiter)
-  _mIxEdCaSe : booléen indiquant si les majuscules sont autorisées dans l’url (0 pour interdire, 1 pour autoriser)

Pour basculer sur ces url propres, la seule chose à faire est d’éditer votre fichier
mes_options.php
afin de positionner la variable
$type_urls = "propres-arbo";

Attention, le fichier mes_options.php n’est pas placé au même endroit selon les versions de Spip :
-  {monDossierSpip}/ecrire/mes_options.php pour SPIP 1.9.1
-  {monDossierSpip}/config/mes_options.php pour SPIP 1.9.2 et ultérieures

Du bon usage des redirections

C’est bien joli de patcher notre SPIP, mais il faut aussi que les requêtes passées au serveur web lui parviennent.

Pour cela, deux solutions :
-  le mod_rewrite d’Apache : la solution la plus propre lorsque le module est disponible sur votre serveur
-  l’utilisation des ErrorDocument : une solution moins élégante techniquement mais toute aussi efficace pour les serveurs les plus démunis (n’hésitez pas à envoyer vos dons pour les aider).

Redirection avec le mod_rewrite

Pas grand chose à faire, il suffit de prendre le fichier mod_rewrite/htaccess.txt et de le placer à la racine de votre site SPIP après l’avoir renommé en .htaccess [1].
Il vous faudra peut-être décommenter et modifier la directive RewriteBase de ce fichier si SPIP est installé dans un sous-répertoire sur le serveur web.
Par exemple, si SPIP est installé dans http://monsite.exemple/spip/ il faut définir RewriteBase /spip/.

Redirection avec la directive ErrorDocument

Ici, ça va vite aussi, il vous faut deux fichiers :

- ErrorDocument/spip-rewrite-with-404.php qu’il faut placer à la racine de votre site SPIP.
Il vous faudra dans tous les cas créer ou définir une page d’erreur 404. Vous en trouverez une dans ErrorDocument/404.html que je vous recommande de placer dans votre dossier de squelettes. Si toutefois vous la placiez ailleurs ou sous un autre nom, il vous faudra modifier la ligne $this->pagedestination="squelettes/nom/de/votre/page/404.html"

Il vous faudra peut-être aussi modifier la variable $this->installdir de ce fichier si SPIP est installé dans un sous-répertoire sur le serveur web.
Par exemple, si SPIP est installé dans http://monsite.exemple/spip/ il faut définir $this->installdir=",^/spip/,"; (la chaîne utilisée est un filtre pour expression rationnelle, il faut donc laisser les virgules l’encadrant ainsi que le ’^’ qui indique que l’on travaille uniquement depuis le début de la chaîne de caractères).

-  ErrorDocument/htaccess.txt qu’il faut aussi placer à la racine de votre site SPIP après l’avoir renommé en .htaccess [1].
Il vous faudra peut-être modifier la ligne ErrorDocument 404 /spip-rewrite-with-404.php de ce fichier si SPIP est installé dans un sous-répertoire sur le serveur web.
Par exemple, si SPIP est installé dans http://monsite.exemple/spip/ il faut adapter la ligne en ErrorDocument 404 /spip/spip-rewrite-with-404.php";

Modifications à apporter à vos squelettes

Ça n’est pas encore terminé ! Puisque l’on crée une arborescence virtuelle, le navigateur et le serveur web ne vont pas s’y retrouver lors des inclusions d’images, scripts, feuilles de styles, etc.

La solution est très simple : ajouter la balise <base href="#URL_SITE_SPIP/" /> dans l’en-tête de votre site.

Au secours, les boutons d’administration ne fonctionnent plus !

Mais non Maryse, inutile d’appeler Jack Bauer, il y a toujours une solution, par contre ça implique de mettre les mains dans le cambouis, et comme Jack est occupé avec les chinois du FBI, il va falloir se débrouiller !

Tout d’abord, recopiez la fonction suivante dans le fichier mes_fonctions.php se trouvant dans votre dossier de squelettes :

<?php

	function url_a_la_racine ( $url ) {
		if ( $url == '' )
			return '';
		
		$racine = $GLOBALS['meta']['adresse_site'];
		$suffixe = preg_replace(',^.*(ecrire/|spip.php)?([^/]*)$,U', "\\1\\2", $url);
		
		return "$racine/$suffixe";
	}

?>

Ensuite, recopiez simplement le fichier bonus/administation.html dans le dossier {monDossierSpip}/squelettes/formulaires/.
ATTENTION ! si vous utilisez une version antérieure à la 1.9.2, il vous faut renommer administration.html en formulaire_admin.html.

Allez, encore un effort, on y est presque, il reste la modification la moins propre selon moi (si quelqu’un a mieux, lachez vos comms !) :

Recherchez la chaîne

<link rel='stylesheet' href='".url_absolue(find_in_path('spip_admin.css'))

dans les fichiers
-  monDossierSpip/ecrire/public/admin.php
-  monDossierSpip/ecrire/public/debug.php
puis remplacez la par

<link rel='stylesheet' href='".find_in_path('spip_admin.css')

Problèmes connus

RealET a dit :

« Une implémentation foireuse commune à Internet Explorer 6 et FireFox 1.5 fait que sur ces navigateur, le base href est pris en compte pour toutes les ancres de la page, ce qui a pour effet de faire planter toutes les ancres et notes de bas de page. »

Je n’ai malheureusement pas de solution à proposer à ce sujet, si quelqu’un connaît un hack, qu’il parle maintenant ou se taise à jamais...


Jean-Kevin, pirate-kiddie des temps modernes a dit :

« C’est nul cette modification : je viens de changer un nom d’article ou de rubrique, mais l’url ne change pas ! »

Mais non Jean-Kevin, c’est normal ! SPIP est partisan du moindre effort, et ce pour le bien de nos serveurs web. Ainsi il ne recalcule pas les urls propres tout seul. Mais n’aie pas peur, il existe un splendide plugin pour lui dire de le faire.


Une autre question ?

Notes

[1sous Windows et MacOS, on ne peut pas renommer un fichier en .htaccess. Il faut donc utiliser votre client ftp préféré pour envoyer le fichier, et utiliser le même client pour renommer ensuite le fichier sur le serveur.

Discussion

36 discussions

  • Bonjour !
    Merci pour cet outil vraiment chouette et simple à mettre en place ! Par contre, j’utilise le plugin forms et table et il semble que ca ne fonctionne pas lors de l’envoi des donnees des formulaires : on a un truc du style http://monsite.com/mapage_formulaire.html au lieu de http://monsite.com/mon_arborescence/mapage_formulaire.html.
    Voila tout, merci pour vos solutions !
    Steve A.

    Répondre à ce message

  • 2

    Hello,

    tout d’abord un grand merci pour cette contrib essentielle !

    Ensuite, je voudrais vous faire part du problème que j’ai rencontré et vous soumettre la modification que j’ai dû mettre en œuvre pour le contourner (Attention, message long) :

    J’utilise à plusieurs endroits d’un site dont je m’occupe la balise #SELF pour rappeler la page en cours en lui passant des paramètres supplémentaires. Depuis la mise en place des urls ’propres-arbo’ je me suis rendu compte que cette balise renvoyait systématiquement à la racine du site, rendant mes liens inutilisables.

    Après qq recherches dans le code de SPIP, je me suis rendu compte qu’un traitement de nettoyage un peu violent (Et surtout incompatible avec votre contrib) de l’url était effectué dans la fonction self() sauf si celle-ci étaient appelée avec un paramètre « root » à ’true’ (Fonction définie dans le fichier ecrire/inc/utils.php). J’ai donc modifié la définition de la balise #SELF pour inclure ce paramètre.

    Après qq tests (Non exhaustifs !) je n’ai pas remarqué d’effets de bord indésirables. Je vous soumets donc cette modification qui pourra pê servir à d’autres.

    ATTENTION : Cette modification est dangereuse car elle se fait dans les fichiers de SPIP et c’est mal, vous voilà prévenus.

    Il faut modifier le fichier ecrire/public/balises.php (Ligne 930 pour la version 1.9.2a) comme résumé dans ce diff :

    *** balises-org.php
    --- balises.php
    *** 927,933 ****
      // http://www.spip.net/@self
      // http://doc.spip.org/@balise_SELF_dist
      function balise_SELF_dist($p) {
    !       $p->code = 'quote_amp(self())';
            $p->interdire_scripts = false;
            return $p;
      }
    --- 927,933 ----
      // http://www.spip.net/@self
      // http://doc.spip.org/@balise_SELF_dist
      function balise_SELF_dist($p) {
    !       $p->code = 'quote_amp(self(true))';
            $p->interdire_scripts = false;
            return $p;
      }

    Si vous avez une solution plus élégante je suis preneur, bien évidemment :-) .

    • En utilisant la surcharge, il suffirait simplement de redéfinir la balise SELF avec cette même fonction intitulée « function balise_SELF($p) » et placée dans mes_fonctions.php par exemple.

    • Exact, ça fonctionne parfaitement.

      Merci beaucoup pour l’astuce (J’oublie trop souvent ces possibilités de surcharge, que j’utilise par ailleurs pourtant).

    Répondre à ce message

  • Bonjour, D’abord je me permet de vous féliciter pour le travail que vous avez fait. En ce moment je l’utilise et ça marche bien ; Par contre j’ai un petit souci concernant mes ancres. J’ai mis différents encres sur mes pages et quand on clique dessus il s’y retrouve plus. Sinon ça marche pour le reste. Merci d’avance.

    Répondre à ce message

  • 1
    Anthony

    Bonjour,
    j’attendais ce système d’url pour spip depuis des années, merci !
    Mais ... J’ai des erreurs 404. Il me semble avoir tout fait correctement.
    Je teste ce système et je me suis créé un sous domaine sur mon domaine déjà existant. Est ce lié à cela ? Dois-je donc changé mon rewrite base ?

    Merci d’avance.

    • Boris Lechner

      Bonjour, j’attendais ce système d’url pour spip depuis des années, merci ! Mais ... J’ai des erreurs 404. Il me semble avoir tout fait correctement. Je teste ce système et je me suis créé un sous domaine sur mon domaine déjà existant. Est ce lié à cela ? Dois-je donc changé mon rewrite base ?
      Merci d’avance.

      En principe, si vous avez suivi mes recommandations, le rewritebase est valable uniquement pour le répertoire de Spip. Donc il devrait être appliqué pour le bon domaine (sous-domaine). Si votre Spip est bien configuré comme étant sur le sous-domaine, je ne vois pas pourquoi ça ne fonctionnerait pas. En résumé, il me manque des informations pour pouvoir essayer de vous aider.

      Avez-vous des erreurs 404 pour toutes les pages ?

    Répondre à ce message

  • 2
    Pierre

    Tout semble fonctionner au poil... J’ai pourtant encore un petit soucis :

    Je travaille sur un site bilingue ou les deux rubriques racine s’appellent « en » et « fr ». L’arborescence s’affiche correctement sur les adresses générés pour l’ensemble des pages (articles, rubriques, mots, etc...), sauf pour les pages de rubriques situées à la racine du site. Autrement dit, une boucle :

    <BOUCLE_rublang(RUBRIQUES){RACINE}>
       <a href="#URL_RUBRIQUE">#TITRE</a>
    </BOUCLE_rublang>

    me renvoie systématiquement des liens sous la forme http://mon_site_spip/rubriqueXX où XX est le numéro de la rubrique concernée. Impossible de généré l’url : http://mon_site_spip/en/

    Quelqu’un a une idée...

    • Pierre

      Bon, je me répond à moi-même après avoir compris le « problème ». Un sécurité du siltre de réécriture des adresses. Ca se passe dans le fichier propres-arbo.php qu’on a placé dans /ecrire/urls
      Autours de la ligne 175, on a :

      	// S'il reste trop de caracteres non latins, ou trop peu
      	// de caracteres latins, utiliser l'id a la place
      
      	if (preg_match(",([^a-zA-Z0-9 /+*=].*){5},", $url, $r)
      	OR strlen($url)<3) {
      		$url = $type.$id_objet;
      	}

      Ainsi donc, un titre de rubrique inferieur à 3 caractères latin est simplement ignoré et remplacé par sa version rubriqueXX, ce qui était mon cas ! J’ai donc remplacé la condition strlen($url)<3 par strlen($url)<1

    • Effectivement, et c’est bien vu !
      Du coup j’ai rajouté cela en option dans la version 1.7 (en ligne), et dorénavant la vérification est désactivée par défaut.
      Tout se joue avec la nouvelle variable _taille_min_url_propre qui est initialisée à 0 par défaut (cf. cet article, que je viens de mettre à jour).

    Répondre à ce message

  • traker

    hello,
    Je voudrais poser une question qui s’eloigne un peu du sujet actuel.. J’utilise les url propres 2 et mes articles possèdent un titre et un surtitre..

    J’aimerai passer dans l’url, le titre plus le surtitre.. du style

    titre:spip
    surtitre:vive internet

    j’obtienne http.xxxxxxxx.com/spip-vive-internet.html

    Et bien comment faire ?! Je suppose que ca se trouve dans le fichier propre.php mais a quelle ligne ? Merci pour votre aide.

    Répondre à ce message

Ajouter un commentaire

Avant de faire part d’un problème sur un plugin X, merci de lire ce qui suit :

  • Désactiver tous les plugins que vous ne voulez pas tester afin de vous assurer que le bug vient bien du plugin X. Cela vous évitera d’écrire sur le forum d’une contribution qui n’est finalement pas en cause.
  • Cherchez et notez les numéros de version de tout ce qui est en place au moment du test :
    • version de SPIP, en bas de la partie privée
    • version du plugin testé et des éventuels plugins nécessités
    • version de PHP (exec=info en partie privée)
    • version de MySQL / SQLite
  • Si votre problème concerne la partie publique de votre site, donnez une URL où le bug est visible, pour que les gens puissent voir par eux-mêmes.
  • En cas de page blanche, merci d’activer l’affichage des erreurs, et d’indiquer ensuite l’erreur qui apparaît.

Merci d’avance pour les personnes qui vous aideront !

Par ailleurs, n’oubliez pas que les contributeurs et contributrices ont une vie en dehors de SPIP.

Qui êtes-vous ?
[Se connecter]

Pour afficher votre trombine avec votre message, enregistrez-la d’abord sur gravatar.com (gratuit et indolore) et n’oubliez pas d’indiquer votre adresse e-mail ici.

Ajoutez votre commentaire ici

Ce champ accepte les raccourcis SPIP {{gras}} {italique} -*liste [texte->url] <quote> <code> et le code HTML <q> <del> <ins>. Pour créer des paragraphes, laissez simplement des lignes vides.

Ajouter un document

Suivre les commentaires : RSS 2.0 | Atom