Jesses Software Engineering Blog
PHP Performance with APC Opcache
PHP is an interpreted language, opposed to a compiled language, meaning that each time a PHP file is requested it must be parsed and interpreted. By using an opcode cacher, such as APC, you are allowing compiled PHP code to be stored in shared memory. Thus when files are requested multiple times they do not have to be repeatedly parsed and interpreted. APC also offers a user cache which allows your application to store data in memory between requests, but that will be covered in a future article.
NOTE: As of PHP 5.5.0, there is an opcode cache extension bundled by default and easily accessible to 5.2, 5.3, and 5.4 via PECL. I still use APC, as it is easy to set up and to manage, but it is worth taking the time to research the native PHP Opcache.
To install APC (on CentOs 6.x) you may need to get some prerequisite packages first:
yum install php-pear php-devel httpd-devel gcc make
After you have the necessary packages you can install APC:
pecl install apc
Other useful commands:
pecl upgrade apc pecl uninstall apc
Update PHP ini
After installing APC you will need to add the extension to your PHP .ini file. On my server, I keep all of my extensions in their own files in /etc/php.d:
; apc.ini, include the APC extension extension=apc.so
After the extension has been included, go ahead and reload the Apache configs. At this point phpinfo() should output information about APC.
APC Admin Page
Next you are going to need to figure out how you want to access the APC admin page, which is a stand alone PHP file. I usually set it up as a subdomain: cache.domain.com. To do this you will need to setup a CNAME record on your server, or with your host. Once that is set up create a vhost file to a directory in your www folder and copy the following file into that directory:
cp /usr/share/pear/apc.php /var/www/html/<dirpath>
I also like to restrict that directory, whether by password or IP address, to prevent random people from coming across your cache admin page. There is little reason for you to access the admin page from outside of your intranet or designated office IP address. An example .htaccess:
Deny from all Allow from <IP address>
After the DNS and vhost are set up, reload Apache again and verify that you can pull up the APC admin page.
Update APC File
One last thing to secure is to password protect the APC admin file itself. Open apc.php and you will see two constants at the top for ADMIN_USERNAME and ADMIN_PASSWORD. Set these values and also verify that the USE_AUTHENTICATION constant is set to 1.
Finally you will want to customize your cache settings. For a complete list of APC configurations visit php.net. Whenever you make changes to your cache’s configurations you will need to reload Apache for them to take affect. Beware, that in doing so you will also clear your cache. Some of the configurations I generally update (all settings should be placed in your APC .ini file):
apc.enabled – This turns APC on and off
apc.max_file_size – Max file size to cache. Set this number depending on how large your source files are. I usually keep it at 1M or 2M.
apc.num_files_hint – A rough estimate of the number of source files on your server that will need to be cached.
apc.shm_size – Size of EACH memory segment in RAM. Depending on your caching needs you can adjust how much memory the cache will have available. After APC has been enabled, browse through all the sites on your server and check how much of the default memory is being used. Then adjust this number accordingly so that you have enough memory to cache what you need but not too much that you’re wasting resources.
apc.shm_segments – Number of segments. It is best to keep this at 1 and allocate a larger shm_size
apc.stat – Whether or not the server checks last modified times of a file before it is served from the cache. This will prevent files from being served from the cache after the file has been updated. However, when this is set to off you will see a “significant performance boost”, but you will need to manually clear the cache or restart the web server when new code is pushed up.
apc.ttl – How long the opcode cache files stay in the cache for, in seconds.
apc.user_entries_hint – Estimated number of user entries in cache
apc.user_ttl – How long the user cache is kept, in seconds.
apc.cache_by_default – Used in conjunction with .filters
apc.filters – This can be used with cache_by_default if you need to set up regex based caching i.e. picking which file name patterns to cache. Set the .cache_by_default to off and the .filters to your regex expressions.
Now that everything is set up all you have to do is check in on the admin page from time to time. A couple things to keep an eye out for:
Memory Usage – Memory usage is the amount of memory the cache is using in RAM. You want to make sure you are not maxing out your allocated space, and to up the shm_size when needed. Adversely, if you are not using all your memory, lower the shm_size. WARNING: Your cache may be flushed if you max out your memory so be sure to determine your memory requirements before implementing in a production environment.
Hits & Misses – This is the count of how many times files are read from the cache (hits) and how many times files have to be interpreted (misses). Note that each file will be a miss when it is first loaded into the cache. In a healthy cache, the percentage of hits to misses should be steadily increasing over time, and the number of cached files should match the number of misses.
High Fragmentation Percentage - Fragmentation, as a simple definition, happens when a file’s opcode cache size has changed and it will no longer fit in the same cache space. You want this value to be as close to 0% as possible and bumping up your shm_size will generally help solve highly fragmented caches.
Cache Full Count – In the tables on the left side of the APC admin page, under the header File Cache Information, you will find the Cache Full Count. This will tell you how many times your cache has filled up and is a good indicator for if you need to allocate more memory.