How to Configure PHP-FPM on Ubuntu 22.04 | 20.04

Configuring PHP-FPM on Ubuntu 22.04 or 20.04 is essential for optimal performance and security when using Nginx as a web server. This guide provides detailed instructions on installing, configuring, and optimizing PHP-FPM, along with some common examples and troubleshooting tips.

Basic Configuration

First, let’s go through installing PHP-FPM and configuring the settings.

Installing PHP-FPM

To install PHP-FPM on Ubuntu 22.04 or 20.04, open the terminal and run the following commands:

sudo apt install php-fpm

Configuring PHP-FPM

Once PHP-FPM is installed, it’s time to configure the settings. Open the main configuration file, typically located at /etc/php/7.4/fpm/php-fpm.conf (replace 7.4 with the installed PHP version).

Adjust the following settings according to the needs:

  • listen: Set the address and port for PHP-FPM to listen to.
  • pm: Configure the process manager mode (static, dynamic, or ondemand).
  • pm.max_children: Set the maximum number of child processes.
  • pm.start_servers: Specify the number of child processes to start.
sudo systemctl restart php7.4-fpm

Configuring Nginx

Now it’s time to configure Nginx to work with PHP-FPM. Open the Nginx server block configuration file (usually located at /etc/nginx/sites-available/default). Add the following lines inside the location ~ \.php$ block:

fastcgi_pass unix:/run/php/php7.4-fpm.sock;
fastcgi_index index.php;
fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
include fastcgi_params;

Replace 7.4 with the installed PHP version. Save the file and restart Nginx:

sudo systemctl restart nginx

Advanced Configuration

With the basic configuration covered, let’s explore more advanced configuration options for PHP-FPM, focusing on customizing PHP-FPM pools and fine-tuning settings.

Customizing PHP-FPM Pools

Creating separate pools for different websites or applications can optimize resource usage. PHP-FPM supports three process manager (pm) modes: static, dynamic, and ondemand. Here’s a breakdown of each mode and examples of their use:

Static Mode

In static mode, the number of child processes remains constant. This mode is suitable for consistent loads. To configure a static pool, adjust the following settings in a new pool configuration file:

[example_static]
user = example_user
group = example_group
listen = /run/php/php7.4-fpm-example-static.sock
listen.owner = www-data
listen.group = www-data
pm = static
pm.max_children = 10

Dynamic Mode

In dynamic mode, the number of child processes adapts to the server load. This mode is suitable for variable loads. To configure a dynamic pool, adjust the following settings in a new pool configuration file:

[example_dynamic]
user = example_user
group = example_group
listen = /run/php/php7.4-fpm-example-dynamic.sock
listen.owner = www-data
listen.group = www-data
pm = dynamic
pm.max_children = 10
pm.start_servers = 2
pm.min_spare_servers = 1
pm.max_spare_servers = 3

Ondemand Mode

In ondemand mode, child processes are created only when needed. This mode is suitable for sporadic loads. To configure an ondemand pool, adjust the following settings in a new pool configuration file:

[example_ondemand]
user = example_user
group = example_group
listen = /run/php/php7.4-fpm-example-ondemand.sock
listen.owner = www-data
listen.group = www-data
pm = ondemand
pm.max_children = 10
pm.process_idle_timeout = 10s;

After creating a new pool configuration file, save it and restart PHP-FPM:

sudo systemctl restart php7.4-fpm

Update your Nginx server block configuration to use the new pool by changing the fastcgi_pass line:

fastcgi_pass unix:/run/php/php7.4-fpm-example.sock;

Restart Nginx to apply the changes:

sudo systemctl restart nginx

Fine-tuning PHP-FPM Settings

In addition to customizing pools, further optimization of PHP-FPM performance is possible by adjusting settings such as timeouts and log files. Here are some settings to consider:

  • request_terminate_timeout: Set a timeout for each request to prevent long-running scripts. Example: request_terminate_timeout = 30s
  • request_slowlog_timeout: Log requests that exceed a specified time limit. Example: request_slowlog_timeout = 5s
  • slowlog: Define the path to the slow log file. Example: slowlog = /var/log/php-fpm/example-slow.log
  • catch_workers_output: Enable capturing output from workers for debugging purposes. Example: catch_workers_output = yes

Adjust these settings in the pool configuration file, save the changes, and restart PHP-FPM to apply them.

Monitoring PHP-FPM Performance

Monitoring PHP-FPM performance helps identify bottlenecks and areas for improvement. There are several monitoring tools and techniques available, such as:

PHP-FPM Status Page

Enable the PHP-FPM status page in the pool configuration file by adding the following line:

pm.status_path = /status

Then, configure Nginx to display the status page by adding a new location block to the server block configuration:

location = /status {
    allow 127.0.0.1;
    deny all;
    include fastcgi_params;
    fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
    fastcgi_pass unix:/run/php/php7.4-fpm-example.sock;
}

After applying these changes and restarting both PHP-FPM and Nginx, the status page can be accessed at http://example.com/status.

Log Analyzers

Log analyzers like GoAccess and AWStats can parse PHP-FPM log files to provide insights into performance and resource usage.

Third-Party Monitoring Tools

Third-party monitoring tools like New Relic and Datadog offer comprehensive monitoring and alerting capabilities for PHP-FPM.

