Optimizing PHP-FPM: A Step-by-Step Guide

7 min read

PHP-FPM is a FastCGI process manager that is used to handle high traffic on web servers. However, sometimes this service can cause high load on servers itself. In this article, we will discuss the best practices for tuning PHP-FPM to handle high traffic.

What is PHP-FPM and Why Does it Cause High Load?

PHP-FPM is a FastCGI daemon that allows a website to handle high load, but sometimes this service itself causes high load. The first step in debugging this issue is to examine the PHP-FPM error logs. In this case, the error logs revealed that the PHP-FPM pool was too busy to handle the high traffic with the existing configuration parameters.

How to Perform PHP-FPM Tuning for High Load

The first thing server owners tend to do for an immediate fix, is to restart the PHP-FPM service. But simply restarting the service is only a band-aid solution, and you will soon see the load spiking.

When we debug such load issues, we analyse the logs and server performance over a period of time. This helps us to pinpoint the culprit and take prompt actions to fix it.

Step 1: Switch Process Manager

Process manager is mainly of 3 types – dynamic, ondemand and static. The performance of the service drastically varies based on this type.

  • In dynamic type, the number of child processes is set dynamically based on the PHP-FPM parameters in conf file. But it is a bit memory-intensive type.
  • In static type, the number of child processes is fixed by pm.max_children parameter, but this type is not flexible for a server with changing web traffic. It also consumes too much memory.
  • In ondemand type, the PHP-FPM processes are spawned only on demand, based on the traffic. This type helps to manage varying traffic in memory restrained servers. But the overhead increases when there is so much traffic fluctuation.

The PHP-FPM process manager is determined after assessing the available server memory, traffic spikes, website pages, CPU usage, etc.

Step 2: Tweak PHP-FPM parameters

PHP-FPM has a lot of configuration parameters which determine the way it performs. These parameters have to be determined based on available server resources such as RAM and CPU.

For instance, the total processes that run in a server would be approximately = (Total RAM / Memory per process) . In a server with multiple services, all of them are taken into account for the tuning process.

The PHP-FPM configuration file will be available at /etc/php-fpm.conf or some other location based on the service path. The contents of the file would look like:

listen.allowed_clients = 127.0.0.1
pm = dynamic
pm.max_children = 5
pm.start_servers = 2
pm.min_spare_servers = 2
pm.max_spare_servers = 5
pm.max_requests = 150
It is important to note that the above settings should be adjusted based on the server's resources and traffic patterns.

Configuration explanation

  • listen.allowed_clients: This setting defines the IP address(es) that are allowed to connect to the PHP-FPM service. The default value is '127.0.0.1' which means only connections from the local host are allowed.
  • pm: This setting determines the type of process manager that PHP-FPM uses. The available options are 'dynamic', 'ondemand', and 'static'.
    • dynamic: The number of child processes is set dynamically based on the PHP-FPM parameters in conf file. This type can be memory-intensive.
    • ondemand: The PHP-FPM processes are spawned only on demand, based on the traffic. This type helps to manage varying traffic in memory-restrained servers. The overhead increases when there is so much traffic fluctuation.
    • static: The number of child processes is fixed by pm.max_children parameter. This type is not flexible for a server with changing web traffic and also consumes too much memory.
  • pm.max_children: This setting defines the maximum number of child processes that can be spawned by PHP-FPM. It is dependent on the server's resources and traffic.
  • pm.start_servers: This setting defines the number of child processes that are spawned when PHP-FPM starts.
  • pm.min_spare_servers: This setting defines the minimum number of idle child processes that should be available at any time.
  • pm.max_spare_servers: This setting defines the maximum number of idle child processes that should be available at any time.
  • pm.max_requests: This setting defines the number of requests that a child process should handle before it is terminated and replaced by a new child process.
  • other parameters: There are other parameters that are specific to your PHP-FPM installation and server resources. Some examples include listen.backlog, listen.mode, pm.status_path, etc.

Further tips to Ensure better performance of PHP-FPM

Here are some of the top tweaks that can be used to enhance the performance of PHP-FPM:

  • Switch to the 'ondemand' process manager: This process manager type can help manage varying traffic in memory-restrained servers.
  • Tune the pm.max_children parameter: This parameter defines the maximum number of child processes that can be spawned by PHP-FPM. It is essential to set this value to an appropriate level for your server's resources and traffic.
  • Increase pm.start_servers and pm.min_spare_servers: These settings define the number of child processes that are spawned when PHP-FPM starts and the minimum number of idle child processes that should be available at any time. Increasing these values can help PHP-FPM to handle sudden traffic spikes.
  • Decrease pm.max_requests: This setting defines the number of requests that a child process should handle before it is terminated and replaced by a new child process. Decreasing this value can help to reduce the overhead of constantly spawning new child processes.
  • Increase php-fpm's timeout settings: This can be done by increasing the following parameters: request_terminate_timeout, request_slowlog_timeout, slowlog_timeout
  • Monitor the PHP-FPM status: It is important to monitor the PHP-FPM status to detect any issues or problems. This can be done by enabling the pm.status_path setting in the PHP-FPM configuration file.
  • Optimize your PHP code: Optimizing your PHP code can help to reduce the load on the PHP-FPM service and improve performance. This can be done by identifying and fixing slow or inefficient code and by using caching where appropriate.
  • Assess the server resources: Assessing the server resources such as CPU, memory, I/O, etc., is important to make sure that the PHP-FPM settings are properly configured for the server's capabilities. This includes setting the PHP-FPM settings based on the server's available memory and CPU resources and monitoring the server's performance to ensure that the PHP-FPM settings are still optimal as the traffic and usage of the server changes over time.
  • Optimize your web server configuration: Optimizing your web server configuration can also help to reduce the load on the PHP-FPM service. This can include configuring the web server to handle a high number of connections, adjusting the number of worker processes, and enabling caching.
  • Use a PHP opcode cache: A PHP opcode cache can help to speed up the execution of PHP scripts by caching the compiled version of the script in memory. This can significantly improve the performance of PHP-FPM, especially under high traffic conditions.
  • Monitor and Analyze the logs: Regularly monitoring and analyzing the PHP-FPM logs can help to detect any issues or problems with the service. This can include identifying slow-performing scripts, detecting errors or warnings, and monitoring the number of child processes being spawned.
  • Monitor resource usage: Keep an eye on the resource usage of the server, such as CPU, memory, I/O, etc. Make sure that the PHP-FPM settings are not over-allocating resources, which could cause the server to crash or become unresponsive.

By implementing these tweaks and monitoring the performance of PHP-FPM, you can significantly improve the performance of your PHP-based web application and reduce the likelihood of high server load caused by PHP-FPM.

Conclusion

In this article, we discussed how to optimize PHP-FPM for high traffic by switching the process manager and tweaking PHP-FPM parameters.