L'encodage d'un site utilisant un logiciel de publication stockant le contenu des pages dans une base de données, comme le font les logiciels de blog, de forum ou de CMS, est une chose importante et susceptible de créer bien des soucis au Webmaster. Les premières versions du célèbre logiciel de blog Wordpress, qui est par ailleurs utilisé pour éditer ce site, utilisaient le charset Latin1 (norme ISO-8859-1), conçu pour afficher toutes les lettres de l'alphabet latin, ainsi que certains caractères accentués (é, ê, ù, à...) et spéciaux (ç, œ, ñ, ß...). Mais l'internationalisation du Web a peu à peu engendré la nécessité d'un charset plus large que le Latin1, prenant en charge plus de caractères. C'est ainsi que Wordpress, comme la plupart des logiciels CMS, de forum ou de blog, a remplacé Latin1 par UTF-8 comme charset par défaut. Ce changement ne pose bien évidemment aucun problème pour les blogs créés postérieurement, toute la mécanique de l'encodage étant transparente pour l'utilisateur. Toutefois, UTF-8 étant incompatible avec le charset Latin1 -- c'est-à-dire qu'il prend en charge de manière différente des caractères accentués utilisés par les deux charsets --, les sites créés en Latin1 doivent faire l'objet de certaines modifications afin de pouvoir être affichés en UTF-8. Cet article a pour but de présenter les modifications qui doivent être apportées à un site utilisant Wordpress, afin de remplacer Latin1 par UTF-8 comme encodage par défaut.

L’encodage d’un site utilisant un logiciel de publication stockant le contenu des pages dans une base de données, comme le font les logiciels de blog, de forum ou de CMS, est une chose importante et susceptible de créer bien des soucis au Webmaster. Les premières versions du célèbre logiciel de blog Wordpress, qui est par ailleurs utilisé pour éditer ce site, utilisaient le charset Latin1 (norme ISO-8859-1), conçu pour afficher toutes les lettres de l’alphabet latin, ainsi que certains caractères accentués (é, ê, ù, à…) et spéciaux (ç, œ, ñ, ß…). Mais l’internationalisation du Web a peu à peu engendré la nécessité d’un charset plus large que le Latin1, prenant en charge plus de caractères. C’est ainsi que Wordpress, comme la plupart des logiciels CMS, de forum ou de blog, a remplacé Latin1 par UTF-8 comme charset par défaut. Ce changement ne pose bien évidemment aucun problème pour les blogs créés postérieurement, toute la mécanique de l’encodage étant transparente pour l’utilisateur. Toutefois, UTF-8 étant incompatible avec le charset Latin1 – c’est-à-dire qu’il prend en charge de manière différente des caractères accentués utilisés par les deux charsets –, les sites créés en Latin1 doivent faire l’objet de certaines modifications afin de pouvoir être affichés en UTF-8. Cet article a pour but de présenter les modifications qui doivent être apportées à un site utilisant Wordpress, afin de remplacer Latin1 par UTF-8 comme encodage par défaut.

Pourquoi modifier l’encodage de son site, au profit de l’UTF-8 ?

Il est nécessaire de répondre à cette question avant d’expliquer la procédure de modification. Disons le d’emblée : celui qui se pose la question doit en principe connaître la réponse. S’il ne la connaît pas, c’est qu’il n’a pas de réelle raison d’opter pour UTF-8, et qu’il peut laisser son site en Latin1. Voyons toutefois les deux avantages de l’UTF-8.

En premier lieu, l’UTF-8 gère plus de caractères que le Latin1. Pour les sites du Web 2.0, qui invitent des internautes partout dans le monde à apporter du contenu, c’est permettre à un plus grand nombre de personnes d’écrire dans leur langue, avec leur alphabet.

En second lieu, et c’est là le point essentiel, la plupart des sites et des logiciels utilisent désormais par défaut l’UTF-8. Il en va donc de même des extensions, des thèmes, et des plug-in développés pour ces logiciels. Par exemple, la traduction officielle de Wordpress en français est encodée en UTF-8, et n’est donc utilisable que sur les sites utilisant le charset UTF-8. Utiliser la traduction française de Wordpress en UTF-8 sur un site dont le charset est Latin1 génère nombre d’erreurs dans l’affichage des pages (les caractères accentués ne sont pas affichés correctement). Il en va de même pour de nombreuses extensions qui ont pour but de rapatrier ou d’agréger du contenu extérieur au site : un add-on Twitter ou RSS, par exemple. Enfin, la plupart des API AJAX utilisent par défaut l’UTF-8. Le contenu récupéré depuis la base de données de manière asynchrone sera donc mal affiché, à moins d’être explicitement converti en Latin1.

