My composer project consists of the src
and tests
folders.
The code inside src
is auto-loaded using composers psr4 autoloader like so
"autoload": {
"psr-4": {
"christmas\\":"src/"
}
}
The class to be tested looks like so
namespace christmas;
class Hello
{ //constructor & dependency injection included in real class
public function sayHello()
{
return "HELLO";
}
}
And Finally my test class looks like so
<?php
use PHPUnit\Framework\TestCase;
require_once('../vendor/autoload.php');
use christmas\Hello;
class TestHello extends TestCase
{
public function testSayHelloMethod()
{
$hello = $this->getMockBuilder('Hello')
->getMock();
$hello->expects($this->once())
->method('sayHello')
->will($this->returnValue('HELLO'));
$this->assertEquals(
"HELLO",
$hello->sayHello()
);
}
}
And here is how my i run phpunit
phpunit tests/TestHello
phpunit echoes back the following output
Time: 45 ms, Memory: 4.00 MB
There was 1 warning:
1) tests\Hello::testSayHelloMethod()
Trying to configure method "sayHello" which cannot be configured because it does not exist, has not been specified, is final, or is static
/usr/share/php/PHPUnit/TextUI/TestRunner.php:641
/usr/share/php/PHPUnit/TextUI/Command.php:206
/usr/share/php/PHPUnit/TextUI/Command.php:162
WARNINGS!
Tests: 1, Assertions: 0, Warnings: 1.
Below is a view of how my code is organized,
├── composer.json
├── src
│ └── Hello.php
├── tests
│ └── TestHello.php
└── vendor
What am i missing ? I need to have a passing test with no single warning.
You need to pass the full, namespaced name of the class to the mock builder, i.e. 'christmas\Hello'
. Since you need to pass it as a string, just using "Hello" isn't enough to properly identify the class.
Since you're already have a use
for the class, you can use ::class
to get the full name. For example:
$hello = $this->getMockBuilder(Hello::class)
->getMock();