Archive for July, 2009

eAccelerator vs APC on PHP 5.2.9

Tuesday, July 7th, 2009

Motivation

A year ago I was working on a website project which used PHP as a language of choice. The project development resulted in quite large amount of PHP code. After a brief research we decided that organising our code the way Zend Framework is organized is our way to go. While ZF’s naming conventions are a nice and effective way to autoload classes and avoid naming conflicts, it is still a bit cumbersome at coding stage (long class names).

At that time I had my first glance at PHP 5.3 feature list and namespaces seemed a good step forward from current practice. Unfortunately stable PHP 5.3 release was far from being released so I had to dump the namespace idea for that particular project. But I decided to migrate to PHP 5.3 as soon as possible.

Another part of the story is server administration. On all the servers I manage I utilise PHP opcode caching. Currently I use eAccelerator and I am satisfied with it’s performance and stability. But eAccelerator’s website (at the moment of this writing) states nothing about PHP 5.3 support. Therefore I was forced to look elsewhere.

Many websites recommend APC with the suggestion that it is being actively maintained, unlike some other opcode caches. I remember back in year 2004 when I was testing it and comparing it to Turck MM cache that its performance sucked. Unfortunately I have no evidence to support my claim, but it is also irrelevant in 2009. Yet “actively maintained” phrase implies hope that APC supports PHP 5.3. And its changelog confirms it.

First stable PHP 5.3 version was released last week and I was psyched to at least test it, but I did not want to be held back by an opcode caching solution, so I decided to compare eAccelerator and APC again. If APC performs as well as eAccelerator does (both on PHP 5.2.9), then I will seriously consider migration to PHP 5.3 and migration from eAccelerator to APC.

Goal

There is a single question to be answered: how does APC perform in comparison to eAccelerator on PHP 5.2.9?

System setup

I used exactly the same system with Apache web server as it is described in this article. I only conducted “Application frontpage” test as it is the only relevant testcase.

I installed APC with the following command

printf “no\n” | /usr/local/httpd/php/bin/pecl install apc

and only enabled it in php.ini by adding

extension=”apc.so”

and removing eAccelerator, with no additional configuration.

Why not PHP 5.3.0 or PHP 5.2.10?

  • PHP 5.3.0: simply because I have not yet tested it and upgraded the systems I manage.
  • PHP 5.2.10: simply because I tried to upgrade but the release is buggy.

Results

eAccellerator vs APC: application frontpage

eAccellerator vs APC: application frontpage

Analysis of results and conclusion

Performance results for both opcode cache solutions are almost identical, difference is negligible. Results at concurrency level higher than 128 are not reliable, I am in a phase of fixing that anomaly. From this test I can conclude that performance-wise you can safely choose any of these two opcode cache solutions.

Stability

I can not comment on the stability of APC more than that I have had no problems with it for this short period of testing time. I have no stability (segfault) problems with eAccelerator in the production environments.

Info/status/control script

What I DO miss with APC is a simple control.php which eAccelerator provides. It gives you an overview of caching statistics.
Update (2009-12-01): Henrik Olsen notified me that APC also includes control script which provides an overview of caching statistics. See comments below for an URI of his article where he demonstrates the subject.

Update

As of today (2009-07-07) the compile results of eAccelerator and APC with PHP 5.3.0 are as follows:

  • eAccelerator v0.9.5.3 – does not compile
  • APC stable v3.0.19 – does not compile
  • APC beta v 3.1.2 – compiles OK, but with some warnings about “–enable-spinlocks” being unrecognised and warning: passing argument 1 of ‘zval_isref_p’ discards qualifiers from pointer target type