liip/functional-test-bundle
Symfony bundle providing base classes and helpers for functional tests, plus a DI-aware mock builder for unit tests. Includes tools for command testing, logged clients, query counting, examples, and parallel test runs.
symfony/http-client, symfony/process, or symfony/dependency-injection). For pure Laravel, this is not directly applicable without significant abstraction layers.phpunit, laravel/testcase) already cover ~80% of these use cases, but the bundle adds DI-aware mocking and Symfony-specific conveniences (e.g., WebTestCase extensions).WebTestCase base class with pre-authenticated clients.DB::enableQueryLog(), but no bundled assertion helpers).symfony/browser-kit, symfony/security). Laravel would need:
symfony/http-client) for Client simulations.symfony/security) for authentication helpers.symfony/dependency-injection) for mocking (Laravel’s container is incompatible).QueryCounter) via standalone classes (extract logic from the bundle).SymfonyClient facade for BrowserKit).laravel/browsershot for headless testing, mockery for DI mocking).QueryCounter logic).WebTestCase) may diverge from Laravel’s HttpTestCase, requiring dual maintenance.actingAs() is simpler than Symfony’s loginClient().partialMock() or Mockery may suffice; Symfony’s DI mocking is niche.DB::listen().Why not use Laravel’s built-in testing tools?
QueryCounter, advanced DI mocking)?Symfony Integration Strategy:
Alternatives Evaluation:
HttpTestCase with custom assertions.symfony/browser-kit directly without the bundle.Long-Term Viability:
HttpTestCase + Http::fake() can replace BrowserKit.actingAs() is Laravel-native; Symfony’s loginClient() is redundant.Mockery or partialMock() covers DI mocking.symfony/http-client (for API testing).symfony/security (for complex auth).symfony/dependency-injection (for advanced service mocking).| Feature | Laravel Native | Symfony Bundle | Recommendation |
|---|---|---|---|
| Functional Tests | HttpTestCase |
WebTestCase |
Use Laravel’s (simpler) |
| Pre-Auth Clients | actingAs() |
loginClient() |
Use Laravel’s |
| Service Mocking | Mockery |
DI Mock Builder | Use Mockery or partialMock() |
| Query Counting | DB::listen() |
QueryCounter |
Implement custom assertion |
| Command Testing | Artisan::call() |
runCommand() |
Use Laravel’s |
Assessment Phase:
QueryCounter).Pest PHP for faster test writing).Pilot Integration:
QueryCounter logic into a Laravel service).SymfonyClient for BrowserKit).laravel/browsershot for headless testing).Full Adoption (High Risk):
composer require symfony/browser-kit symfony/security symfony/dependency-injection
WebTestCase:
use Liip\FunctionalTestBundle\Test\WebTestCase as SymfonyWebTestCase;
use Illuminate\Foundation\Testing\TestCase;
abstract class LaravelWebTestCase extends TestCase {
protected function makeClient(array $credentials = null) {
return SymfonyWebTestCase::makeClient($credentials);
}
}
Fallback Plan:
QueryCounter) into standalone classes.WebTestCase methods.actingAs() works with database users, while Symfony’s loginClient() supports UserInterface. Custom adapters may be needed.Phase 1: Low-Risk Adoption (1-2 weeks):
QueryCounter).Phase 2: Pilot Testing (2-3 weeks):
Phase 3: Full Integration (3-4 weeks):
Phase 4: Optimization:
v2.0) and avoid major upgrades.How can I help you explore Laravel packages today?