TDD with WordPress global functions and PHPUnit

I’m trying to do tdd with my WordPress plugins. The problem is that using WP_UnitTestCase is way way to slow and despite the name provides integration tests rather than unit tests. So instead of using WP_UnitTestCase I have been working on creating truly isolated tests for my plugins but the problem is that I find myself using a lot of WordPress global functions such as wp_get_current_user() or wp_signon().

Currently I have a file of the functions I’ve used that are basically stubbed out.

Read More

What is the best way to go about mocking these functions? Ultimately I’d like to be able to mock these functions the same way as I would other methods with the ability to control their output and test that they’re called. Is there a more OO way to set the current user or check for authentication that I’m missing?

Related posts

1 comment

  1. You can create a class for invoking global WordPress functions. This can have a map of methods to global functions or even invoking whatever method is called that starts with wp_ using __call or any other way you come up with.

    Then you would use this class from inside your plugin to call the functions. I suppose plugins are instantiated by WordPress so you won’t be able to inject this class on production code. So you can make it externally settable to allow injecting a mock but if none is provided, use the real one.

    Like this:

    <?php    
    
    class Plugin
    {
        private $invoker;
    
        public function getWpInvoker()
        {
            if (!isset($this->invoker)) {
                $this->invoker = new WordPressGlobalFunctionsInvoker();
            }
        }
    
        public function setWpInvoker(WordPressGlobalFunctionsInvoker $invoker)
        {
            $this->wp_invoker = $invoker;
        }
    
        public function foo()
        {
            $current_user = $this->getWpInvoker()->wp_get_current_user();
        }
    }
    

    In the test you would mock the WordPressGlobalFunctionsInvoker class and inject the mock to the plugin so you take control over the functions being called.

Comments are closed.