Pour l’ensemble de ces raisons, il est préférable d’utiliser le charset UTF-8, qui devient peu à peu la norme sur le Web.

La modification globale de l’encodage d’un site nécessite plusieurs interventions, à plusieurs niveaux, sur ce site. On peut voir cela comme une chaîne, composée de quatre maillons : la base de données, le contenu des tables, le logiciel de blog, le site. S’il manque un des maillons, des erreurs d’affichage se produiront. Voyons donc les quatre maillons, en détails, pour Wordpress.

Premier maillon : la base de données

L’encodage utilisé par le serveur de base de données est une contrainte à prendre en compte lors de l’installation d’un logiciel d’édition Web. L’hébergeur du domaine Valhalla.fr, par exemple, avait paramétré le serveur MySQL 4 pour utiliser le charset Latin1 par défaut, lors de la mise en place de ce site sous Wordpress. Aujourd’hui, la version de production est MySQL 5, et l’encodage par défaut est UTF-8.

Il existe plusieurs manières de connaître l’encodage utilisé par défaut par MySQL, et l’encodage utilisé pour chacune des tables d’une base de données. Le plus simple, avec un hébergement mutualisé, est de se rendre sur la page d’accueil de phpMyAdmin – celui-ci est habituellement fourni par l’hébergeur, mais il est généralement possible de l’installer soi-même sur le serveur–.

Avec un accès SSH au serveur, la commande SHOW TABLE STATUS nom_de_la_base; [cf. documentation] permet d’afficher le charset de chacune des tables d’une base de données, sous cette forme :

wp_posts |MyISAM| 10 |Dynamic | 439 | 16576 | 7276888 | 281474976710655 | 45056 | 0 | 454 | 2010-03-20 12:48:04 | 2010-03-20 12:48:05 | 2010-03-20 12:48:05 | latin1_swedish_ci |

Pour commencer, il est toujours bon de créer une sauvegarde des données, et de travailler sur la sauvegarde plutôt que sur les données originales. Pour créer une sauvegarde, on peut utiliser 1) la ligne de commande, si l’on a un accès SSH au serveur ; 2) un logiciel client ; 3) un logiciel en ligne comme phpMyAdmin.

L’utilisation de la ligne de commande est souvent la meilleure solution. Elle nécessite toutefois un accès SSH au serveur, cet celui-ci est rarement fourni dans le cadre d’un hébergement mutualisé. Pour sauvegarde la base de données en ligne de commande, on utilisera l’instruction suivante :

mysqldump --opt -u nom_dutilisateur -p nom_de_la_base > ma_sauvegarde.sql

A défaut d’un accès SSH, on peut utiliser un logiciel client. Navicat (Windows/Mac/Linux) est connu pour son efficacité, tout comme EMS SQL manager et SQLYog (Windows-only). Il en existe également des gratuits, tel que Sequel Pro (Mac), Toad (Windows) ou encore ceux fournis par MySQL (Windows/Mac/Linux).

Enfin, s’il est impossible de contacter le serveur MySQL depuis le réseau, on utilisera phpMyAdmin ou un logiciel local équivalent. Ce n’est toutefois pas la meilleure solution, car elle impose de scinder la sauvegarde en plusieurs fichiers.

Une fois la base de données sauvegardée dans un fichier .sql, il faut éditer ce fichier, dans un éditeur de texte brut (NotePad sous Windows, TextEdit sous Mac, par exemple) et remplacer DEFAULT CHARSET = latin1 par DEFAULT CHARSET = utf8 dans tout le fichier. Ceci n’est pas à faire manuellement, mais en utilisant la fonction Rechercher et remplacer de l’éditeur de texte.

Reste à créer une nouvelle base de données vide, en spécifiant lors de la création qu’elle doit utiliser le charset UTF-8. Cela est possible avec les logiciels précités, ou en ligne de commande avec l’instruction suivante :

CREATE DATABASE ma_nouvelle_base DEFAULT CHARACTER SET utf8 COLLATE utf8_general_ci;

