Free tools Windows power users keep installed
One-click scans. No signup required.
The safest way to optimize Nginx and PHP-FPM on an Ubuntu VPS is to measure your workload, send each PHP site to the correct FPM pool, size pm.max_children from observed worker memory, and then tune process mode, listener security, buffering, and caching one change at a time. There is no reliable universal worker count: the right value depends on available RAM after Ubuntu, Nginx, databases, and monitoring are accounted for.
Antihost offers Linux VPS plans with full root access, unlimited traffic on a 1 Gbps port and a 14-day free trial.
What Nginx and PHP-FPM are doing together
Nginx serves static files and accepts HTTP connections. When a request needs PHP, its FastCGI module forwards the request to PHP-FPM. PHP-FPM keeps a managed group of PHP worker processes, called a pool, and returns the generated response to Nginx.
As an Amazon Associate I earn from qualifying purchases.
PC Slower Than It Used to Be?
A free scan shows the junk files, broken settings and background clutter dragging Windows down - then fixes them in one click.Free scan · Windows 10 & 11Outdated Drivers Are Slowing You Down
One free scan finds every outdated or missing driver and matches the right update for your exact hardware.Free scan · exact hardware matchThe hand-off has three details that must be correct:
- Listener: Nginx must connect to the Unix socket or TCP address on which the intended pool is listening.
- Script path: The FastCGI parameter
SCRIPT_FILENAMEmust resolve to the real PHP file. A wrong path commonly produces “Primary script unknown” or a 404. - Service state: The PHP-FPM service and the selected pool must be running after configuration changes.
Nginx’s ngx_http_fastcgi_module also controls request parameters, response buffering, and FastCGI caching. Buffering and caching are different: buffering changes how Nginx receives and stores an upstream response, while caching can avoid running PHP at all for a cache hit.
#1 Best Overall
- Read Before You Buy — No Video Output: These adapters support charging and USB 2.0 data transfer, but cannot transmit video signals. Except for standard USB webcams (which use USB data only), they are not compatible with HDMI/DisplayPort cables, video-capable USB-C hubs, or docking stations with video output.
- Convert USB-A Ports to USB-C: Designed to connect USB-C earphones, cables, flash drives, card readers, and other USB-C accessories to standard USB-A ports. Plug-and-play with no drivers or software required.
- Aluminum Alloy Housing: Built with a sturdy aluminum alloy shell that aids in heat dissipation and protects against daily wear and scratches. Designed to maintain a stable and secure connection.
- Compact & Travel-Friendly: The ultra-compact design allows the adapter to stay plugged into your device without blocking adjacent ports or adding bulk, reducing wear and tear on your original USB ports.
- 12-Month Warranty: Backed by a 12-month manufacturer warranty for peace of mind. Designed to meet strict quality control standards for reliable everyday performance.
Inventory the VPS before changing a pool
Optimization starts with a baseline. Record the installed PHP-FPM version, physical memory, CPU count, database footprint, number of sites, and current pool files. On Ubuntu, common pool definitions are under /etc/php/<version>/fpm/pool.d/; the exact directory depends on the installed PHP version.
- Check memory and swap with
free -h. Note total RAM, used RAM, available RAM, and swap activity. - Check CPU capacity with
nprocand inspect load withuptimeor your monitoring system. - List PHP versions and services. For an example PHP 8.2 installation, use
systemctl status php8.2-fpm; substitute the version actually installed on your VPS. - Review Nginx virtual hosts in
/etc/nginx/sites-enabled/and pool files in the corresponding PHP-FPM configuration directory. - Measure representative traffic: requests per second, response-time percentiles, PHP error rates, database latency, disk wait, and peak concurrency. A quiet test page is not a substitute for production-shaped traffic.
Reserve memory for Ubuntu itself, Nginx, the database, queues, monitoring agents, and a safety margin before assigning RAM to PHP workers. If the VPS swaps during a peak, adding FPM children usually makes latency worse rather than better.
Quick wins for a faster PC:
Repair Windows errors before they cause bigger problemsFix Now →Scan for outdated or missing drivers - takes under a minuteDriver Scan →When separate PHP-FPM pools are useful
A pool can have its own Unix user and group, listener, PHP settings, log files, and process limits. Give a site or workload a separate pool when it needs a distinct filesystem identity, independent restart behavior, different concurrency limits, or separate observability.
| Design | Advantages | Costs and limits | Use when |
|---|---|---|---|
| One shared pool | Lowest memory use and simplest administration | A busy site can consume the shared worker limit; logs and tuning are less granular | Sites have similar trust, traffic, and PHP requirements |
| One pool per site | Separate Unix identities, limits, logs, and restart scope | Each pool needs spare capacity and adds configuration to maintain | Sites need different users, fairness, or failure domains |
| Dedicated pool for a workload | Protects a queue, API, or administrative application from unrelated traffic | More complex capacity planning; a small pool can become a bottleneck | A workload has unusual request duration or priority |
Pools are an operational boundary, not a complete security boundary. The PHP manual explicitly warns: “Pools are not a security mechanism, because they do not provide full separation; e.g. all pools would use a single OPcache instance.” Use filesystem permissions, application isolation, patching, and—when a hard boundary is required—separate containers or virtual machines.
Create and connect a dedicated pool
1. Create the Unix account and directories
Create a non-login account for the site if it does not already have one, then ensure its document root and writable directories have deliberate ownership. Do not make the entire web root writable by Nginx merely to solve an upload problem.
Rank #2
- 5-in-1 USB-C Hub: Experience comprehensive connectivity featuring a Power Delivery input, two USB-A 2.0 ports, a USB-A 3.0 port, and an HDMI port. (Note: The USB-C power delivery input port is only for connecting an external wall charger to power your laptop and cannot power peripheral devices.)
- 90W Pass-Through Charging: Achieve optimal charging with 90W pass-through power to your laptop, supported by a total input of 100W, with the hub reserving 10W for operational efficiency. (Note: Wall charger not included.)
- Quick Data Transfers: Accelerate your productivity with rapid data transfers using a high-speed 5Gbps USB 3.0 port and two 480Mbps USB 2.0 ports.
- 4K HDMI Display: Enhance your visual experience with a hub capable of delivering 4K resolution at 30Hz in both mirror and extend modes. Please note that this hub is compatible with MacBook (macOS 12 and newer), Windows 10 and 11, ChromeOS, and laptops equipped with DP Alt Mode and Power Delivery. Note: This device is not compatible with Linux.
- What You Get: Anker USB-C Hub (5-in-1, 4K HDMI), welcome guide, 18-month warranty, and our friendly customer service.
sudo adduser --system --group --no-create-home siteuser
sudo install -d -o siteuser -g siteuser /srv/example.com
Use your actual path and account names. The Nginx worker account (commonly www-data on Ubuntu) needs read and execute access to the application and write access only where the application genuinely requires it.
2. Define the pool
Copy the distribution pool as a starting point or create a file such as /etc/php/8.2/fpm/pool.d/example.conf. The following is a conservative example; its process counts are starting values, not a benchmark:
[example]
user = siteuser
group = siteuser
listen = /run/php/example.sock
listen.owner = www-data
listen.group = www-data
listen.mode = 0660
pm = dynamic
pm.max_children = 12
pm.start_servers = 3
pm.min_spare_servers = 2
pm.max_spare_servers = 5
access.log = /var/log/php8.2-fpm-example.access.log
slowlog = /var/log/php8.2-fpm-example.slow.log
request_slowlog_timeout = 5s
Use the installed PHP version in paths and service names. The socket directory must exist at boot; Ubuntu’s packaged PHP-FPM service normally creates /run/php. Check ownership and mode after starting the service.
3. Point the Nginx server block at that socket
Inside the relevant virtual host, a typical PHP location is:
location ~ .php$ {
try_files $uri =404;
include snippets/fastcgi-php.conf;
fastcgi_pass unix:/run/php/example.sock;
}
The Ubuntu include supplies standard FastCGI parameters, including the script filename on many releases. If you build the parameters yourself, ensure you set fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name; and do not accidentally override it with a path from another virtual host. Keep try_files $uri =404; so Nginx does not pass arbitrary nonexistent paths to PHP.
Rank #3
- Sleek 7-in-1 USB-C Hub: Features an HDMI port, two USB-A 3.0 ports, and a USB-C data port, each providing 5Gbps transfer speeds. It also includes a USB-C PD input port for charging up to 100W and dual SD and TF card slots, all in a compact design.
- Flawless 4K@60Hz Video with HDMI: Delivers exceptional clarity and smoothness with its 4K@60Hz HDMI port, making it ideal for high-definition presentations and entertainment. (Note: Only the HDMI port supports video projection; the USB-C port is for data transfer only.)
- Double Up on Efficiency: The two USB-A 3.0 ports and a USB-C port support a fast 5Gbps data rate, significantly boosting your transfer speeds and improving productivity.
- Fast and Reliable 85W Charging: Offers high-capacity, speedy charging for laptops up to 85W, so you spend less time tethered to an outlet and more time being productive.
- What You Get: Anker USB-C Hub (7-in-1), welcome guide, 18-month warranty, and our friendly customer service.
4. Validate and reload
- Test Nginx syntax with
sudo nginx -t. - Test PHP-FPM configuration with the versioned service, for example
sudo php-fpm8.2 -twhen that binary is available. - Reload PHP-FPM and Nginx through systemd:
sudo systemctl reload php8.2-fpmfollowed bysudo systemctl reload nginx. - Request a harmless PHP endpoint and inspect both Nginx’s error log and the pool’s log. Remove any temporary diagnostic script that exposes configuration details.
A reload applies configuration without unnecessarily dropping existing connections. Use a restart only when a reload is unavailable or a process remains unhealthy.
Size pm.max_children from real memory use
pm.max_children is the concurrency ceiling for a pool. The PHP documentation defines it as the limit on “the number of simultaneous requests that will be served.” It is not a target throughput number and not a count that should be copied from another VPS.
A practical sizing formula
First determine a memory budget for PHP:
PHP budget = available RAM - Ubuntu/Nginx - database - other services - safety margin
max_children ≈ PHP budget / measured PHP worker RSS
Measure several workers during representative traffic, not immediately after startup. The Linux resident set size (RSS) includes shared pages, so treat the result as an estimate and validate it under load. For example, if you deliberately reserve 1,200 MB for PHP and observe a 120 MB working-set size per busy worker, a starting ceiling is about 10 children, not 12; the difference leaves room for variation and allocator growth. This arithmetic is an illustration, not a universal recommendation.
Use the smallest ceiling that handles normal concurrency without a queue growing continuously. If requests spend most of their time waiting on a database or remote API, adding children can multiply pressure on that dependency. If workers are CPU-bound, more children than available CPU capacity may only increase context switching.
What to observe while tuning
- FPM active and idle processes, maximum active processes, and whether the pool reaches its limit.
- Nginx upstream response time and queueing symptoms.
- Worker RSS, total available memory, swap-in/out, and OOM-killer events.
- Database connection count, lock time, slow queries, disk latency, and network wait.
- Application error rates and latency percentiles during both normal and peak periods.
Raise pm.max_children only when the pool is demonstrably saturated and memory and downstream services have headroom. Lower it when the VPS swaps, the database is overwhelmed, or latency rises as concurrency increases.
Rank #4
- Dual Converters, Infinite Potential:Includes 2× USB C male to USB A female adapters and 2× USB A male to USB C female adapters. Perfect for a wide range of uses—tablets with Bluetooth keyboards, expand USB ports on macbook, and more. Two different converters for all your daily needs
- Next-Level 10Gbps & 3A Charging: No more slow 480Mbps, this usb to usb c adapter has a transfer speed of up to 10Gbps, allowing you to do more transferring in less time. This usb adapter fits both USB A and USB C charger, supporting up to 3A fast charging
- Upgraded Exquisite Craftsmanship: With an aluminum alloy housing and metal connector, the usbc to usb adapter is extremely durable and sturdy. Rigorously tested to withstand more than 10,000 times of plugging and unplugging, ensuring long-lasting performance
- Broad Compatible: The usb c to usb adapter widely supports all USB C/ USB A devices like laptops, tablets, cellphones, car chargers, and phone chargers. Such as compatible with MacBook Pro/Air 2023/2022, Thunderbolt 4/3 Devices,Apple MagSafe Watch 9/8/7/SE/Ultra, iPad Pro 2022/2021, Samsung Galaxy S23/S20/S10, and iPhone 17/16/15 Pro. Plug and play
- Please Note: To reach 10Gbps speed, keep the cable under 3.3 ft. For USB A Male to USB C adapters, try flipping the USB C connector. USB C Male to USB A adapters support bidirectional 10Gbps transfer within 3.3 ft
Choose static, dynamic, or ondemand
| Mode | Process behavior | Strength | Trade-off |
|---|---|---|---|
static |
Keeps exactly pm.max_children workers |
Predictable latency and no process-start delay | Reserves the full worker memory footprint even when idle |
dynamic |
Starts at pm.start_servers, maintains pm.min_spare_servers, and caps idle workers at pm.max_spare_servers; never exceeds pm.max_children |
Good balance for steady sites with bursts | More settings to tune and some process churn |
ondemand |
Starts workers only when requests arrive and retires idle workers after pm.process_idle_timeout |
Low idle memory use for infrequent traffic | Cold-start latency and process churn during bursts |
When static fits
Use static when traffic is consistently high, worker memory is predictable, and the VPS has enough reserved RAM to keep the full set resident. It can reduce startup variability, but it makes an oversized count expensive all day.
When dynamic fits
dynamic is a sensible default for most continuously used web applications. Set pm.start_servers near the normal warm concurrency, then keep minimum and maximum spare counts modest. If requests arrive in bursts, increase the spare floor only after confirming that memory remains safe.
When ondemand fits
Choose ondemand for low-volume sites, staging systems, and pools that must release idle memory. Set pm.process_idle_timeout long enough to avoid constantly killing and recreating workers. For latency-sensitive bursts, the startup cost can outweigh the memory savings.
Unix socket or TCP listener?
| Listener | Best fit | Configuration and risk |
|---|---|---|
| Unix socket | Nginx and PHP-FPM on the same VPS | Use a path such as /run/php/example.sock; control ownership and mode so only the intended Nginx account can connect |
| TCP loopback | Local setups that require a port or standardized upstream definitions | Bind to 127.0.0.1 or another local address and configure listen.allowed_clients; never expose the FPM port publicly |
| TCP on a private network | FPM deliberately runs on another host | Use firewall rules, encrypted transport where appropriate, client restrictions, and capacity planning for network failure |
For a single-host Ubuntu VPS, a Unix socket is usually the simplest secure choice. PHP documents that an exposed FastCGI endpoint can permit arbitrary code execution. A socket is not automatically safe: a permissive mode or directory can still let unintended local users submit requests. Verify with stat /run/php/example.sock and review parent-directory permissions.
Use buffering and caching deliberately
FastCGI buffering
Nginx buffering lets it read an upstream response into memory and temporary files before sending it to a client. That can prevent a slow client from tying up an FPM worker, but buffer sizes are workload-specific. Leave the distribution defaults until measurements show upstream back-pressure or excessive temporary-file I/O. Change one buffer directive at a time and watch memory, disk writes, and response-time percentiles.
Best Value
- 5-in-1 Connectivity: Equipped with a 4K HDMI port, a 5 Gbps USB-C data port, two 5 Gbps USB-A ports, and a USB C 100W PD-IN port. Note: The USB C 100W PD-IN port supports only charging and does not support data transfer devices such as headphones or speakers.
- Powerful Pass-Through Charging: Supports up to 85W pass-through charging so you can power up your laptop while you use the hub. Note: Pass-through charging requires a charger (not included). Note: To achieve full power for iPad, we recommend using a 45W wall charger.
- Transfer Files in Seconds: Move files to and from your laptop at speeds of up to 5 Gbps via the USB-C and USB-A data ports. Note: The USB C 5Gbps Data port does not support video output.
- HD Display: Connect to the HDMI port to stream or mirror content to an external monitor in resolutions of up to 4K@30Hz. Note: The USB-C ports do not support video output.
- What You Get: Anker 332 USB-C Hub (5-in-1), welcome guide, our worry-free 18-month warranty, and friendly customer service.
FastCGI cache
FastCGI caching can remove PHP execution for cache-safe responses. Define a cache zone, a stable cache key, methods to cache (normally GET and HEAD), an expiration policy, and explicit bypass and no-cache rules. Do not cache responses that depend on a logged-in identity, authorization header, cart, session, administrator interface, preview state, or a state-changing request.
Do these 3 things before closing this tab:
1Repair Windows errors before they cause bigger problems2Scan for outdated or missing drivers - takes under a minute3Clear out junk files and repair common Windows errors- Bypass and do not store requests with session or authentication cookies unless the application explicitly marks them public.
- Exclude POST, PUT, PATCH, and DELETE unless the application and cache policy explicitly support them.
- Bypass cache for administrative paths, checkout, account pages, and personalized API responses.
- Provide a controlled purge or versioning strategy when content changes.
- Confirm that cache hits do not leak one user’s response to another user.
Buffering improves transport behavior; caching changes correctness and freshness. Treat them as separate decisions and validate each with response headers, logs, and application tests.
Expose FPM status and slow requests safely
Enable the pool’s status path and slow log so you can distinguish worker saturation from database or network latency. A typical pool can include:
pm.status_path = /fpm-status
ping.path = /fpm-ping
slowlog = /var/log/php8.2-fpm-example.slow.log
request_slowlog_timeout = 5s
Route these endpoints only through an internal Nginx location, allow the monitoring address, and deny public access. Status output can reveal process counts and request details; it should never be an unauthenticated Internet endpoint. Set the slow threshold from your service-level objective rather than copying five seconds blindly.
Correlate FPM status with Nginx access logs and host metrics. A full pool with low CPU but high database wait indicates a downstream bottleneck. High CPU with short PHP requests suggests compute pressure. Normal FPM utilization with slow responses points toward disk, network, or an upstream service.
What’s actually slowing this PC down?
Pick the symptom - the matching free tool is one click away.
Operational workflow for safe changes
- Write down the current pool and Nginx configuration, traffic window, and baseline latency and error metrics.
- Change one variable: pool assignment, process count, mode, buffer, or cache rule—not several at once.
- Run
nginx -tand the PHP-FPM configuration test before reloading. - Reload through systemd, then watch logs and memory for at least one representative peak.
- Compare p50, p95, and p99 latency, error rate, swap, worker RSS, database load, and cache behavior.
- Keep a rollback copy and revert immediately if memory pressure, correctness errors, or tail latency worsens.
Pool changes can alter fairness. A large pool for one site may starve every other site even when each site’s individual configuration looks reasonable. Set explicit ceilings and reserve capacity for critical workloads.
Troubleshoot common failures
| Symptom | Likely cause | Checks and fix |
|---|---|---|
| 502 Bad Gateway | FPM stopped, wrong socket path, or socket permissions | Check systemctl status php8.2-fpm, confirm listen matches fastcgi_pass, inspect socket ownership, and read Nginx’s error log |
| “Primary script unknown” | Incorrect SCRIPT_FILENAME or a missing file |
Verify the virtual host root, real file path, and FastCGI include; keep try_files $uri =404 |
| Workers constantly at max | Too little capacity, slow PHP, or a blocked database/API | Inspect slow logs and downstream timings before raising the limit; add children only with memory headroom |
| VPS runs out of memory | pm.max_children or multiple pools exceed the RAM budget |
Lower ceilings, reduce idle workers, fix leaks or slow dependencies, and verify swap and OOM logs |
| High latency after switching to ondemand | Worker cold starts during bursts | Use dynamic with a small warm reserve or increase the idle timeout if memory permits |
| Private page served from cache | Missing cookie, authorization, method, or path bypass rule | Disable caching for the affected route, purge entries, add explicit bypass/no-cache conditions, and test as multiple users |
Final implementation checklist
- Each PHP location uses the intended pool socket or restricted local TCP endpoint.
SCRIPT_FILENAMEresolves to the requested file, and nonexistent scripts return 404.- Pool users, groups, socket ownership, and writable directories follow least privilege.
pm.max_childrencomes from measured worker memory and a documented RAM budget.- The selected process mode matches traffic frequency, burstiness, and latency requirements.
- FPM status and slow logs are enabled only on protected internal endpoints.
- Nginx and PHP-FPM configuration tests pass before every reload.
- FastCGI cache rules exclude authenticated, personalized, administrative, and state-changing responses.
- Metrics cover memory, swap, CPU, database load, worker saturation, latency, errors, and cache correctness.
The most effective optimization is usually disciplined capacity management rather than a magic directive value: isolate pools where operations require it, keep the listener private, size workers from evidence, and verify every change against real traffic and downstream limits.
Quick Recap
Product prices and availability are accurate as of the date/time indicated and are subject to change. Any price and availability information displayed on Amazon at the time of purchase will apply.




