Optimisation PHP(symfony) sur AWS EFS
Optimisation PHP(symfony) sur AWS EFS

Optimisation PHP(symfony) sur AWS EFS

Checklist d’une plateforme PHP sur EFS.

image
image

Introduction

Nous vivons dans un monde où NFS est toujours présent et même bien actif en réalité. Bien que nous rencontrions de plus en plus de plateformes Cloud Natives, il nous reste à gérer des plateformes, certes dans le Cloud mais, qui proviennent de lift & shift. Sur l’une d’elles j’ai eu à basculer les données Web stockées sur chacune des instances Web (EC2 via EBS) de la plateforme vers un stockage réseau unique passant par le protocole NFS (AWS EFS).

Il est certain que cette bascule n’allait pas améliorer les performances de la plateforme (latence supplémentaire d’accès aux assets PHP). Donc, il a fallu vérifier et optimiser tout ce que l’on pouvait afin de pallier cette latence.

Nous verrons d’une part les optimisations pour PHP Symfony puis d’autre part les optimisations pour AWS EFS.

Optimisations pour PHP

Ici, les optimisations passeront par l’activation et configuration d’OPCache.

Nous avons donc voir ce que cela implique (dans le php.ini).

  • opcache.enable = 1. On active OPCache qui permet de mettre en cache les fichiers PHP compilés ce qui évite d’avoir à les re-compiler (et donc d’accéder aux fichiers sur l’EFS) à chaque requête.
  • opcache.memory_consumption = 256. Ce paramètre permet de définir la quantité de mémoire qui sera allouée à OPCache sur la totalité fournie par la machine. Nous avons été tentés de lui en attribuer davantage mais vous verrez dans les optimisations EFS pourquoi on a décidé de rester à ce niveau.
  • opcache.max_accelerated_files = 30000. On désigne ici le nombre maximum d’objets PHP compilés que l’on peut mettre dans le cache. Valeur bornée entre 200 et 100000 en PHP < 5.5.6, et 1000000 pour les plus récentes. Ici, beaucoup de sites sont présents au sein de cette plateforme et beaucoup de fichiers PHP sont à compiler.
  • opcache.validate_timestamps = 0. Paramètre très intéressant pour une mise en place des fichiers PHP sur EFS. Il permet simplement de dire à OPCache de ne pas aller vérifier la fraîcheur des fichiers PHP sources (donc sur EFS) une fois ceux-ci compilés. Cela convient parfaitement pour les machines de production où les fichiers PHP ne changent que lors d’une nouvelle release. Si un fichier PHP devait tout de même être changé avec une telle configuration, il faudra permettre de réinitialiser l’objet dans le cache OPCache via la fonction opcache_invalidate().

Optimisations pour EFS

AWS EFS est un service de partage de stockage via le réseau qui s’appuie sur NFS. Mais il a quelques petites spécificités que nous allons évoquer ici quand il s’agit de s’en servir comme lieu de stockage de vos fichiers PHP.

  • Nous servons des fichiers destinés à des serveurs Web et donc avons choisi le mode EFS General Purpose Performance comme recommandé par AWS, cependant ceux-ci ont des performances de bande passante relative à l’espace consommé. Comme notre volumétrie EFS n’est pas très élevée, nous avons ajouté une image vide de 250 Go afin d’atteindre les performances qui nous convenaient.
sudo dd if=/dev/urandom of=/path/to/efs/large_file bs=1024k count=256000
  • Cela est d’autant plus utile lors du téléversement d’une nouvelle release via la pipeline (GitLab) vers EFS. On peut aussi régler la bande passante de l’EFS en tant que paramètre en choisissant Provisionned Throughput au lieu de Bursting Throughput mais chaque modification nécessitant 24 h de délai, nous avons opté pour la commande dd. Maintenant, quand la plateforme sera stabilisée et qu’on sera sûr que ce mode nous convient, on analysera les différences de coûts entre notre mode actuel et celui en Provisionned Throughput.
  • Nous avons aussi testé la recommandation d’AWS de paralléliser les accès à EFS afin de mieux répartir les performances en termes de bande passante. Nous avons ainsi basculé nos instances de type t3a.medium vers 2 fois plus de t3a.small. Heureusement, l’application est davantage gourmande en CPU qu’en RAM. Cela n’a pas impacté la vitesse de rendu de l’application. Aussi, nous avons constaté un léger gain (bien que minime) sur ce point qui suit la charge et le scaling.

Mot de la fin

Nous avons vu les optimisations que nous avons mises en place lors de notre intervention mais il reste cependant d’autres pistes d’optimisations sur cette plateforme :

  • Le preload OPCache qui nécessite une version plus à jour de PHP. Cela permet de précharger des classes PHP lors du démarrage et de rendre l’application plus rapide pour les premiers clients.
  • Procéder à des bascules de release par simple changement de liens symbolique. Cela nécessite par contre de configurer realpath_cache_size ainsi que realpath_cache_ttl pour permettre à l’application d’accéder aux nouvelles versions des fichiers PHP (en complément d’un clear OPCache bien synchronisé) et de revoir le mécanisme de déploiement continu.

En résumé, on aimerait peut-être croire que le NFS est mort et qu’il faudrait l’enterrer mais la réalité est bien autre. AWS EFS nous a rendu service :

  • Gain sur le renew (lors d’une nouvelle release) et le scaling des instances EC2 réduite à un point de montage en lieu et place d’opérations multiples de build et de cache de l’application sur chaque instance.
  • Bien que cela ajoute une ligne dans le billing, le montant est négligeable sur cette plateforme (-$90/mois). Montant en partie couvert par la réduction de la taille des EBS des instances EC2 en place et qui pourraient apparaître lors de scaling.

Merci pour votre lecture. Si cet article vous a plu, merci de le partager sur vos réseaux 😉

Philippe Vidal - Oct 12, 2020

image