La nouvelle base étant créée, il reste à injecter les données provenant de la sauvegarde – c’est-à-dire le fichier .sql modifié à l’étape précédente. Encore une fois, on utilisera l’un ou l’autre des logiciels précités, ou la commande suivante, si l’accès SSH au serveur de base de données est possible :

mysql -u nom_dutilisateur -p ma_nouvelle_base < ma_sauvegarde.sql

Deuxième maillon : le contenu des tables

Il existe plusieurs manières de modifier le contenu des tables. Ouvrir le fichier de sauvegarde et modifier son encodage dans un éditeur de texte ne sera généralement pas suffisant.

La première manière est d’utiliser la fonction PHP iconv() sur le texte du fichier de sauvegarde :

iconv -f iso-8859-1 -t utf8 ma_sauvegarde_latin1.sql > ma_sauvegarde_utf8.sql

On peut également utiliser un script qui remplace les caractères un par un dans le fichier :

<?php
$source = file_get_contents('ma_sauvegarde_latin1.sql');
$destination = fopen('ma_sauvegarde_utf8.sql','wb');
fwrite($destination, "\xEF\xBB\xBF".utf8_encode($source));
fclose($destination);
?>

Après avoir modifié le fichier, on restaurera la sauvegarde dans la nouvelle base créée, comme indiqué ci-avant. La troisième solution est la plus élégante. Contrairement aux deux autres, elle doit être mise en oeuvre après l’insertion de la sauvegarde dans la base de données. Il s’agit de demander à MySQL (à partir de la version 5 seulement) d’opérer la conversion, grâce à l’instruction suivante :

ALTER TABLE ma_table CONVERT TO CHARACTER SET utf8;

Cette instruction peut être exécutée avec les logiciels précités, depuis n’importe quel script sur le serveur ou par la ligne de commande. Elle devra bien entendu être répétée pour chacune des tables de la base de données :

ALTER TABLE wp_comments CONVERT TO CHARACTER SET utf8;
ALTER TABLE wp_commentmeta CONVERT TO CHARACTER SET utf8;
ALTER TABLE wp_links CONVERT TO CHARACTER SET utf8;
ALTER TABLE wp_options CONVERT TO CHARACTER SET utf8;
ALTER TABLE wp_postmeta CONVERT TO CHARACTER SET utf8;
ALTER TABLE wp_term_relationships CONVERT TO CHARACTER SET utf8;
ALTER TABLE wp_term_taxonomy CONVERT TO CHARACTER SET utf8;
ALTER TABLE wp_terms CONVERT TO CHARACTER SET utf8;
ALTER TABLE wp_users CONVERT TO CHARACTER SET utf8;
ALTER TABLE wp_usermeta CONVERT TO CHARACTER SET utf8;
ALTER TABLE wp_posts CONVERT TO CHARACTER SET utf8;

Troisième maillon : le logiciel

Certains logiciels indiquent en dur, dans leurs fichiers de configuration, l’encodage utilisé. C’est le cas de Wordpress. Le fichier à éditer porte le nom de wp-config.php ; il se situe à la racine du répertoire d’installation de Wordpress.

Pour modifier l’encodage, il faut modifier –ou rajouter, le cas échéant– la ligne suivante (en début de fichier) :

define('DB_CHARSET', 'utf8');

Il faudra aussi, le cas échéant, demander à Wordpress d’utiliser les données de la nouvelle base, encodée en UTF-8 :

define('DB_NAME', 'ma_nouvelle_base_en_utf8');

Quatrième maillon : le site

Les pages générées par Wordpress (et par tous les autres logiciels d’édition) indiquent au navigateur du lecteur quel charset utiliser pour un affichage correct. Cette indication se situe dans l’en-tête du code HTML généré (pour le voir : clic-droit dans la page, et affichage du code source) :

<meta http-equiv="Content-Type" content="text/html; charset=UTF-8" />

Pour que Wordpress utilise UTF-8 dans cette instruction, il faut modifier la valeur de l’encodage dans l’interface d’administration de son site (mon_site/wp-admin), section Settings (Configuration), sous-section Reading (Lecture).
[L’adresse directe est la suivante : http://mon_site/wp-admin/options-reading.php].

Et voilà ! Après toutes ces opérations, qui peuvent rapidement se révéler un parcours du combattant, le site devrait s’afficher en UTF-8, avec tous les caractères spéciaux et accentués.

à Montpellier, le 20 mars 2010