web-dev-qa-db-fra.com

Étapes pour optimiser WordPress par rapport à la charge du serveur?

Outre l'installation de W3 Total Cache ou d'un autre plug-in de mise en cache, quelles étapes puis-je suivre pour que mon thème et mon site s'exécutent aussi vite que possible?.

80
Paul Sheldrake

Vous pouvez installer WordPress sur Nginx. Il existe un certain nombre de ressources pour vous aider:

Certaines informations de performance de ce dernier lien (qui semble être un peu différent de la configuration):

J'ai donc décidé de placer un proxy devant wordpress dans le cache statique autant que possible. TOUT le trafic non authentifié est servi directement à partir du cache de fichiers nginx, certaines requêtes (telles que la génération de flux RSS) allant de 6 pages/seconde à plus de 7000 pages/seconde. Oof. Nginx prend également en charge la journalisation et le gzipping, laissant ainsi aux plus lourds apaches les moyens de faire ce qu’ils font le mieux: servir des pages wordpress dynamiques uniquement lorsque cela est nécessaire.

...

Sur nginx - c’est tellement efficace que c’est effrayant. Je ne l’ai jamais vu utiliser plus de 10 à 15 mégaoctets de RAM et un peu d’UC, même sous notre charge la plus lourde. Nos graphiques ganglia ne mentent pas: nous avons réduit de moitié nos besoins en mémoire, doublé le débit de notre réseau sortant et entièrement nivelé notre charge de travail. Nous n’avons eu pratiquement aucun problème depuis que nous avons mis cela en place.

31
Travis Northcutt

Définissez les expirations côté client pour des éléments tels que css, images, JavaScript, etc. qu'il n'est pas nécessaire de télécharger à nouveau pour chaque affichage de page. Cela a de loin fait la plus grande différence dans les temps de chargement de mon site. Le téléchargement le plus rapide est le téléchargement qui n'est jamais arrivé ...

# BEGIN Expire headers
<IfModule mod_expires.c>
  ExpiresActive On
  ExpiresDefault "access plus 7200 seconds"
  ExpiresByType image/x-icon "access plus 2592000 seconds"
  ExpiresByType image/jpeg "access plus 2592000 seconds"
  ExpiresByType image/png "access plus 2592000 seconds"
  ExpiresByType image/gif "access plus 2592000 seconds"
  ExpiresByType application/x-shockwave-flash "access plus 2592000 seconds"
  ExpiresByType text/css "access plus 2592000 seconds"
  ExpiresByType text/javascript "access plus 2592000 seconds"
  ExpiresByType application/x-javascript "access plus 2592000 seconds"
  ExpiresByType text/html "access plus 7200 seconds"
  ExpiresByType application/xhtml+xml "access plus 7200 seconds"
</IfModule>
# END Expire headers

# BEGIN Cache-Control Headers
<IfModule mod_headers.c>
  <FilesMatch "\\.(ico|jpe?g|png|gif|swf|gz)$">
    Header set Cache-Control "max-age=2592000, public"
  </FilesMatch>
  <FilesMatch "\\.(css)$">
    Header set Cache-Control "max-age=2592000, public"
  </FilesMatch>
  <FilesMatch "\\.(js)$">
    Header set Cache-Control "max-age=2592000, private"
  </FilesMatch>
<filesMatch "\\.(html|htm)$">
Header set Cache-Control "max-age=7200, public"
</filesMatch>
# Disable caching for scripts and other dynamic files
<FilesMatch "\.(pl|php|cgi|spl|scgi|fcgi)$">
Header unset Cache-Control
</FilesMatch>
</IfModule>
# END Cache-Control Headers

Vous pouvez pré-gzip tout ce que vous pouvez raisonnablement (7-Zip est un bon outil pour cela) et le télécharger au même endroit que le fichier que vous venez de gzipper. Changez .htaccess pour servir les fichiers pré-compressés, comme ci-dessous. La mise en garde ici est que vous devez vous rappeler de re-gzip-les si/lorsque vous mettez à jour les choses. Cela évite la surcharge du processeur, en plus de l’analyse .htaccess.

