How to Restart PHP-FPM: Every Method Explained for Linux Administrators
PHP-FPM (PHP FastCGI Process Manager) is a high-performance process manager that handles PHP execution as a separate service, decoupled from the web server. Restarting PHP-FPM applies configuration changes from `php.ini` or `php-fpm.conf`, reclaims leaked memory in long-running worker pools, and recovers from unresponsive child processes — all without touching Nginx, Apache, or any other component of your stack.
This guide covers every practical restart method available on modern and legacy Linux distributions, including signal-based control, multi-version environments, and graceful reload strategies for zero-downtime production deployments.
Why You Need to Restart PHP-FPM
Understanding the exact trigger for a restart prevents unnecessary downtime and helps you choose the least disruptive method:
- Configuration changes: Modifications to `php.ini`, `php-fpm.conf`, or any pool configuration file under `/etc/php/<version>/fpm/pool.d/` require a restart or reload to take effect. PHP-FPM reads these files only at startup or on a `USR2` signal.
- Memory reclamation: PHP-FPM worker processes accumulate memory over time, particularly on high-traffic servers running memory-intensive applications. A controlled restart recycles workers and resets their memory footprint.
- Unresponsive workers: If child processes enter a zombie state or stop accepting connections, a restart clears the process table and spawns a fresh pool.
- Log rotation: After `logrotate` renames or compresses the active log file, PHP-FPM still holds a file descriptor to the old inode. A reload forces it to open the new file descriptor, ensuring log continuity.
- OPcache invalidation: When deploying new application code, restarting PHP-FPM flushes the OPcache entirely, guaranteeing workers execute the updated bytecode rather than stale cached versions.
- Extension or module changes: Adding or removing PHP extensions in `php.ini` requires a full restart — a reload alone is insufficient because the extension list is evaluated at process initialization.
Prerequisites
Before executing any restart command, confirm the following:
- You have `root` access or `sudo` privileges on the server.
- You know the exact PHP-FPM service name on your system (it varies by distribution and installed version).
- You have identified the PID file path if you plan to use signal-based control (typically `/run/php/php<version>-fpm.pid` on Debian/Ubuntu or `/run/php-fpm/php-fpm.pid` on RHEL/CentOS).
To discover the active PHP-FPM service name:
“`bash
systemctl list-units –type=service | grep fpm
“`
To locate the PID file path:
“`bash
grep -i pid /etc/php/*/fpm/php-fpm.conf
“`
Method 1: Restart PHP-FPM with systemctl (Recommended)
`systemctl` is the authoritative service manager on all systemd-based distributions, including Ubuntu 16.04+, Debian 8+, CentOS 7+, AlmaLinux, Rocky Linux, and Fedora. It is the correct tool for the vast majority of production servers.
Standard Restart
“`bash
sudo systemctl restart php8.2-fpm
“`
Replace `php8.2-fpm` with the version installed on your system (e.g., `php7.4-fpm`, `php8.1-fpm`, `php-fpm`). On RHEL-based systems, the service is typically named `php-fpm` without a version prefix.
Reload Without Full Restart
A reload sends a `USR2` signal internally, instructing the master process to re-read its configuration and gracefully replace worker processes. Existing in-flight requests are completed before workers are recycled:
“`bash
sudo systemctl reload php8.2-fpm
“`
Critical distinction: `reload` is non-disruptive and preferred for configuration changes in production. `restart` terminates all workers immediately, which can drop active connections under high concurrency.
Stop and Start Separately
“`bash
sudo systemctl stop php8.2-fpm
sudo systemctl start php8.2-fpm
“`
Use this two-step approach when you need to confirm the service is fully stopped before bringing it back — for example, after changing the `listen` socket path or modifying `pm.max_children` significantly.
Verify the Service State
“`bash
sudo systemctl status php8.2-fpm
“`
A healthy output shows `Active: active (running)` and lists the master PID. If the service failed to start, `systemctl status` displays the last journal entries, which is faster than hunting through log files manually.
To stream live logs during a restart:
“`bash
sudo journalctl -u php8.2-fpm -f
“`
Method 2: Restart PHP-FPM with the Legacy service Command
The `service` command is a compatibility wrapper around `systemctl` on modern systems and directly invokes SysVinit scripts on older distributions (Ubuntu 14.04, CentOS 6, Debian 7). It remains relevant when managing servers that have not been migrated to systemd.
“`bash
sudo service php-fpm restart
“`
To stop and start independently:
“`bash
sudo service php-fpm stop
sudo service php-fpm start
“`
On distributions that still use SysVinit, the underlying script is located at `/etc/init.d/php-fpm`. You can invoke it directly if the `service` wrapper is unavailable:
“`bash
sudo /etc/init.d/php-fpm restart
“`
Method 3: Managing Multiple PHP Versions Simultaneously
Servers running control panels such as cPanel, Plesk, or custom multi-tenant setups frequently have several PHP versions installed in parallel. Each version runs as an independent PHP-FPM service with its own configuration tree, socket, and PID file.
Restarting a Specific Version
“`bash
Debian/Ubuntu (packages from ondrej/php PPA or distribution repos)
sudo systemctl restart php7.4-fpm
sudo systemctl restart php8.1-fpm
sudo systemctl restart php8.2-fpm
RHEL/CentOS with Remi repository
sudo systemctl restart php74-php-fpm
sudo systemctl restart php81-php-fpm
“`
Restarting All PHP-FPM Versions at Once
When a system-wide change affects all versions (such as a shared library update), restart all instances with a single loop:
“`bash
for ver in 7.4 8.1 8.2; do
sudo systemctl restart php${ver}-fpm && echo "php${ver}-fpm restarted"
done
“`
Identifying Which Version Serves a Specific Site
Each Nginx virtual host or Apache VirtualHost maps to a specific PHP-FPM socket. Check the site configuration to determine which version is active before restarting:
“`bash
Nginx
grep fastcgi_pass /etc/nginx/sites-enabled/yourdomain.conf
Apache with mod_proxy_fcgi
grep SetHandler /etc/apache2/sites-enabled/yourdomain.conf
“`
If you manage your server through a control panel, VPS with cPanel provides a graphical interface for switching PHP versions per domain without manual service restarts.
Method 4: Sending POSIX Signals Directly to the Master Process
PHP-FPM's master process responds to a defined set of POSIX signals. This method bypasses the init system entirely and gives you precise, low-level control — essential in containerized environments, custom init systems, or when `systemctl` is unavailable.
Signal Reference Table
| Signal | Effect | Use Case |
|---|---|---|
| — | — | — |
| `SIGTERM` (15) | Graceful shutdown | Orderly stop, waits for workers to finish |
| `SIGINT` (2) | Immediate shutdown | Force stop when graceful shutdown hangs |
| `SIGQUIT` (3) | Graceful stop | Equivalent to SIGTERM for PHP-FPM |
| `SIGUSR1` (10) | Reopen log files | Post-logrotate log file descriptor refresh |
| `SIGUSR2` (12) | Graceful reload | Reload config, recycle workers without dropping connections |
| `SIGKILL` (9) | Force kill | Last resort — no cleanup, no graceful handling |
Reload Configuration (Zero Downtime)
“`bash
sudo kill -USR2 $(cat /run/php/php8.2-fpm.pid)
“`
This is functionally equivalent to `systemctl reload` and is the safest way to apply `php-fpm.conf` or pool configuration changes on a live server.
Reopen Log Files After Rotation
“`bash
sudo kill -USR1 $(cat /run/php/php8.2-fpm.pid)
“`
Run this immediately after `logrotate` executes to prevent PHP-FPM from continuing to write to the renamed log file.
Graceful Shutdown
“`bash
sudo kill -QUIT $(cat /run/php/php8.2-fpm.pid)
“`
The master process stops accepting new connections and waits for all active workers to complete their current requests before exiting. Follow this with `sudo systemctl start php8.2-fpm` to bring the service back up.
Important: Always verify the PID file path before using these commands. An incorrect path results in sending a signal to an unrelated process. Confirm with:
“`bash
cat /run/php/php8.2-fpm.pid
ps aux | grep php-fpm
“`
Method 5: Force-Killing PHP-FPM Processes with pkill or killall
This is a last-resort method for situations where PHP-FPM has become completely unresponsive and neither `systemctl` nor signal-based control produces results. It terminates all PHP-FPM processes unconditionally, which will interrupt any in-flight requests.
“`bash
sudo pkill -9 php-fpm
“`
Or using `killall`:
“`bash
sudo killall -9 php-fpm
“`
After force-killing, the service will not restart automatically unless it is managed by a process supervisor. Start it explicitly:
“`bash
sudo systemctl start php8.2-fpm
“`
When to use this: Zombie process accumulation, runaway child processes consuming 100% CPU, or situations where the master process is alive but no longer managing its pool. Before reaching for `pkill -9`, attempt `kill -QUIT` on the master PID first — it is far less disruptive.
Method 6: Restarting the Web Server to Indirectly Affect PHP-FPM
Restarting Nginx or Apache does not restart PHP-FPM. Because PHP-FPM runs as a completely independent service communicating over a Unix socket or TCP port, the web server restart only affects the HTTP layer. This is a common misconception.
“`bash
Nginx
sudo systemctl restart nginx
Apache
sudo systemctl restart apache2
“`
The only scenario where a web server restart is relevant to PHP-FPM is when you have modified the `fastcgi_pass` directive in Nginx or the `ProxyPassMatch` rule in Apache to point to a different PHP-FPM socket. In that case, Nginx must reload its configuration to connect to the new socket path — but PHP-FPM itself still needs its own separate restart.
For full-stack maintenance, restart both services in the correct order: PHP-FPM first, then the web server.
Comparison: PHP-FPM Restart Methods at a Glance
| Method | Command Example | Disruption Level | Use Case |
|---|---|---|---|
| — | — | — | — |
| `systemctl restart` | `systemctl restart php8.2-fpm` | Medium — drops active connections | Standard config changes, dev/staging |
| `systemctl reload` | `systemctl reload php8.2-fpm` | None — graceful worker recycle | Production config changes |
| `kill -USR2` | `kill -USR2 $(cat /run/php/php-fpm.pid)` | None — graceful reload | Production, containerized environments |
| `kill -QUIT` | `kill -QUIT $(cat /run/php/php-fpm.pid)` | Low — waits for requests to finish | Controlled shutdown before maintenance |
| `kill -USR1` | `kill -USR1 $(cat /run/php/php-fpm.pid)` | None — log FD refresh only | Post-logrotate |
| `service restart` | `service php-fpm restart` | Medium | Legacy SysVinit systems |
| `pkill -9` | `pkill -9 php-fpm` | High — immediate termination | Unresponsive processes, last resort |
| Web server restart | `systemctl restart nginx` | Web layer only | Updating fastcgi socket path in web server config |
PHP-FPM Pool Configuration: What Requires a Restart vs. a Reload
Not all configuration changes carry the same weight. Knowing which changes require a full restart versus a simple reload reduces unnecessary downtime:
Reload (`USR2` / `systemctl reload`) is sufficient for:
- `pm.max_children`, `pm.start_servers`, `pm.min_spare_servers`, `pm.max_spare_servers`
- `request_terminate_timeout`, `request_slowlog_timeout`
- `slowlog` path changes
- `php_admin_value` and `php_flag` directives within pool files
- `access.log` path changes
Full restart required for:
- Changes to the `listen` directive (socket path or TCP port)
- Adding or removing PHP extensions in `php.ini`
- Changing `user` or `group` directives in the pool
- Modifying `include` paths in `php-fpm.conf`
- Updating the PHP binary itself (version upgrades)
Best Practices for Production PHP-FPM Restarts
- Always prefer `reload` over `restart` on live servers. A reload recycles workers gracefully, completing in-flight requests before spawning replacements. A hard restart drops all active connections immediately.
- Validate configuration before reloading. PHP-FPM provides a built-in syntax check that prevents loading a broken configuration:
“`bash
sudo php-fpm8.2 -t
Expected output: NOTICE: configuration file … test is successful
“`
- Check logs before and after. Review `/var/log/php8.2-fpm.log` (or the path defined in your `php-fpm.conf`) for `WARNING` or `ERROR` entries that indicate pool startup failures.
- Monitor worker pool metrics post-restart. Use the PHP-FPM status page (enabled via `pm.status_path` in your pool config) to verify that the expected number of workers are active and idle after the restart.
- Automate with deployment pipelines. In CI/CD workflows, trigger `systemctl reload php-fpm` as a post-deploy hook rather than a full restart. This ensures zero-downtime deployments on every code push.
- Set `pm.max_requests` to auto-recycle workers. Rather than scheduling periodic restarts to combat memory leaks, configure `pm.max_requests = 500` (or an appropriate value) to automatically restart each worker after serving a fixed number of requests.
PHP-FPM on VPS and Dedicated Server Environments
The restart method you use is also influenced by your hosting environment. On a VPS Hosting plan with full root access, all methods described in this guide are available without restriction. You have direct access to `systemctl`, the PID file, and the process table.
On Dedicated Servers, where you control the entire hardware stack, you can additionally configure PHP-FPM with `pm = ondemand` or `pm = dynamic` to tune worker spawning behavior precisely, and use `systemd` drop-in files to customize restart policies (e.g., `Restart=on-failure`, `RestartSec=5s`).
If you manage multiple client sites through a VPS Control Panels solution, PHP-FPM restart operations are often abstracted into the panel's UI, but understanding the underlying commands remains essential for troubleshooting scenarios where the panel itself is unresponsive.
For applications requiring high PHP concurrency — such as Laravel, WordPress multisite, or WooCommerce stores — pairing PHP-FPM with a properly tuned pool configuration on a Dedicated Server eliminates the resource contention that shared environments introduce.
Technical Decision Matrix: Choosing the Right Restart Method
Use this matrix to select the correct approach based on your specific situation:
| Situation | Recommended Method |
|---|---|
| — | — |
| Applied changes to `php.ini` or pool `.conf` files | `systemctl reload php<ver>-fpm` |
| Added a new PHP extension | `systemctl restart php<ver>-fpm` |
| PHP-FPM is unresponsive, master process alive | `kill -QUIT <master_pid>`, then `systemctl start` |
| PHP-FPM is completely frozen, no signal response | `pkill -9 php-fpm`, then `systemctl start` |
| Post-logrotate log file refresh | `kill -USR1 <master_pid>` |
| Deploying new application code (OPcache flush) | `systemctl reload php<ver>-fpm` or `kill -USR2` |
| Changed `listen` socket path | `systemctl restart php<ver>-fpm` |
| Multiple PHP versions, one needs updating | `systemctl restart php<specific-ver>-fpm` only |
| Containerized environment without systemd | `kill -USR2 <master_pid>` via entrypoint script |
| Syntax-checking config before applying | `php-fpm<ver> -t` first, then reload/restart |
FAQ
What is the difference between `systemctl restart` and `systemctl reload` for PHP-FPM?
`restart` immediately terminates all master and worker processes and starts fresh, dropping any in-flight requests. `reload` sends a `USR2` signal to the master process, which spawns new workers with the updated configuration while existing workers finish their current requests before exiting. Always use `reload` in production.
How do I find the correct PHP-FPM service name on my server?
Run `systemctl list-units –type=service | grep fpm`. On Debian/Ubuntu systems with multiple versions from the `ondrej/php` PPA, you will see entries like `php7.4-fpm.service` and `php8.2-fpm.service`. On RHEL/CentOS with the Remi repository, the naming convention is `php74-php-fpm.service`.
Does restarting PHP-FPM affect active database connections or user sessions?
A hard restart (`systemctl restart`) terminates all worker processes immediately, which closes any persistent database connections held by those workers. User sessions stored in files or a database are unaffected because they persist independently of PHP-FPM workers. A graceful reload (`systemctl reload`) allows workers to complete their current requests, so persistent connections are closed cleanly.
Why does PHP-FPM fail to start after a restart?
The most common causes are a syntax error in `php.ini` or a pool configuration file, a port or socket path conflict (another process already listening on the configured `listen` address), or insufficient permissions on the socket directory. Run `php-fpm<ver> -t` to validate configuration syntax, and check `journalctl -u php<ver>-fpm` for the exact error message.
Can I restart PHP-FPM without root or sudo privileges?
Not on a standard Linux installation. PHP-FPM's master process runs as root (it drops privileges to the configured `user`/`group` for worker processes), and managing system services requires elevated privileges. On shared hosting environments, the hosting provider handles PHP-FPM restarts through their control panel. For full control over PHP-FPM, a VPS Hosting plan with root access is the appropriate solution.
