I have been researching this issue for days and although many people ask this question I never found a clear and concise answer.
I am running:
- PHP Unit: Version 3.7.21
- WordPress: Version 3.5.1
- OS: Ubuntu 11.10
- MySQL: Version 5.1.69-0ubuntu0.11.10.1
- PHP: Version 5.3.6-13ubuntu3.10
Long story short, I have the basic wordPress core downloaded into a directory on my computer. I have successfully downloaded and installed pear and phpunit. I tested phpunit by writing basic tests on simple php files which worked fine. My issue is when I run phpunit on a wordpress site (which I have not changed the core WP files of).
I get the error:
“PHP Fatal error: Call to a member function main() on a non-member
object in /< root_directory>/functions.php on line 779”.
This error corresponds to this code-segment:
function wp( $query_vars = '' ) {
global $wp, $wp_query, $wp_the_query;
$wp->main( $query_vars ); // Line 779
if ( !isset($wp_the_query) )
$wp_the_query = $wp_query;
}
After some intense internet crawling I found many people had errors on this exact line so I know there is some general thing like an environment setting or our setup process that gave us all this error.
Some solutions I have read and tried that did not work for me:
- Change the required file in your “index.php” file.
- Place a require of “load.php” above the head in your “index.php” file.
- Re-install WordPress
- Change boot-strap and phpunit environments.
I have been a web-developer for 5 years but I have never used WordPress for one of my clients before. Once I can get this set up writing the unit tests will be easy; but I have no idea what is causing this issue. Any links to guides/tutorials or clear explanations would be greatly appreciated. Thank you for your time.
–EDIT–
The test file I am running is:
<?php
//include PHPUnit
require_once('PHPUnit/Autoload.php');
//include the code to be tested
require_once('../index.php');
// extend the PHPUnit class
class StackTest extends PHPUnit_Framework_TestCase {
public function testOne(){
$this->assertTrue(TRUE);
$this->assertEquals(2,2);
$this->assertTrue(1<3);
}
}
?>
I didn’t use any WordPress specific function tests; I just ran basic tests that work when I don’t access the homepage of my WordPress site and fail when I do.
Also another note; I properly set up my config file and my database. The site works perfectly fine, it is just the PHPUnit tests are unable to successfully run the websites files.
Unit tests for WordPress are a tricky thing. If you need to test the code with a live database, etc. I would suggest using the official WordPress test suite. I’ve gotten unit tests running for a plugin using that method before, but it wasn’t pretty, and was fairly unreliable. If you need to do it that way, though, I personally wouldn’t think of doing it with anything but the official test suite.
There’s tons of information on the official repository on the core make blog. In your test suite’s bootstrap file you need to set up any options that you need to override. Normally, that’s going to be active plugins (so you can test your plugin):
After that, you need to include the
includes/bootstrap.php
file from the core test suite. Once that’s done, your tests ought to run as “expected”.In my experience, however, those kinds of tests never run as expected, since the database and all of the WordPress code introduce an insane amount of hidden dependencies and state to your tests. Because of that, I prefer to just mock the WordPress api and run my tests without all those dependencies and all that state.
To do that, I use WP_Mock. It lets you simulate the WordPress environment with fine-grained control. For example, if you have a function that needs to add a filter to
'the_content'
and then callthe_content()
, the following code for WP_Mock lets you test that:If the expectations set forth in WP_Mock are not met, it throws an exception, causing the test to fail.