Il existe un paquet python nommé python-slugify
qui fait un assez bon travail de slugification :
pip install python-slugify
Ça marche comme ça :
from slugify import slugify
txt = "This is a test ---"
r = slugify(txt)
self.assertEquals(r, "this-is-a-test")
txt = "This -- is a ## test ---"
r = slugify(txt)
self.assertEquals(r, "this-is-a-test")
txt = 'C\'est déjà l\'été.'
r = slugify(txt)
self.assertEquals(r, "cest-deja-lete")
txt = 'Nín ho. W shì zhng guó rén'
r = slugify(txt)
self.assertEquals(r, "nin-hao-wo-shi-zhong-guo-ren")
txt = ''
r = slugify(txt)
self.assertEquals(r, "kompiuter")
txt = 'jaja---lol-méméméoo--a'
r = slugify(txt)
self.assertEquals(r, "jaja-lol-mememeoo-a")
Voir Autres exemples
Ce paquet fait un peu plus que ce que vous avez posté (jetez un coup d'œil à la source, c'est juste un fichier). Le projet est toujours actif (il a été mis à jour 2 jours avant ma réponse initiale, plus de neuf ans plus tard (dernière vérification le 2022-03-30), il est toujours mis à jour).
attention : Il existe un deuxième paquet, nommé slugify
. Si vous avez les deux, vous risquez d'avoir un problème, car ils ont le même nom pour l'importation. Celui qui est juste nommé slugify
n'a pas fait tout ce que j'ai vérifié rapidement : "Ich heiße"
est devenu "ich-heie"
(devrait être "ich-heisse"
), veillez donc à choisir le bon, lorsque vous utilisez la fonction pip
o easy_install
.
1 votes
Travaillez-vous souvent avec l'unicode ? Si c'est le cas, le dernier re.sub pourrait être meilleur si vous l'entourez d'unicode(), c'est ce que fait django. De même, le [^a-z0-9]+ peut être raccourci en utilisant \w . voir django.template.defaultfilters, il est proche du vôtre, mais un peu plus raffiné.
0 votes
Les caractères unicode sont-ils autorisés dans les URL ? De plus, j'ai changé \w à a-z0-9 parce que \w comprend le caractère _ et les lettres majuscules. Les lettres sont mises en minuscules à l'avance, il n'y aura donc pas de lettres majuscules à faire correspondre.
0 votes
'_' est valide (mais c'est votre choix, vous l'avez demandé), l'unicode correspond aux caractères encodés en pourcentage.
0 votes
Merci Mike. J'ai posé une mauvaise question. Y a-t-il une raison de la ré-encoder en chaîne unicode, si nous avons déjà remplacé tous les caractères sauf "a-z", "0-9" et "-" ?
0 votes
Pour django, je crois qu'il est important pour eux d'avoir toutes les chaînes de caractères en tant qu'objets unicode pour la compatibilité. C'est votre choix si vous voulez cela.
0 votes
J'ai fait une demande de modification du fichier slugify ( github.com/zacharyvoase/slugify ) Python lib qui aborde tous les problèmes : github.com/ksamuel/slugify . Standalone pure python pip installable slugify utilisant unicodata, ou unidecode si installé. Vous pouvez choisir un séparateur personnalisé et même conserver tous les caractères non ASCII. J'espère qu'il sera bientôt accepté et poussé sur pypi.
0 votes
En python 3.6 j'ai dû rajouter le décodage à la chaîne : slug = slug.encode('ascii', 'ignore').lower().decode('ascii') sinon la variable slug était convertie en binaire et re.sub levait une exception.