Я пытаюсь найти способ отменить все изменения базы данных (mysql) (транзакции) после завершения моих тестов. Не после каждого метода тестирования, а после того, как все они выполнены. Я читал, что для такого подхода используется черта DatabaseTransactions
, но она откатывает транзакции БД после каждого метода тестирования. Операция выглядит так:
Run Test1 -> Perform DB transactions -> Rollback -> Run Test2 ... -> Run LastTest
Но что мне нужно:
Run Test1 -> Perform DB transactions -> Run Test2 ..... -> Run LastTest -> Rollback
PS: я знаю, что должен использовать другую базу данных для тестирования и могу использовать черту RefreshDatabase
для этого. Но в моем случае я не могу использовать другую базу данных. Пожалуйста, не спрашивайте, почему)
Может быть, вам следует запустить тесты с макетом, чтобы предотвратить реальные изменения? В противном случае вам решать, что вы сделали и как это отменить.
Ваши тесты должны быть независимыми, то есть вы должны иметь возможность запускать один тест, не полагаясь на другие тесты, предоставляющие определенное состояние базы данных. Если вы делаете это ради ускорения тестов (поскольку откат после каждого теста действительно медленнее), то вы можете рассмотреть возможность запуска mysqldump в своей базе данных перед тестами, а затем восстановление после него (это можно автоматизировать в сценарии или с помощью хуки phpunit). Конечно, это сделает его медленнее, если вам действительно нужно запустить какой-либо тест самостоятельно, поскольку вы будете выполнять резервное копирование и восстановление всей базы данных.
@Techno Потому что база данных слишком большая и не написана с миграциями. У нас уже есть база данных разработки, независимая от производства. Всякий раз, когда какие-либо изменения (такие как добавление индексов, столбцов или изменение типа столбца или что-то еще) в рабочей базе данных, они также обновляют разрабатываемую базу данных. Но если нам понадобится третий, нам нужно будет сделать те же изменения в трех разных местах.
@apokryfos Я пишу тесты для проверки своих API, и все они зависят друг от друга. Пользователь не может выполнить 2cn API до выполнения 1-го. И в каждом API я обновляю некоторые данные о клиентах в базе данных и использую их для будущих API. Тогда каков наилучший подход для моего случая?
Насколько мне известно, вам не нужны миграции для копирования/вставки БД. Просто используйте mysqldump, чтобы создать копию и импортировать ее;)
Неважно чем написано, после каждого изменения в БД нам нужно будет копировать/вставлять БД. Миграции - это просто более простой способ сделать это, поэтому я указал на это
Я не понимаю, зачем вам нужно все синхронизировать, так как это для тестирования и ничего больше, но если вы настаиваете на использовании отвертки вместо молотка, сделайте это. Я не знаю, почему гвоздь не входит.
Плохая практика — разрабатывать тесты таким образом. Тесты предназначены для проверки отдельной функции или модуля и должны быть автономными. Если ваш 2-й тест зависит от первого, вы должны изменить его и вместо этого настроить 2-й тест, чтобы иметь необходимое состояние в базе данных для запуска без каких-либо зависимостей или лучше использовать насмешки.
Всем, кто, как и я, может запутаться в будущем, я настоятельно рекомендую использовать Mocking для модульного тестирования, чтобы подделать как вашу базу данных, так и сторонние API. Проведя еще несколько исследований, я обнаружил, что модульные тесты должны быть независимы друг от друга. Они не должны влиять на базу данных, а сторонние API не должны вызываться во время тестирования.
Для большего понимания mocking
в laravel, пожалуйста, ознакомьтесь со ссылками:
https://laravel.com/docs/9.x/mocking
https://ralphjsmit.com/laravel-mock-dependencies
https://matthewdaly.co.uk/blog/2018/02/25/unit-testing-your-laravel-controllers
Но в моем случае я не могу использовать другую базу данных. Пожалуйста, не спрашивайте, почему >> ПОЧЕМУ?