Version 2 (modified by Vincent Caron, 10 years ago) (diff)




phptop - print system ressource usage statistics from PHP scripts


phptop [options]


Phptop prints per query and average metrics comparable to the 'time' program or shell builtin: wallclock, user and system CPU time along with memory and other ressources usage.

It can be used from the command line to diagnose performance problem in quasi real time (minimum sampling is 1 minute) with minimal overhead, or to generate HTML reports.

It uses a a few lines of PHP which hook into your existing code without any changes, records per query statistics via the standard error log, then collects and prints reports with a standalone program. Phptop itself is written in Perl.


-c, --count N

Limit output to top N URLs (default is 10).

-f, --full-query

Consider full URL with CGI parameters (ie. do not strip ?param=...).

-h, --help

Display a short options summary.

-l, --log path

Logfiles to parse, you may use several -l options and wildcards in paths. Be careful to quote your wildcards in order they are not interpreted by your shell. If no -l options are used, try a few guesses.

-o, --output mode

Output mode: text or html (default is 'text').

-p, --path-only

Only print URL paths, skip the http://<host> prefix.

-s, --sort key

Sort by hit, time, user, sys or mem (default is 'hit'). You may use several -s options, they will generate as much statistics in one go (hence reusing the parsing effort efficiently).

-t, --time N

Parse data from now back to N seconds (default is 300, ie. 5 minutes).

-v, --version

Display version number and copyright information.


Using phptop to print the top CPU (user) consumers for the last 10min:

phptop -l /path/to/error.log -t 600

Getting stats from the last 10 minutes, sorted by hits, from well known log files:

phptop -p

Hint: on a given server, define a shell alias which already sets the proper error log paths. This way you don't have to repeat them again. Bash recipe:

$ echo "alias phptop='phptop -l /home/*/log/error.log'" >>.bashrc
$ source .bashrc
$ phptop -t60


Wallclock, system and user times are cumulated for similar URLs, and the total per URL is shown. It is an absolute time value which must be related to your observation window (-t option). The wallclock time is not a very interesting measure, since it depends both on your server ressources, on the client and on the client-server bandwidth, minus buffering effects. Interpret it with much caution.

The user and system time are CPU ressources. For a one minute observation window (-t 60), on a quad-core system you have 4 minutes (240 seconds) worth of CPU time to be split between user (CPU running application code), system (CPU running kernel code) and idle (CPU waiting I/O or doing nothing). On a busy and healthy server, user and system time add up to the whole available CPU time. If your user and system total time is far from the available CPU time, consult your server loadavg: if it's high (more than your number of CPUs), your server is probably waiting on I/O (more often disk than network); if it's low, your application might be waiting on remote services (think remote HTTP APIs) which are slow or not responding.

The memory figures can't be added, it would not make any sense. Instead simple satistics like maximum and average memory per URL are computed. The peak memory usage is very interesting when running phptop over a large time window (one day or more) to figure out your optimal PHP memory_limit figure, which is itself very useful for proper configuration and usage of system ressources (number of PHP processes, SQL server connections, and so on). Over a short time window it also acts as a poor man's profiler, and can spot.


Phptop hooks into existing code via the auto_prepend_file PHP option. This option might be set and overriden at different levels by other programs (global, per-directory, per-vhost, etc). Since phptop has been verified to have no measurable impact on heavy production servers, it is considered to be a good idea to enable it globally. If your server uses several log files (typically one per virtual host), you will be able to only pickup needed data at analysis time (which is the potentially costly phase).

Phptop records data via the error_log() PHP instruction. The author considers that any sane server setup should have a working error log, and it would have been inefficient and dangerous to handle custom logging (which would obviously end up firing lots of open/write/close, not being properly rotated and so on). It might annoy your monitoring tools, but again if you're serious about monitoring you know how to filter out noise. Logging one (small) text line per request is considered an infinitesimal amount of effort wrt. to the simplest SQL query. A phptop sample is smaller than some user agent string you find in your web server access logs.

At analysis time (when launching phptop itself), care has been taken to read and parse only the needed amount of data. Most importantly it will use the tac(1) command to 'reverse tail' the error logs, and default to a slower method if this command is not found.

The analysis process itself is mostly CPU bound if your error log sits on a reasonably available storage, and runs at approx. 15,000 samples/sec on a 2.4Ghz Intel core. That is why phptop output should be almost instantaneous while analysing the last minutes (eg. -t 300), even on a very busy server (100 req/sec or more).


Phtop should run '-s user' as a default instead of the useless-but-look-ma-my-hits '-s hit'.

Phptop has been extensively used on production servers, but only on GNU/Linux Debian Etch (4.0), Lenny (5.0) and specifically on the AMD64 architecture with PHP 5.2. Tests and reports with other kernels, distributions and PHP versions are warmly welcome.

Please file bugs on (simple registration needed), we try to solve them quickly and release often.



If set and stdout is a tty, overrides the detected terminal width. If there is no terminal (like when piping to another program), set output width.




Written by Vincent Caron

Homepage at

Copyright © 2009,2010,2011 Bearstech. License GPLv3+: GNU GPL version 3 or later <>. This is free software: you are free to change and redistribute it. There is NO WARRANTY, to the extent permitted by law.


time(1), getrusage(2)