Securing PHP-FPM and Nginx

To enhance the security of your PHP-FPM and Nginx setup, consider implementing these measures:

Restricting File Access

Prevent unauthorized access to sensitive files by adding the following lines to your Nginx server block configuration:

location ~ /\. {
    deny all;
}

This snippet blocks access to hidden files (those starting with a dot).

Using HTTPS

Enable HTTPS by obtaining an SSL certificate from a trusted provider like Let’s Encrypt and updating your Nginx server block configuration:

listen 443 ssl;
ssl_certificate /path/to/fullchain.pem;
ssl_certificate_key /path/to/privkey.pem;

Troubleshooting Common Issues

Here are some common issues that might be encountered while configuring PHP-FPM on Ubuntu 22.04 or 20.04, along with example fixes:

Incorrect File Permissions

Ensure that file permissions are set correctly for web files and directories. Nginx and PHP-FPM should have the necessary read and write permissions. To check the current permissions of a file or directory, use the ls -l command:

ls -l /path/to/directory

If the permissions are incorrect, use the chmod command to set the appropriate permissions. For example, to grant read and write permissions to the owner and read permissions to the group and others for a file, use:

chmod 644 /path/to/file

For a directory use:

chmod 755 /path/to/directory

Additionally, ensure that the correct user and group own the files and directories using the chown command:

sudo chown www-data:www-data /path/to/file_or_directory

Incompatible PHP-FPM and Nginx Configurations

Double-check PHP-FPM and Nginx configurations to ensure they’re compatible. For example, if the PHP-FPM pool is configured to listen on a Unix socket, the fastcgi_pass directive in Nginx should point to the correct socket:

fastcgi_pass unix:/run/php/php7.4-fpm-example.sock;

If PHP-FPM is listening on a TCP socket, the fastcgi_pass directive should use the corresponding IP address and port:

fastcgi_pass 127.0.0.1:9000;

To verify the PHP-FPM pool configuration, check the listen directive in the pool configuration file:

listen = /run/php/php7.4-fpm-example.sock

or

listen = 127.0.0.1:9000

After making any necessary changes, restart both PHP-FPM and Nginx to apply them:

sudo systemctl restart php7.4-fpm
sudo systemctl restart nginx

PHP Scripts Not Executed

If PHP scripts are not being executed and the browser displays the PHP code instead, ensure that the Nginx server block configuration includes the appropriate location block for PHP files:

location ~ \.php$ {
    fastcgi_pass unix:/run/php/php7.4-fpm.sock;
    fastcgi_index index.php;
    fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
    include fastcgi_params;
}

Make sure to replace 7.4 with the installed PHP version. Save the changes and restart Nginx:

sudo systemctl restart nginx

Overcommitment of Resources with PHP-FPM Static Mode

Static mode in PHP-FPM can lead to overcommitment of resources if not configured correctly, especially on shared hosting environments or dedicated high-performance VPS. In these cases, static mode might not be ideal, as it requires a consistent allocation of system resources.

Risks of Overcommitment

Overcommitment can cause system performance degradation, leading to slow page loads, unresponsive applications, or even server crashes. When using static mode, it’s crucial to align the configuration with the available system resources to prevent these issues.

Inappropriate Static Mode Configuration Example

Suppose the system has 4 GB of RAM, and each PHP-FPM process consumes around 50 MB of memory. If pm.max_children is set too high, it can lead to overcommitment:

[example_static]
user = example_user
group = example_group
listen = /run/php/php7.4-fpm-example-static.sock
listen.owner = www-data
listen.group = www-data
pm = static
pm.max_children = 100

In this example, PHP-FPM processes would consume 100 (max_children) * 50 MB = 5,000 MB of memory, exceeding the available 4 GB of RAM.

Appropriate Static Mode Configuration Example

To prevent overcommitment, ensure that pm.max_children is set within the limits of the available system resources. In the same 4 GB RAM scenario, a more suitable configuration would be:

[example_static]
user = example_user
group = example_group
listen = /run/php/php7.4-fpm-example-static.sock
listen.owner = www-data
listen.group = www-data
pm = static
pm.max_children = 60

In this configuration, PHP-FPM processes would consume 60 (max_children) * 50 MB = 3,000 MB of memory, well within the available 4 GB of RAM.

Conclusion

Configuring PHP-FPM on Ubuntu 22.04 or 20.04 can lead to better performance and security for web applications. An optimized setup can be achieved by following the basic and advanced examples provided in this guide. It is essential to continuously monitor and fine-tune PHP-FPM settings to ensure the best possible performance and resource usage for specific use cases.

Additional Resources and Relevant Links

To further expand your knowledge and understanding of PHP-FPM and Nginx, here are some valuable resources and links:

  • PHP-FPM Official Documentation: A comprehensive guide on PHP-FPM installation, configuration, and optimization.
  • Nginx Official Documentation: An extensive resource covering Nginx setup, configuration, and advanced features.
  • Nginx Beginner’s Guide: A beginner-friendly introduction to Nginx, covering the basics of configuration, directory structure, and more.
  • Ubuntu Official Documentation: Official Ubuntu documentation, including guides on server administration, package management, and system maintenance.
  • Let’s Encrypt: A free, automated, and open certificate authority that provides SSL certificates for securing websites with HTTPS.

Your Mastodon Instance
Share to...