November 23rd, 2010

Zend Studio – Unit Testing

How to properly configure and setup Zend Studio 6.1 for Unit Testing & debugging.

— Matt Fellows —

Unit Testing in Zend Studio

I though I might share my experience with Zend Studio 6.1.1, whilst debugging and unit testing a recent web application. Although in general, Zend Studio is a fantastic product and can make your life extremely easy, it is not without it’s nuances. Here are some of the problems (and resolutions of course!) that I came across.

Poor Error reporting

By far the most frustrating thing about Unit Testing in Zend Studio, is that when your test cases don’t work, you better be good at debugging, becuause Zend Studio doesn’t report the errors very well. You then end up wasting time you could spend doing other things. However, instead you are spending that time trying to figure out what on earth is going on! I recently had a lot of trouble creating the most basic Zend_Controller test case even though my application appeared to be working correctly. The actual method looked like the following:


public function testHomePageAction()
{
$this->dispatch('/');
$this->assertModule('default');
}

But no matter what I tried, it never asserted the correct module, not even the error module. The errors that were coming back from the system were vague and of no help altogether (see this issue, at least it is on their radar.

What I found (after hours of debugging and trying a number of things), was that during postDispatch() the ErrorHandler was catching an Exception that didn’t appear to be visible during dispatch. If I stepped in to that class in the PHP Debug perspective and set a breakpoint at line 226 of Zend_Controller_Plugin_ErrorHandler


 ...
// Get exception information
$error            = new ArrayObject(array(), ArrayObject::ARRAY_AS_PROPS);
$exceptions       = $response->getException();
$exception        = $exceptions[0];
$exceptionType    = get_class($exception);
$error->exception = $exception;
...

I could look into the Variables window at the $exceptions variable and see the exception that was occurring. It turns out it was just that the Registry had been initialized twice (probably by the testing framework) and that caused it to dispatch twice – once for the intended action and once for the ‘error’.

Lesson: If you are having troubles, cut to the chase and view the Exceptions in Debug mode.

Use your own PHP

The in-built PHP binaries that come with Zend just don’t cut it. No mysqli support, no SoapClient and probably a whole bunch of other things that you or I would require in day to day life. The easiest way to get your application working in and out of Zend Studio is to use the same PHP binary. You can add yours easily into the Studio by adding it to:

Window > Preferences > PHP > PHP Executables > Add

Just point it to the location of your PHP binary and php.ini files and then add the location of the Zend Debugger to your php.ini file as follows:


zend_extension=/usr/apps/Zend/ZendStudioForEclipse-6.1.1/plugins/org.zend.php.debug.debugger.linux.x86_5.2.15.v20080907/resources/php5/ZendDebugger.so

Really really slow Unit Testing / Debugging

If you are finding that to run 1 simple unit test that you have to wait 6 hours (exagerrated) for it to finish and more annoyingly that the IDE itself is unresponsive while doing so, it is probably because you have Code Coverage Statistics and Generate Report options turned on. Do yourself a favour, if you’re not using them, turn it off by unchecking them here:

Window > Preferences > PHP > PHPUnit

Hopefully I have helped some annoyed / frustrated developers.

  • Anthony Thompson

    One minor note, I was having trouble getting into debugging mode actually stopping at breakpoints, stepping, etc., and found the following very helpful tip at http:stackoverflow.comquestions8139891cant-get-zend-studio-and-phpunit-to-work-together

    “If you want ZS to run the PHPunit bootstrap, you have to specifically select the file PHPunit.xml and tell it to run as PHPunit test. If you just select an individual test and run as PHPunit test, the bootstrap will not be run”

    Once I ran as test from phpunit.xml it worked – but it had never worked when I tried run as test on the test file itself in my case, IndexControllerTest.