Intereting Posts
Expedia API book.api.ean.com blank Метод «email» для объекта «Symfony \ Component \ Form \ FormView» не существует в SqliGestionCongeBundle: по умолчанию: add.html.twig Функция PHP для проверки времени между заданным диапазоном? Apache не загружает Xdebug, но делает это при запуске из командной строки Проверка JQuery не работает PHP Специальная функция SMTP-почты Возврат ERROR fputs send bytes failed errno = 32 Разбитая труба удалите символы Unicode, но сохраните все специальные и английские символы с preg_replace Как подсчитать и ограничить запись в одном запросе в MYSQL? PHP: регулярное выражение для игнорирования скрытых кавычек в кавычках Получить конкретную информацию об устройстве Объединение нескольких ассоциативных массивов в один массив ассоциативных массивов Получение непрочитанной почты из веб-сервисов обмена через PHP Различия: просмотр страницы Источник против просмотра в Firebug Возвращение ответа JSON из запроса MySQL Как сделать копию объекта без ссылки?

Контрольные контроллеры в Symfony2 с доктриной

Я создал очень простой контроллер REST в Symony2 с вставкой / обновлениями / удалениями базы данных в действиях контроллера.

Есть ли хороший способ написать тесты модуляции / интеграции для этих действий контроллера без загрязнения производственной базы данных? Должен ли я работать с разными средами – или есть ли предлагаемый путь от поставщика инфраструктуры для этого?

Текущий контроллер Пример:

public function postAction() { $json = $this->getRequest()->getContent(); $params = json_decode($json); $name = $params->name; $description = $params->description; $sandbox = new Sandbox(); $sandbox->setName($name); $sandbox->setDescription($description); $em = $this->getDoctrine()->getManager(); $em->persist($sandbox); $em->flush(); $response = new Response('/sandbox/'.$sandbox->getId()); $response->setStatusCode(201); return $response; } 

Текущий тестовый пример:

 class SandboxControllerTest extends WebTestCase { public function testRest() { $client = static::createClient(); $crawler = $client->request('POST', '/service/sandbox', array(), array(), array(), json_encode(array('name' => 'TestMe', 'description' => 'TestDesc'))); $this->assertEquals( 201, $client->getResponse()->getStatusCode() ); } } 

На мой взгляд, вы обязательно должны избегать базы данных изменений с вашими тестами.

Моим любимым способом добиться этого является интуитивно понятный менеджер, находящийся в тестовом клиенте. Например:

 public function testRest() { // create entity manager mock $entityManagerMock = $this->getMockBuilder('Doctrine\ORM\EntityManager') ->setMethods(array('persist', 'flush')) ->disableOriginalConstructor() ->getMock(); // now you can get some assertions if you want, eg.: $entityManagerMock->expects($this->once()) ->method('flush'); // next you need inject your mocked em into client's service container $client = static::createClient(); $client->getContainer()->set('doctrine.orm.default_entity_manager', $entityManagerMock); // then you just do testing as usual $crawler = $client->request('POST', '/service/sandbox', array(), array(), array(), json_encode(array('name' => 'TestMe', 'description' => 'TestDesc'))); $this->assertEquals( 201, $client->getResponse()->getStatusCode() ); } 

Одна вещь с этим решением, о котором вы должны знать, заключается в том, что перед каждым запросом вы должны вводить свою издеваемую службу. Это происходит потому, что клиент перезагружает ядро ​​между каждым запросом (что означает, что контейнер также перестраивается).

редактировать:

Мой подход GET в тестах контроллера заключается в том, что я могу издеваться над репозиториями объектов и т. Д., Чтобы заглушить каждый процесс получения данных из db, но это большая работа, и это не очень удобно, поэтому я предпочитаю в этом случае (я имею в виду только, если мы говорим о тестировании контроллера), фактически получая реальные данные из db. По реальным данным я имею в виду данные, созданные с помощью приборов доктрины. И пока мы не меняем базу данных, мы можем зависеть от приборов.

Но если мы говорим об изменении данных внутри db (методы POST / PUT / DELETE), я всегда использую mocks. Если вы будете использовать em mock и зададите соответствующие ожидания по методам «perist» и «flush», вы можете быть уверены, что данные правильно созданы / обновлены / удалены фактически без каких-либо изменений в базе данных.

Вот что я делаю

в тестовом классе добавьте статическую переменную $ kernel и создайте функцию, загружающую ядро ​​в тестовый режим

 protected static $kernel; protected static $container; public static function setUpBeforeClass() { self::$kernel = new \AppKernel('test', true); self::$kernel->boot(); self::$container = self::$kernel->getContainer(); } 

И как первая строка тестовой функции, вызовите self:setUpBeforeClass()

Это заставляет symfony загружать конфигурационный файл config_test.yml, и вы можете определить другое соединение с базой данных там

Хороший способ сделать это, особенно если вам нужно иметь некоторые тестовые данные в вашей базе данных, используется отдельная база данных SQLite вместе с DoctrineFixturesBundle.

  • Вот как установить FixturesBundle
  • Чистый способ настроить светильники и тесты

    Убедитесь, что расширение SQLite активировано в вашем php