我在App\Commands
命名空间中创建了 CLI 程序的测试套件。我遇到的问题是,laravel容器似乎无法解决测试方法依赖关系,也无法解决laravel帮助程序.......我在 Windows 10 。
PHP代码:
<?php
use Illuminate\Foundation\Testing\WithoutMiddleware;
use Illuminate\Foundation\Testing\DatabaseMigrations;
use Illuminate\Foundation\Testing\DatabaseTransactions;
use ACME\SomeClass;
class CLICommandTest extends TestCase
{
use DatabaseTransactions;
protected $key = '';
protected $someClass = null;
public function __construct(SomeClass $someClass)
{
parent::__construct();
$this->someClass = $someClass;
$this->key = config('someconfig')['key'];
}
/*
* test handle method
*/
public function testHandle()
{
//assertions
}
}
我创造了&amp;包括服务提供商:
<?php
use ACME\SomeClass;
$this->app->bind('ACME\SomeClass', function($app){
return new SomeClass($value);
});
当我从phpunit
或PATH
运行vendor/bin
时出现此错误:
PHP Fatal error: Uncaught TypeError: Argument 1 passed to CLICommandTest::__construct() must be an instance of ACME\SomeClass, none given, called in phar://C:/PHPUnit/phpunit/phpunit/Framework/TestSuite.php on line 475 and defined in C:\path\tests\CLICommandTest.php:16
Stack trace:
#0 phar://C:/PHPUnit/phpunit/phpunit/Framework/TestSuite.php(475): CLICommandTest->__construct()
#1 phar://C:/PHPUnit/phpunit/phpunit/Framework/TestSuite.php(880): PHPUnit_Framework_TestSuite::createTest(Object(ReflectionClass), 'testHandle')
#2 phar://C:/PHPUnit/phpunit/phpunit/Framework/TestSuite.php(195): PHPUnit_Framework_TestSuite->addTestMethod(Object(ReflectionClass), Object(ReflectionMethod))
#3 phar://C:/PHPUnit/phpunit/phpunit/Framework/TestSuite.php(297): PHPUnit_Framework_TestSuite->__construct(Object(ReflectionClass))
#4 phar://C:/PHPUnit/phpunit/phpunit/Framework/TestSuite.php(381): PHPUnit_Framework_TestSuite->addTestSuite(Object(ReflectionClass))
#5 phar://C:/PHPUnit/phpunit/phpunit/Framework/TestSuit in C:\path\tests\CLICommandTest.php on line 16
Fatal error: Uncaught TypeError: Argument 1 passed to CLICommandTest::__construct() must be an instance of ACME\SomeClass, none given, called in phar://C:/PHPUnit/phpunit/phpunit/Framework/TestSuite.php on line 475 and defined in C:\path\tests\CLICommandTest.php on line 16
TypeError: Argument 1 passed to CLICommandTest::__construct() must be an instance of ACME\SomeClass, none given, called in phar://C:/PHPUnit/phpunit/phpunit/Framework/TestSuite.php on line 475 in C:\path\tests\CLICommandTest.php on line 16
Call Stack:
0.0036 492584 1. {main}() C:\PHPUnit\phpunit:0
0.1375 8875000 2. PHPUnit_TextUI_Command::main() C:\PHPUnit\phpunit:515
0.1375 8878160 3. PHPUnit_TextUI_Command->run() phar://C:/PHPUnit/phpunit/phpunit/TextUI/Command.php:106
0.1375 8878160 4. PHPUnit_TextUI_Command->handleArguments() phar://C:/PHPUnit/phpunit/phpunit/TextUI/Command.php:117
0.1624 10379328 5. PHPUnit_Util_Configuration->getTestSuiteConfiguration() phar://C:/PHPUnit/phpunit/phpunit/TextUI/Command.php:663
0.1624 10379912 6. PHPUnit_Util_Configuration->getTestSuite() phar://C:/PHPUnit/phpunit/phpunit/Util/Configuration.php:796
0.1651 10381496 7. PHPUnit_Framework_TestSuite->addTestFiles() phar://C:/PHPUnit/phpunit/phpunit/Util/Configuration.php:885
0.1651 10381496 8. PHPUnit_Framework_TestSuite->addTestFile() phar://C:/PHPUnit/phpunit/phpunit/Framework/TestSuite.php:409
0.1732 10916648 9. PHPUnit_Framework_TestSuite->addTestSuite() phar://C:/PHPUnit/phpunit/phpunit/Framework/TestSuite.php:381
0.1732 10917104 10. PHPUnit_Framework_TestSuite->__construct() phar://C:/PHPUnit/phpunit/phpunit/Framework/TestSuite.php:297
0.1733 10982344 11. PHPUnit_Framework_TestSuite->addTestMethod() phar://C:/PHPUnit/phpunit/phpunit/Framework/TestSuite.php:195
0.1733 10982760 12. PHPUnit_Framework_TestSuite::createTest() phar://C:/PHPUnit/phpunit/phpunit/Framework/TestSuite.php:880
0.1735 10986272 13. CLICommandTest->__construct() phar://C:/PHPUnit/phpunit/phpunit/Framework/TestSuite.php:475
问题是什么?
答案 0 :(得分:1)
在类的use
块名称中应该匹配:
<?php
use ACME\SomeClass; // <== see, it should be SomeClass here, not someClass
$this->app->bind('ACME\SomeClass', function($app){
return new SomeClass($value);
});
除此之外,您的class CLICommandTest extends TestCase
实际上延伸了\PHPUnit_Framework_TestCase。它的构造函数签名是:
public function __construct($name = null, array $data = [], $dataName = '')
第一个参数是测试的名称,它是可选的。您的
public function __construct(SomeClass $someClass)
以更严格的要求覆盖签名:第一个参数是必需的,它必须具有类型SomeClass
。它制动合同,因此测试运行器无法实例化测试用例。
我建议阅读Laravel testing和PHPUnit docs以了解如何编写测试以及为什么很少需要扩展构造函数。
看起来你也想使用setUp/tearDown方法:
class CLICommandTest extends TestCase
{
use DatabaseTransactions; // <== please double check you need the trait here
protected $key = '';
protected $someClass = null;
public function setUp()
{
// here you probably want to create an instance of your application
$this->someClass = new SomeClass;
$this->key = 'value of the key';
}
...
答案 1 :(得分:0)
Laravel和phpunit是独立的框架。只有在laravel应用程序的某些部分(控制器,事件等)中,才能传递类依赖关系,服务容器才能解析它们。 phpunit与此无关。
虽然您仍然可以使用辅助函数来利用容器:
$someObject = app()->make(SomeClass::class);
但是,对于测试,您可能想要模拟对象而不是从头开始构建它,在这种情况下使用Mockery库。