首页 文章

PHP symfony4:KernelTestCase中的依赖注入命令

提问于
浏览
1

您好我正在尝试为symfony4控制台命令创建单元测试,但我无法正确注入依赖项 . 我对symfony4很新,所以也许这对你们来说是个基本问题 .

我的单元测试看起来像这样:

<?php

namespace App\Tests\Command;

use App\Command\ExecuteSalesTaskCommand;
use Symfony\Bundle\FrameworkBundle\Console\Application;
use Symfony\Bundle\FrameworkBundle\Test\KernelTestCase;
use Symfony\Component\Console\Tester\CommandTester;
use Psr\Log\LoggerInterface;
use App\Repository\TaskRepository;

class ExeculteSalesTaskCommandTest extends KernelTestCase
{
    /**
     * @param LoggerInterface $logger
     * @param TaskRepository  $taskRepository
     */
    public function testExecute(LoggerInterface $logger, TaskRepository $taskRepository)
    {
        $kernel      = self::bootKernel();
        $application = new Application($kernel);

        $application->add(new ExecuteSalesTaskCommand($logger,$taskRepository));

        # UPDATED
        $logger         = self::$kernel->getContainer()->get(LoggerInterface::class);
        $taskRepository = self::$kernel->getContainer()->get(TaskRepository::class);

        $command       = $application->find('app:execute-sales-task');
        $commandTester = new CommandTester($command);
        $commandTester->execute(
            [
                'command'  => $command->getName(),
            ]
        );

        // the output of the command in the console
        $output = $commandTester->getDisplay();
        $this->assertContains('Execute sales resulted: ', $output);
    }
}

我的问题是我得到了这样的注入错误:

ArgumentCountError:函数App \ Tests \ Command \ ExeculteSalesTaskCommandTest :: testExecute()的参数太少,0传递,正好2个预期

更新:当我从容器中取出依赖项时,我得到这种错误:

有1个错误:1)App \ Tests \ Command \ ExeculteSalesTaskCommandTest :: testExecute Symfony \ Component \ DependencyInjection \ Exception \ ServiceNotFoundException:编译容器时已删除或内联“Psr \ Log \ LoggerInterface”服务或别名 . 您应该将其公开,或者直接停止使用容器并改为使用依赖注入 .

如何正确地注入必要的依赖项,以便创建ExecuteSalesTaskCommand的实例?

2 回答

  • 1

    我也遇到过类似的问题 . 但以下为我工作 . 我不认为您需要向应用程序添加命令并再次找到它?请找到以下解决方案 . 它可能会帮助别人 .

    <?php
    // BaseCommandTester.php
    /**
     * This is basis for the writing tests, that will cover commands
     *
     */
    namespace App\Tests\Base;
    
    use Symfony\Bundle\FrameworkBundle\Test\KernelTestCase;
    use Symfony\Bundle\FrameworkBundle\Console\Application;
    use Symfony\Component\Dotenv\Dotenv;
    
    class BaseCommandTester extends KernelTestCase
    {
        /**
         * @var
         */
        private $application;
    
        /**
         * to set test environment and initiate application kernel
         */
        public function setUp()
        {
            /**
             * get test env
             */
            $dotenv = new Dotenv();
            $dotenv->load('/var/www/.env.test');
    
            /**
             * boot kernel
             */
            $kernel = self::bootKernel();
            $this->application = new Application($kernel);
            parent::setUp();
        }
    
        /**
         * @return mixed
         */
        public function getApplication()
        {
            return $this->application;
        }
    
        /**
         * @param mixed $application
         */
        public function setApplication($application)
        {
            $this->application = $application;
        }
    
    }
    

    测试用例

    // FeedUpdaterCommandTest.php
    <?php
    
    namespace App\Tests\Command;
    
    use App\Tests\Base\BaseCommandTester;
    use Symfony\Component\Console\Tester\CommandTester;
    
    class FeedUpdaterCommandTest extends BaseCommandTester
    {
        /**
         * test to update all feeds
         */
        public function testExecuteUpdateAll() {
            /**
             * init command tester and executre
             */
            $commandName = 'app:feedUpdater';
            $expectedResult = '[OK] Update Success Feed Type : All';
    
            $command = $this->getApplication()->find($commandName);
            $commandTester = new CommandTester($command);
            $commandTester->execute(array(
                'command' => $command->getName()
            ));
    
            /**
             * get result and compare output
             */
            $result = trim($commandTester->getDisplay());
            $this->assertEquals($result, $expectedResult);
        }
    }
    

    测试结果

    #Run tests
    root@xxx:/var/www# bin/phpunit tests/Command
    #!/usr/bin/env php
    PHPUnit 6.5.13 by Sebastian Bergmann and contributors.
    
    Testing tests/Command
    2018-11-28T07:47:39+00:00 [alert] Successful update of popularProducts Feeds!
    2018-11-28T07:47:39+00:00 [alert] Successful update of topVouchers Feeds!
    .                                                                   1 / 1 (100%)
    
    Time: 1.44 seconds, Memory: 12.00MB
    
    OK (1 test, 1 assertion)
    

    我正在使用以下Sf4版本

    -------------------- --------------------------------------
      Symfony
     -------------------- --------------------------------------
      Version              4.1.7
    

    服务定义及其默认私有

    #config/services.yml
        App\Service\FeedGenerator:
            arguments:
                $feeds: '%feed_generator%'
    

    我认为你不需要再次自动装配 .

  • 0

    我发现问题是我试图手动加载依赖项 . 使用自动装配,如下所示:

    public function testExecute()
    {
        $dotenv = new Dotenv();
        $dotenv->load(__DIR__.'/.env.test');
    
        $kernel      = self::bootKernel();
        $application = new Application($kernel);
    
        $executeSalesCommand = self::$kernel->getContainer()->get(
            'console.command.public_alias.App\Command\ExecuteSalesTaskCommand'
        );
    
        $application->add($executeSalesCommand);
    
        $command       = $application->find('app:execute-sales-task');
        $commandTester = new CommandTester($command);
        $commandTester->execute(
            [
                'command' => $command->getName(),
            ]
        );
    
        // the output of the command in the console
        $output = $commandTester->getDisplay();
    
        // do your asserting stuff
    }
    

    您需要从内核容器中获取命令 . 现在它有效 .

相关问题