Si vous voyez des boucles de redirection (“ERR_TOO_MANY_REDIRECTS”) ou un WordPress qui alterne entre http:// et https:// selon la page, le problème vient presque toujours d’un forçage HTTPS fait au mauvais endroit (ou deux fois), ou d’un proxy/CDN mal déclaré.
Le besoin / Le problème serveur
Vous avez installé un certificat SSL (Let’s Encrypt, Cloudflare, certificat payant). Le cadenas apparaît parfois, mais pas partout. Ou bien l’administration (/wp-admin) redirige en boucle. Ou encore Google indexe les deux versions (HTTP et HTTPS), ce qui crée du contenu dupliqué.
À la fin, vous saurez :
- forcer une redirection HTTP → HTTPS proprement, côté serveur (Apache ou Nginx), sans casser WordPress 6.9.4 ;
- verrouiller les URL WordPress au bon endroit (base de données / wp-config.php) ;
- gérer le cas fréquent “HTTPS derrière un proxy/CDN” (Cloudflare, reverse-proxy, load balancer) ;
- vérifier le résultat avec
curl, WP‑CLI et les logs serveur.
Je le dis tout de suite : le meilleur forçage HTTPS est celui fait au niveau du serveur web, avec une redirection unique et prévisible. Les “snippets” PHP qui redirigent au runtime finissent souvent en boucle, surtout avec cache, proxy, ou page builder.
Résumé rapide
- Forcez HTTPS côté serveur (Apache/Nginx) plutôt que via un plugin ou un snippet PHP.
- Assurez-vous que WordPress stocke bien des URL en
https://(optionshomeetsiteurl). - Si vous êtes derrière Cloudflare/proxy, corrigez la détection HTTPS dans
wp-config.php(sinon boucles). - Testez la redirection avec
curl -Iet vérifiez les headersLocationetStrict-Transport-Security. - Ne faites pas deux redirections concurrentes (ex. .htaccess + plugin + CDN), sinon boucle.
Avant de commencer (prérequis)
Vous allez toucher à des fichiers serveur. Une erreur de syntaxe peut mettre le site en erreur 500. Travaillez proprement.
Accès nécessaires
- SSH (recommandé) pour éditer les fichiers et lancer les commandes
curl, WP‑CLI. - FTP/SFTP au minimum pour modifier
.htaccessetwp-config.php. - Accès base de données (MySQL/MariaDB) via CLI (
mysql) ou phpMyAdmin, pour vérifier/ajusterhome/siteurl. - WP‑CLI (recommandé) pour lire/écrire les options sans passer par l’admin.
Sauvegarde obligatoire (avant toute modification)
Avant de modifier quoi que ce soit, faites une sauvegarde de la base et des fichiers. Voici des commandes typiques. Je les explique juste après.
Ce que font ces commandes : elles exportent la base WordPress (SQL) et créent une archive des fichiers WordPress (tar.gz). Vous pourrez revenir en arrière si vous cassez la redirection.
# 1) Sauvegarde de la base via WP-CLI (depuis la racine WordPress)
wp db export ~/backup-wp-https-$(date +%F).sql
# 2) Sauvegarde des fichiers (uploads + code)
tar -czf ~/backup-wp-files-https-$(date +%F).tar.gz .
Versions et environnement
- WordPress : 6.9.4 (avril 2026).
- PHP : 8.1+ (8.2/8.3 souvent en prod ; évitez 7.x, beaucoup de snippets anciens cassent).
- Serveur web : Apache (avec mod_rewrite) ou Nginx.
- Si vous utilisez un CDN/proxy (Cloudflare, Fastly, reverse proxy), notez-le : ça change la détection de HTTPS côté PHP.
Sources officielles utiles : WordPress HTTPS (Advanced Administration), WP‑CLI Commands, Apache mod_rewrite, Nginx rewrite module, PHP $_SERVER.
Étape 1 : Confirmer que le SSL est OK et identifier le “front” (Apache, Nginx, proxy)
Avant de forcer HTTPS, vous devez vérifier deux choses : (1) le certificat est servi correctement, (2) qui répond réellement aux requêtes (Apache, Nginx, ou un proxy devant).
Vérifier le certificat et la chaîne TLS
Ce que fait la commande : openssl s_client ouvre une connexion TLS et affiche le certificat présenté. C’est le moyen le plus direct de voir si le bon cert est servi.
# Remplacez example.com par votre domaine
echo | openssl s_client -servername example.com -connect example.com:443 2>/dev/null | openssl x509 -noout -subject -issuer -dates
Vérifier la redirection actuelle (ou son absence)
Ce que fait la commande : curl -I récupère uniquement les en-têtes HTTP. Vous voulez voir un 301 (ou 308) depuis HTTP vers HTTPS, puis un 200 final.
curl -I http://example.com/
curl -I https://example.com/
Identifier si vous êtes derrière un proxy/CDN
Si votre hébergement a Cloudflare activé, ou un load balancer, votre serveur web peut recevoir du HTTP même si l’utilisateur est en HTTPS. Dans ce cas, WordPress voit $_SERVER['HTTPS'] vide et génère des URL en http://, ce qui déclenche des boucles.
Indice rapide : si curl -I https://example.com renvoie un header server: cloudflare ou des headers cf-ray, vous êtes probablement derrière Cloudflare.
Étape 2 : Forcer HTTPS au niveau serveur (recommandé)
Le but : une seule règle de redirection, au tout début du cycle, avant WordPress, avant PHP, avant le cache applicatif. C’est plus rapide et plus stable.
Cas A — Apache (.htaccess) sur hébergement mutualisé
Sur Apache, la solution la plus courante (et compatible mutualisé) est un bloc mod_rewrite dans .htaccess à la racine WordPress. Cette règle redirige toute requête HTTP vers HTTPS, en conservant le chemin et la query string.
Où coller le code : dans /.htaccess, au-dessus du bloc WordPress “BEGIN WordPress”. Si vous le mettez en dessous, WordPress peut réécrire avant vous selon les règles.
# Éditez .htaccess (exemple avec nano)
nano .htaccess
Ajoutez (ou adaptez) :
# --- Forcer HTTPS (à placer AVANT le bloc WordPress) ---
<IfModule mod_rewrite.c>
RewriteEngine On
# Si la connexion n'est pas HTTPS, on redirige vers HTTPS
RewriteCond %{HTTPS} !=on
RewriteRule ^ https://%{HTTP_HOST}%{REQUEST_URI} [L,R=301]
</IfModule>
# --- Fin forçage HTTPS ---
Résultat attendu : curl -I http://example.com doit retourner 301 avec Location: https://example.com/....
Pourquoi je n’ajoute pas “www → non-www” ici ?
Parce que les débutants empilent souvent : HTTP→HTTPS et non-www→www et redirection via plugin et redirection CDN. Faites d’abord HTTPS seul. Ensuite seulement, ajoutez une canonicalisation (www ou non-www) si nécessaire, en une seule règle.
Cas B — Nginx (server block) sur VPS / cloud
Avec Nginx, vous ne touchez pas à .htaccess (il n’est pas lu). Vous devez ajouter un server block sur le port 80 qui redirige vers 443.
Ce que vous allez faire : créer (ou modifier) deux blocs : un pour :80 qui redirige, un pour :443 qui sert WordPress en TLS.
# Tester la conf avant reload (ne sautez pas cette étape)
sudo nginx -t
Exemple minimal (à adapter à votre distro : Debian/Ubuntu souvent dans /etc/nginx/sites-available/) :
# /etc/nginx/sites-available/example.com.conf
server {
listen 80;
listen [::]:80;
server_name example.com www.example.com;
# Redirection permanente vers HTTPS
return 301 https://$host$request_uri;
}
server {
listen 443 ssl http2;
listen [::]:443 ssl http2;
server_name example.com www.example.com;
root /var/www/example.com/public;
index index.php index.html;
# Certificats (exemple Let's Encrypt)
ssl_certificate /etc/letsencrypt/live/example.com/fullchain.pem;
ssl_certificate_key /etc/letsencrypt/live/example.com/privkey.pem;
# WordPress : try_files classique
location / {
try_files $uri $uri/ /index.php?$args;
}
location ~ .php$ {
include snippets/fastcgi-php.conf;
fastcgi_pass unix:/run/php/php8.2-fpm.sock;
}
# Sécurité basique : empêcher l'accès à certains fichiers
location ~* /(wp-config.php|readme.html|license.txt)$ {
deny all;
}
}
Ensuite :
sudo nginx -t
sudo systemctl reload nginx
Cas C — Vous avez déjà une redirection au niveau CDN/proxy
Si Cloudflare (ou autre) force déjà HTTPS, vous pouvez choisir de laisser le CDN gérer la redirection. Dans ce cas, évitez d’ajouter une seconde redirection côté origin si vous n’êtes pas sûr de la chaîne. En pratique, j’ai souvent vu :
- CDN force HTTPS côté visiteur,
- origin reçoit HTTP,
- WordPress croit être en HTTP et redirige vers HTTP,
- CDN re-force HTTPS… boucle.
Si vous êtes dans ce cas, passez directement à l’étape wp-config.php derrière proxy.
Étape 3 : Verrouiller les URL WordPress (WordPress Address / Site Address)
WordPress stocke deux URL clés :
- siteurl : l’URL où se trouve WordPress (souvent la racine).
- home : l’URL publique du site.
Si l’une est en http:// et l’autre en https://, vous aurez des redirections incohérentes, des assets en mixte, et parfois des boucles sur /wp-admin.
Vérifier via WP‑CLI
Ce que fait la commande : lire les options directement en base, sans passer par wp-admin (utile si l’admin boucle).
wp option get home
wp option get siteurl
Pour corriger :
# Remplacez par votre domaine exact
wp option update home "https://example.com"
wp option update siteurl "https://example.com"
Vérifier via MySQL (si WP‑CLI indisponible)
Ce que fait la commande : interroger la table wp_options. Si votre préfixe n’est pas wp_, adaptez.
mysql -u DBUSER -p DBNAME -e "SELECT option_name, option_value FROM wp_options WHERE option_name IN ('home','siteurl');"
Pour mettre à jour :
mysql -u DBUSER -p DBNAME -e "UPDATE wp_options SET option_value='https://example.com' WHERE option_name IN ('home','siteurl');"
Cas “je ne peux plus me connecter” après changement d’URL
Ça arrive si vous avez forcé un domaine différent (www vs non-www) ou si un proxy modifie le host. Revenez en arrière en remettant l’ancienne valeur via MySQL, puis fixez la canonicalisation au niveau serveur (une seule règle).
Étape 4 : Corriger wp-config.php (HTTPS derrière proxy / load balancer)
Quand un proxy termine le TLS (HTTPS côté visiteur) et parle en HTTP à l’origin, PHP voit une requête HTTP. WordPress 6.9.4 se base sur des variables serveur (ex. $_SERVER['HTTPS'], $_SERVER['SERVER_PORT']) et sur certains headers (ex. X-Forwarded-Proto) selon la config. Si ces infos ne sont pas cohérentes, WordPress génère des URL en http://, et votre redirection serveur repart… boucle.
La correction la plus courante (X-Forwarded-Proto)
Où coller le code : dans wp-config.php, avant la ligne /* That's all, stop editing! */. Ne collez pas ça dans functions.php : c’est trop tard (WordPress a déjà pris des décisions).
Ce que fait ce snippet : si le proxy envoie X-Forwarded-Proto: https, on force $_SERVER['HTTPS']='on' pour que WordPress se comporte comme en HTTPS.
<?php
// ... votre wp-config.php ...
/**
* Détection HTTPS derrière proxy / load balancer.
* À utiliser si votre reverse-proxy termine le TLS et parle en HTTP à l'origin.
*
* Risque : si un attaquant peut forger ces headers jusqu'à PHP (proxy mal configuré),
* vous pouvez avoir des comportements inattendus. À activer uniquement si vous savez
* que ces headers sont injectés par un proxy de confiance.
*/
if (
! empty($_SERVER['HTTP_X_FORWARDED_PROTO'])
&& strpos($_SERVER['HTTP_X_FORWARDED_PROTO'], 'https') !== false
) {
$_SERVER['HTTPS'] = 'on';
}
// Optionnel : si votre proxy fournit le port
if (! empty($_SERVER['HTTP_X_FORWARDED_PORT']) && $_SERVER['HTTP_X_FORWARDED_PORT'] === '443') {
$_SERVER['SERVER_PORT'] = '443';
}
// ... le reste du fichier ...
/* That's all, stop editing! Happy publishing. */
Variante Cloudflare (CF-Visitor)
Cloudflare peut envoyer CF-Visitor contenant {"scheme":"https"}. Je préfère X-Forwarded-Proto quand il est fiable, mais sur certains setups Cloudflare-only, ce test dépanne.
<?php
// ... votre wp-config.php ...
/**
* Détection HTTPS derrière Cloudflare.
* À utiliser seulement si vous êtes certain que le trafic passe par Cloudflare.
*/
if (! empty($_SERVER['HTTP_CF_VISITOR']) && strpos($_SERVER['HTTP_CF_VISITOR'], 'https') !== false) {
$_SERVER['HTTPS'] = 'on';
}
Verrouiller home/siteurl via wp-config.php (option “anti-dérive”)
Si votre base est modifiée par un script, une migration, ou un plugin, vous pouvez verrouiller les URL dans wp-config.php. C’est utile sur des environnements staging/production où l’on veut éviter qu’un import SQL remette du http://.
Effet : WordPress utilisera ces constantes, même si la base contient autre chose.
<?php
// ... votre wp-config.php ...
/**
* Verrouille les URL du site.
* Pratique si des migrations réinjectent du http:// dans la base.
*/
define('WP_HOME', 'https://example.com');
define('WP_SITEURL', 'https://example.com');
Je l’utilise souvent sur des sites qui ont une chaîne de déploiement (staging → prod). Sur un blog simple, ce n’est pas obligatoire, mais ça évite des surprises.
Étape 5 : Nettoyer le contenu mixte et les redirections (sans plugin)
Une fois la redirection en place, vous pouvez encore voir “contenu mixte” : la page est en HTTPS, mais charge des images/scripts en HTTP. Ça ne se corrige pas avec .htaccess : il faut corriger les URL stockées.
Identifier les URL http:// dans la base
Ce que fait la commande : wp search-replace remplace des chaînes dans la base, en gérant la sérialisation PHP (crucial pour WordPress). Évitez de faire un simple UPDATE ... REPLACE() si vous ne maîtrisez pas : vous pouvez casser des données sérialisées.
# Dry-run : liste ce qui serait remplacé, sans modifier
wp search-replace 'http://example.com' 'https://example.com' --all-tables --dry-run
Si le dry-run est cohérent :
# Remplacement réel
wp search-replace 'http://example.com' 'https://example.com' --all-tables
Si vous aviez un changement www → non-www (ou l’inverse), faites-le en même temps, sinon vous créez une chaîne de redirections inutile :
# Exemple : http://www → https:// (sans www)
wp search-replace 'http://www.example.com' 'https://example.com' --all-tables
wp search-replace 'https://www.example.com' 'https://example.com' --all-tables
Cas Divi 5 / Elementor / Avada : où se cache le “http://”
Les page builders stockent beaucoup de contenu en base (parfois sérialisé, parfois JSON). WP‑CLI gère bien la plupart des cas, mais vous devez penser à :
- vider les caches du builder (Divi 5, Elementor, Avada) après remplacement ;
- regénérer les fichiers CSS/JS si le builder en produit ;
- vider le cache serveur (FastCGI cache, Varnish) si activé.
Je vois souvent des gens faire le search-replace, puis conclure “ça ne marche pas” parce que leur CDN sert encore l’ancienne version en cache.
Fichiers de configuration complets
Cette section donne des versions “prêtes à copier-coller” des fichiers typiques. Adaptez le domaine, les chemins, et testez avant reload.
.htaccess complet (WordPress sur Apache)
Où : à la racine WordPress (public_html/.htaccess souvent). Cette version inclut :
- forçage HTTPS,
- bloc WordPress standard,
- quelques protections simples.
# .htaccess (Apache) — WordPress 6.9.4+
# Sauvegardez ce fichier avant modification.
# --- Forcer HTTPS (AVANT WordPress) ---
<IfModule mod_rewrite.c>
RewriteEngine On
# Redirige tout HTTP vers HTTPS
RewriteCond %{HTTPS} !=on
RewriteRule ^ https://%{HTTP_HOST}%{REQUEST_URI} [L,R=301]
</IfModule>
# --- Fin forçage HTTPS ---
# --- Protections simples ---
# Empêche le listing de répertoires
Options -Indexes
# Empêche l'accès aux fichiers sensibles
<FilesMatch "^(wp-config.php|.env|.htaccess)$">
Require all denied
</FilesMatch>
# --- BEGIN WordPress ---
# Les directives (lignes) entre "BEGIN WordPress" et "END WordPress" sont
# générées dynamiquement et doivent être modifiées uniquement via WordPress.
<IfModule mod_rewrite.c>
RewriteEngine On
RewriteRule .* - [E=HTTP_AUTHORIZATION:%{HTTP:Authorization}]
RewriteBase /
RewriteRule ^index.php$ - [L]
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
RewriteRule . /index.php [L]
</IfModule>
# --- END WordPress ---
nginx.conf (server blocks) complet (WordPress sur Nginx)
Où : un fichier de site dans /etc/nginx/sites-available/. Exemple relativement standard, compatible PHP‑FPM.
# /etc/nginx/sites-available/example.com.conf
server {
listen 80;
listen [::]:80;
server_name example.com www.example.com;
# Forcer HTTPS
return 301 https://$host$request_uri;
}
server {
listen 443 ssl http2;
listen [::]:443 ssl http2;
server_name example.com www.example.com;
root /var/www/example.com/public;
index index.php index.html;
# TLS (Let's Encrypt)
ssl_certificate /etc/letsencrypt/live/example.com/fullchain.pem;
ssl_certificate_key /etc/letsencrypt/live/example.com/privkey.pem;
# Taille upload (adaptez)
client_max_body_size 64m;
# WordPress
location / {
try_files $uri $uri/ /index.php?$args;
}
# PHP
location ~ .php$ {
include snippets/fastcgi-php.conf;
# Adaptez à votre version PHP-FPM
fastcgi_pass unix:/run/php/php8.2-fpm.sock;
# Important pour WordPress (PATH_INFO)
fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
}
# Bloquer l'accès à des fichiers sensibles
location ~* /(wp-config.php|.env|readme.html|license.txt)$ {
deny all;
}
# Cache statique basique (optionnel)
location ~* .(css|js|jpg|jpeg|png|gif|webp|svg|ico)$ {
expires 7d;
add_header Cache-Control "public, max-age=604800";
try_files $uri =404;
}
}
wp-config.php (extrait complet centré HTTPS)
Où : /wp-config.php. Ne modifiez jamais des fichiers du core WordPress. Celui-ci est fait pour être édité.
<?php
/**
* Extrait wp-config.php — focalisé HTTPS / proxy.
* Compatible WordPress 6.9.4+ et PHP 8.1+.
*/
// Détection HTTPS derrière proxy / load balancer
if (
! empty($_SERVER['HTTP_X_FORWARDED_PROTO'])
&& strpos($_SERVER['HTTP_X_FORWARDED_PROTO'], 'https') !== false
) {
$_SERVER['HTTPS'] = 'on';
}
// Verrouillage des URL (optionnel mais robuste)
define('WP_HOME', 'https://example.com');
define('WP_SITEURL', 'https://example.com');
// Forcer SSL sur l'admin (utile si vous avez des règles réseau particulières)
define('FORCE_SSL_ADMIN', true);
/* That's all, stop editing! Happy publishing. */
php.ini (extrait utile côté HTTPS)
Ce n’est pas obligatoire pour forcer HTTPS, mais je l’ajoute parce que beaucoup de problèmes “SSL” sont en réalité des timeouts ou des uploads qui échouent pendant la migration HTTPS (search-replace, régénération CSS/JS).
; php.ini (extrait) — adaptez à votre hébergement
memory_limit = 256M
max_execution_time = 120
post_max_size = 64M
upload_max_filesize = 64M
Vérification
Le but ici est de prouver que :
- HTTP redirige vers HTTPS en une seule étape ;
- WordPress génère bien des URL en HTTPS ;
- vous n’avez pas de boucle proxy/CDN ;
- les headers et caches ne vous mentent pas.
Tester la redirection (HTTP → HTTPS)
Ce que fait la commande : suit les redirections et affiche les headers à chaque étape.
curl -IL http://example.com/
Ce que vous voulez voir :
- une première réponse
301ou308avecLocation: https://example.com/; - puis un
200final en HTTPS ; - pas de ping-pong http↔https.
Vérifier les URL WordPress côté base
wp option get home
wp option get siteurl
Vérifier que WordPress “croit” être en HTTPS
Ce que fait la commande : exécute un petit PHP via WP‑CLI et affiche des valeurs utiles. Pratique quand vous êtes derrière proxy.
wp eval 'var_dump(is_ssl()); var_dump($_SERVER["HTTPS"] ?? null); var_dump($_SERVER["HTTP_X_FORWARDED_PROTO"] ?? null);'
Vérifier HSTS (si vous l’activez plus tard)
Si vous ajoutez HSTS (voir section sécurité), testez :
curl -I https://example.com/ | grep -i strict-transport-security
Si ça ne marche pas
Quand HTTPS “ne marche pas”, je cherche toujours dans cet ordre : (1) boucle de redirections, (2) mauvais host, (3) proxy, (4) cache, (5) contenu mixte.
Diagnostic par étapes (rapide et fiable)
1) Vous avez une boucle “ERR_TOO_MANY_REDIRECTS”
Vérification :
curl -IL http://example.com/ | sed -n '1,20p'
curl -IL https://example.com/ | sed -n '1,40p'
Ce que vous cherchez : une alternance Location: http://... puis Location: https://.... Si oui, vous avez deux systèmes qui se contredisent.
Solution typique :
- désactivez temporairement la redirection côté CDN (ou côté origin) pour n’en garder qu’une ;
- ajoutez la détection proxy dans
wp-config.php(étape 4) ; - videz les caches (CDN + serveur + plugin de cache si présent).
2) Vous obtenez une erreur 500 après modification de .htaccess
Vérification : une erreur 500 juste après édition est souvent une directive Apache non autorisée sur mutualisé (ou une faute de syntaxe).
À faire : restaurez le fichier, puis ré-appliquez le bloc minimal.
# Restaurer depuis une sauvegarde si vous en avez une
cp .htaccess.bak .htaccess
Logs utiles (si vous avez accès) :
# Chemins variables selon distro/hébergeur
sudo tail -n 200 /var/log/apache2/error.log
sudo tail -n 200 /var/log/nginx/error.log
3) Le site est en HTTPS mais wp-admin renvoie en HTTP
Ça sent le proxy mal détecté ou un siteurl resté en HTTP.
Vérification :
wp option get siteurl
wp eval 'var_dump(is_ssl());'
Solution : mettez siteurl en https et ajoutez le snippet proxy si nécessaire.
4) Le cadenas est là mais vous avez du “contenu non sécurisé”
Vérification : cherchez des http://votredomaine en base.
wp search-replace 'http://example.com' 'https://example.com' --all-tables --dry-run
Solution : faites le remplacement réel, puis purgez caches et régénérez les assets du builder.
Tableau de diagnostic (symptômes réalistes)
| Symptôme | Cause probable | Vérification | Solution |
|---|---|---|---|
| Boucle infinie (ERR_TOO_MANY_REDIRECTS) | Redirection doublée (CDN + .htaccess + plugin) ou proxy non détecté | curl -IL http://… et observer les Location |
Garder une seule redirection côté serveur, ajouter détection proxy dans wp-config.php |
| Le site charge en HTTPS mais certaines pages reviennent en HTTP | home/siteurl incohérents, ou URL hardcodées dans le builder |
wp option get home siteurl, wp search-replace --dry-run |
Mettre les deux en HTTPS, faire un search-replace, vider caches |
| Erreur 500 après édition .htaccess | Syntaxe incorrecte ou directives interdites | Restaurer .htaccess, lire error.log |
Revenir au bloc minimal mod_rewrite, supprimer directives non supportées |
| wp-admin redirige en HTTP | Proxy TLS, WordPress ne voit pas HTTPS | wp eval 'var_dump(is_ssl());' |
Snippet X-Forwarded-Proto dans wp-config.php |
| Après migration, images cassées / mixte | Anciennes URL en base + cache | wp search-replace + test navigateur privé |
Search-replace + purge CDN/serveur + regen assets Divi/Elementor/Avada |
Pièges et erreurs courantes
- Copier la règle .htaccess au mauvais endroit : si vous la mettez après “BEGIN WordPress”, vous pouvez obtenir des comportements bizarres selon les règles générées. Placez-la avant.
- Oublier de sauvegarder : un
.htaccesscassé peut bloquer l’accès au site et à l’admin. Gardez un.htaccess.bak. - Faire la redirection en PHP (functions.php) : ça arrive trop tard, et vous pouvez créer des boucles avec le cache. Si vous devez absolument le faire, faites-le dans un mu-plugin et uniquement en dernier recours, mais je ne le recommande pas ici.
- Utiliser un vieux snippet incompatible : beaucoup de tutos datent de PHP 5/7 et utilisent des patterns fragiles. En 2026 (WP 6.9.4, PHP 8.1+), restez sur des règles serveur simples et des constantes
WP_HOME/WP_SITEURL. - Ne pas vider les caches : cache navigateur, cache plugin, cache Nginx FastCGI, Varnish, CDN. Testez en navigation privée et avec
curl(qui ignore votre cache navigateur). - Confondre “forcer HTTPS” et “corriger le mixte” : la redirection ne réécrit pas vos contenus stockés. Le mixte se corrige via search-replace.
- Tester directement en production sans fenêtre de retour : faites vos changements à un moment où vous pouvez intervenir (et idéalement sur un staging).
Sécurité serveur
Forcer HTTPS, c’est bien. Le faire proprement, c’est mieux. Voici des ajouts fréquents côté serveur une fois que tout est stable.
Activer HSTS (avec prudence)
HSTS (HTTP Strict Transport Security) dit au navigateur : “ce domaine doit toujours être en HTTPS”. C’est efficace contre certaines attaques (downgrade), mais dangereux si vous cassez votre HTTPS ensuite (vous vous enfermez).
Je conseille de commencer avec une durée courte, sans includeSubDomains, puis d’augmenter.
Apache (dans la vhost, idéalement ; à défaut .htaccess si autorisé)
# Ajoute HSTS (durée 1 jour pour démarrer)
Header always set Strict-Transport-Security "max-age=86400"
Nginx
# Dans le server { ... } :443
add_header Strict-Transport-Security "max-age=86400" always;
Forcer des cookies sécurisés (WordPress)
WordPress gère déjà beaucoup de choses, mais si vous êtes derrière proxy et que vous avez eu des soucis de cookies, vérifiez que l’admin est bien en SSL et que FORCE_SSL_ADMIN est à true (voir extrait wp-config.php plus haut).
Permissions fichiers (rappel utile)
Des permissions trop permissives facilitent l’exploitation en cas de faille plugin. Valeurs courantes :
- répertoires : 755
- fichiers : 644
wp-config.php: parfois 640 selon votre modèle d’utilisateurs/groupes
# Exemple (à adapter à votre hébergement et user/group)
find . -type d -exec chmod 755 {} ;
find . -type f -exec chmod 644 {} ;
Headers utiles (hors HSTS)
Ce n’est pas spécifique HTTPS, mais souvent configuré en même temps :
X-Content-Type-Options: nosniffReferrer-PolicyContent-Security-Policy(plus délicat, à tester)
Référence : WordPress Security (Advanced Administration).
Ressources
- WordPress Advanced Administration: HTTPS
- WP‑CLI: Commands
- WordPress.org: Editing wp-config.php
- Apache HTTP Server: mod_rewrite
- Nginx: ngx_http_rewrite_module
- PHP: $_SERVER
- GitHub: WordPress core (wordpress-develop)
FAQ
Est-ce que je dois forcer HTTPS dans WordPress ou dans .htaccess/Nginx ?
Côté serveur. La redirection se fait avant PHP, c’est plus rapide et ça évite des boucles avec cache/proxy. WordPress doit surtout avoir home et siteurl en HTTPS.
Pourquoi mon HTTPS marche sur la home mais pas sur /wp-admin ?
Souvent parce que WordPress ne détecte pas HTTPS (proxy/CDN), ou parce que siteurl est resté en HTTP. Vérifiez avec wp option get siteurl et le test wp eval 'var_dump(is_ssl());'.
Dois-je ajouter FORCE_SSL_ADMIN dans wp-config.php ?
Oui si vous avez eu des comportements incohérents sur l’admin. Ça n’est pas une redirection globale, mais ça force l’admin à se comporter en SSL.
Je suis sur Nginx : pourquoi le .htaccess ne fait rien ?
Nginx n’interprète pas .htaccess. Il faut configurer la redirection dans le server block Nginx (port 80 → 443).
Quel code .htaccess est le plus “safe” pour débuter ?
Le bloc minimal : RewriteCond %{HTTPS} !=on puis RewriteRule ^ https://%{HTTP_HOST}%{REQUEST_URI}. Évitez de mélanger avec www/non-www tant que vous n’avez pas validé HTTPS.
Pourquoi j’ai “ERR_TOO_MANY_REDIRECTS” après avoir activé Cloudflare ?
Cloudflare termine le TLS et votre origin reçoit du HTTP. WordPress croit être en HTTP et redirige mal. Ajoutez la détection X-Forwarded-Proto dans wp-config.php et évitez les redirections doublées.
Est-ce que je peux corriger le contenu mixte uniquement avec une redirection ?
Non. La redirection ne change pas les URL stockées dans vos contenus. Faites un wp search-replace (avec dry-run d’abord).
Le search-replace MySQL “REPLACE()” marche-t-il ?
Ça peut casser des données sérialisées (widgets, options, builders). Utilisez plutôt wp search-replace qui gère la sérialisation.
Divi 5 / Elementor / Avada : dois-je refaire quelque chose après migration HTTPS ?
Oui : purge des caches du builder et régénération des assets si disponible. Sinon vous pouvez continuer à servir des CSS/JS référencés en HTTP depuis un cache.
Dois-je activer HSTS tout de suite ?
Attendez que tout soit stable. Commencez avec un max-age faible (ex. 86400), testez, puis augmentez. HSTS peut vous bloquer si votre HTTPS casse.
Où est l’erreur la plus fréquente quand on suit un tutoriel HTTPS ?
Empiler plusieurs forçages (plugin + .htaccess + CDN) et oublier que le proxy change la perception de HTTPS côté PHP. Faites une seule redirection serveur, puis corrigez wp-config.php si vous êtes derrière proxy.