RewriteEngine on
#Check to see if browser can accept gzip files. If so and we have it - serve it!
ReWriteCond %{HTTP:accept-encoding} gzip
RewriteCond %{HTTP_USER_AGENT} !Safari
#make sure there's no trailing .gz on the url
ReWriteCond %{REQUEST_FILENAME} !^.+\.gz$
#check to see if a .gz version of the file exists.
RewriteCond %{REQUEST_FILENAME}.gz -f
#All conditions met so add .gz to URL filename (invisibly)
RewriteRule ^(.+) $1.gz [QSA,L]

Ceci est juste une réponse brute. Il y a beaucoup de variations sur ce thème. J'ai blogué à ce sujet et ajouté de nombreuses références à des articles plus approfondis sur http://icanhazdot.net/2010/03/23/some-wordpress-stuff/ . Lisez cela et, plus important encore, les références que je signale - ce sont de bonnes ressources.

Sachez que si vous bricolez souvent, les utilisateurs devront actualiser leur cache.

Un plugin que j'ai trouvé très utile aussi est wp-minify . La chose à surveiller avec celui-ci est que vous devez exclure les éléments spécifiques à la page (formulaire de contact, curseur de page avant, etc.) afin de ne pas télécharger à nouveau l'ensemble des fichiers CSS, JS, etc. pour chaque page. C'est un bon moyen de réduire, de combiner et de compresser vos CSS, JS, etc. de base. Cela réduit beaucoup le nombre de requêtes http. Wp-minify fonctionne bien avec les supercaches et les en-têtes d'expiration décrits plus haut.

Utilisez Yslow dans Firebug (Firefox) ou similaire pour surveiller vos demandes http et ce qui est compressé et non compressé. Consultez également les en-têtes d'expiration. Vous verrez bientôt ce que vous pouvez améliorer.

26
CAD bloke

Minimisez le nombre de plugins que vous exécutez pour ne donner que ce dont vous avez vraiment besoin. Soyez particulièrement conscient des plugins qui ajoutent du code javascript et CSS à chaque chargement de page, même lorsque ce code n'est pas utilisé sur la page.

Si vous créez votre propre thème à partir de rien, décomposez votre CSS afin que les fonctionnalités qui ne nécessitent que des modèles de page ou types de vues particuliers (publication unique, archives, catégorie, etc.) ne soient chargées que lorsque cela est nécessaire.

Configurez W3TC pour utiliser un CDN (comme Amazon CloudFront ou tout autre support pris en charge par W3TC).

Voyez si les options Minify fonctionnent pour vous (certains plugins génèrent des fichiers js/css qui ne se minident pas très bien, alors assurez-vous de tester votre site après avoir activé la fonctionnalité minify).

Si vous avez le plein contrôle de votre serveur MySQL, assurez-vous que le query_cache est activé. Utilisez un script d’ajustement MySQL pour trouver d’autres moyens d’optimiser la configuration de votre base de données.

Si utiliser un CDN est problématique pour une raison quelconque, configurez mod_expires dans votre configuration Apache. Définissez des délais d'expiration aussi raisonnables que possible pour les types statiques tels que images, css, javascript, vidéo, audio, etc.

21
Dougal Campbell

Exécutez memcached et utilisez un object cache pour réduire le nombre de requêtes de base de données. Cela met en cache les données de la base de données plutôt que les pages. Pas sûr si w3-total-cache le fait déjà.

Assurez-vous d’exécuter un cache opcode tel que APC . (Il y en a plusieurs autres disponibles.)

14
Annika Backstrom

En plus d'utiliser un plug-in de mise en cache du disque tel que wp-cache, placez votre blog sur un volume hôte sur lequel la propriété "noatime" est définie. Sinon, SSH dans votre hôte (si votre hébergeur Web le fournit) et exécutez régulièrement cette commande sur vos fichiers tous les quelques jours:

chattr -R +A ~/*

Le ~/* signifie "mes fichiers dans mon répertoire personnel". Vous pouvez changer ce chemin comme bon vous semble. Vous pouvez également configurer cela sur un travail cron dans cpanel si votre hébergeur Web le fournit.

Pour plus d'informations sur la propriété atime, voir this . Cela accélère considérablement les performances de lecture des disques Linux.

Parfois, votre site est martelé par des araignées. Vous pouvez utiliser un outil tel que SpyderSpanker ou Chennai Central pour filtrer les araignées qui n'aident pas à augmenter le nombre de pages de votre site, mais simplement à le ralentir, puis à étrangler les bonnes araignées (telles que Google, Bing, etc.) en leur envoyant des messages aléatoires. Messages HTTP 304 non modifiés.

Une autre chose que je vois est juste des plugins mal écrits. Si vous apprenez à créer des plugins, vous commencez à voir comment certains plugins sont codés de manière inefficace, ou même à trouver des bombes temporelles, telles qu'une table de base de données qui se remplit et ne se nettoie jamais, stockant des données telles que les données de connexion entrantes.

Au-delà de toutes les autres solutions proposées ici, vous pouvez également créer une ferme Web WordPress de votre blog en l’hébergeant sur plusieurs PC avec nœud Web qui se reconnectent tous à une seule base de données et à un seul volume de disque pour les fichiers (comme un volume monté sur NFS). ). Découvrez Ultra Monkey pour savoir comment tout mettre en œuvre.

8
Volomike

Quelques réponses spontanées:

1) Minimisez le nombre de requêtes HTTP que le navigateur doit adresser à votre hôte en concaténant JavaScript et CSS lorsque cela est possible/pratique.

2) Déchargez autant que possible votre image/contenu multimédia sur des CDN tiers, en particulier si vous utilisez un hébergement partagé.

3) Essayez de réduire le nombre de messages que vous affichez sur la page d'accueil afin de réduire le temps de rendu total.

3a) Essayez d’utiliser un thème qui présente quelques articles en vedette en première page et tous les autres articles plus anciens sous forme d’extraits.

7
ZaMoose

La mise en cache du menu WordPress vous donne également une amélioration des performances. Surtout si vous avez beaucoup de pages ou une structure de menu géante, cela devrait être pris en compte.

Faites-le en 2 étapes faciles. Au début, créez une fonction qui obtient ou crée le menu, au lieu d'appeler directement wp_nav_menu.

function get_cached_menu( $menuargs ) {

    if ( !isset( $menuargs['menu'] ) ) {

        $theme_locations = get_nav_menu_locations();
        $nav_menu_selected_id = $theme_locations[$menuargs['theme_location']];
        $termslug = get_term_by( 'id', $nav_menu_selected_id, 'nav_menu' );
        $transient = 'menu_' . $termslug->slug . '_transient';

    } else {

        $transient = 'menu_' . $menuargs['menu'] . '_transient';

    }


    if ( !get_transient( $transient ) ) { // check if the menu is already cached

        $menuargs['echo'] = '0'; // set the output to return
        $this_menu = wp_nav_menu( $menuargs ); // build the menu with the given $menuargs
        echo $this_menu; // output the menu for this run
        set_transient( $transient, $this_menu ); // set the transient, where the build HTML is saved

    } else {

        echo get_transient( $transient ); // just output the cached version

    }

}

Dans votre thème, remplacez le wp_nav_menus par get_cached_menu. Maintenant, chaque fois que le menu est appelé, vous avez une seule requête de base de données à la place de la totalité du menubuilding.

Les menus ne changent pas souvent - mais vous devez également vous accrocher à l'action wp_update_nav_menu pour supprimer les anciens transitoires.

Fais-le comme ça:

add_action('wp_update_nav_menu', 'my_delete_menu_transients');

function my_delete_menu_transients($nav_menu_selected_id) {

    $termslug = get_term_by( 'id', $nav_menu_selected_id, 'nav_menu' );

    $transient = 'menu_' . $termslug->slug . '_transient';

    delete_transient( $transient ); 

}

Le menu sera généré lors du prochain appel de la page et utilisera la version mise en cache jusqu'à ce que quelqu'un mette à nouveau à jour le menu.

Version mise à jour

Merci @helgatheviking pour avoir signalé une erreur entre les slugs et les identifiants. J'ai mis à jour les fonctions pour que cela fonctionne à la fois avec theme_position et menu (pour un appel direct du menu).

Les menus sont toujours enregistrés avec le nom du menu, pas la position dans le thème.

7
fischi

Utilisez une classe de base de données ajustée pour l'optimisation. Nous avons fait de bonnes expériences avec notre propre code pour réduire l'utilisation de la mémoire et la vitesse d'accès à la base de données. En plus de cela, vous pouvez optimiser la structure de la base de données elle-même en apportant de petites modifications qui font également beaucoup.

Une partie du code de classe de la base de données peut être trouvée dans le wordpress trac, il n’a pas été transformé en noyau ( Ticket # 11799 et connexe ).

5
hakre

Pour un site à fort trafic, vous devez ajuster tous les tampons MySQL pour le contenu en place. Quelle que soit la version de WordPress, la configuration de la couche MySQL peut être calculée .

En fait, si vous avez des données InnoDB sans activer innodb_file_per_table, vous devez nettoyer InnoDB en segmentant chaque table dans son propre espace table physique . Il est possible de faire un réglage MySQL décent même si vous avez un matériel limité . Il existe de nombreux scénarios permettant de réaliser de telles optimisations InnoDB .

IMHO, vous ne pouvez pas planifier de bons paramètres pour my.cnf sans connaître la quantité de données à configurer. Vous devez charger périodiquement un jeu de données actuel de la production dans un environnement intermédiaire, effectuer des optimisations et définir les nombres à configurer dans le fichier my.cnf du serveur de production.

4
RolandoMySQLDBA

J'ai récemment parlé de ce sujet à WordCamp Houston . Toutes les recommandations ci-dessus sont excellentes et l'important est de vous assurer que tout le matériel frontal est entièrement optimisé pour que vous puissiez commencer à travailler sur les problèmes de mise en cache et de performances du serveur.

Le rendu progressif rendra vos pages plus rapides car l'utilisateur verra le contenu de la page avant qu'elle ne soit entièrement chargée. Pour ce faire, assurez-vous que tout blocage js est tout en bas de la page et css en haut.

De même, si vous utilisez beaucoup de boutons de médias sociaux, vous pouvez personnaliser les scripts pour les charger dans un iframe une fois la page entièrement chargée. J'ai écrit un tutoriel sur la procédure à suivre avec le bouton TweetMeMe re Tweet (obsolète depuis que Twitter a publié son propre bouton retweet), mais je peux toujours l'appliquer à d'autres boutons de partage.

Pour améliorer les performances du serveur, considérez Nginx comme proxy frontal pour le contenu statique avec Apache, qui gère les charges lourdes PHP et MySQL.

3
Chris_O

vous pouvez activer la compression globale sortie . cela gzip tout sortira automatiquement si le navigateur le supporte. Cela réduit considérablement la taille des fichiers transférés, mais augmente la charge de votre processeur.

3
Scott M.

Étant donné que personne n'en a encore parlé, l'une des étapes les plus importantes pour améliorer les performances du serveur, quelle que soit la configuration de LAMP, consiste à passer au thread de travail Apache et à mod_fcgid.

Cela a libéré 500 Mo de mémoire sur mon serveur privé virtuel.

2
nottinhill

Guide de vérification du ralentissement du plugin

Il existe un plugin extrêmement simple appelé Page Load Time , qui ajoute une minuterie au pied de page. C'est en fait seulement quatre lignes de code:

<?php
function ur_pageload_footer() {
    printf(__('Page in %s seconds', 'pageload'), timer_stop());
}
add_action('wp_footer', 'ur_pageload_footer')

Ensuite:

  1. Créer une feuille de calcul
  2. Listez tous vos plugins actifs et mettez-les dedans
  3. Actualisez la page trois fois en notant le temps de chargement de la page à chaque tour.
  4. Parcourez vos plugins un par un en les désactivant
  5. Répétez l'étape 3
  6. Notez l'ordre dans lequel vous avez désactivé les plugins

Votre feuille de calcul devrait ressembler à quelque chose comme

+-------+-------+-------+-------+--------+
| Run 1 | Run 2 | Run 3 | Order | Plugin |

Donc, si après la désactivation d'un plugin, le temps de réponse de la page augmente de manière significative, vous pouvez voir si vous pouvez éviter ce plugin.

J'ai trouvé deux plugins qui ont provoqué un ralentissement "significatif" mqtranslate et (le plutôt vieux mais bon) Plugin de navigation à plusieurs niveaux .

1
icc97