experteam/api-testing-bundle
Experteam API Testing Bundle provides testing services for APIs in Symfony 5.4, including a Controller Web Test Case that streamlines controller testing. Install via Composer to simplify API test setup and speed up your testing workflow.
First, the stack mismatch: this is a Symfony 5.4 bundle, not a Laravel package. As a Laravel developer, it will not plug into php artisan test, RefreshDatabase, or $this->getJson(). You can only meaningfully use it if you are working inside a Symfony 5.4 codebase (e.g. an inherited/legacy service). If you are evaluating it for a Laravel project, stop here — Laravel's built-in HTTP testing (getJson, assertJson, actingAs) already covers the same ground with better documentation.
Install (Symfony 5.4 app):
composer require --dev experteam/api-testing-bundle
The README says composer require, but test-only utilities belong in require-dev so production installs with --no-dev stay clean.
Where to look first: the README only advertises one thing — a Controller Web Test Case. Since it is undocumented, inspect the vendor directory before writing tests:
ls vendor/experteam/api-testing-bundle/src
head -n 40 vendor/experteam/api-testing-bundle/src/*Test*.php
Confirm three things immediately:
Experteam\ApiTestingBundle\...).WebTestCase or KernelTestCase.config/bundles.php.First use case: extend the provided base class in tests/Controller and hit one endpoint.
// namespace verified from vendor/ — do not copy blindly
use Experteam\ApiTestingBundle\Tests\ControllerWebTestCase;
final class ProductControllerTest extends ControllerWebTestCase
{
public function testListReturnsJson(): void
{
$client = static::createClient();
$client->request('GET', '/api/products');
$this->assertResponseIsSuccessful();
$this->assertResponseHeaderSame('content-type', 'application/json');
}
}
Ensure config/packages/test/framework.yaml has test: true, or createClient() will throw before your test logic runs.
Wrap the base class in your own. Do not extend the vendor class directly from every test. Create tests/AbstractApiTestCase.php extending ControllerWebTestCase, then put auth, fixtures, and JSON helpers there. This is the primary extension point, since none is documented.
abstract class AbstractApiTestCase extends ControllerWebTestCase
{
protected KernelBrowser $client;
protected function setUp(): void
{
parent::setUp();
$this->client = static::createClient();
}
protected function loginAs(string $email, string $password): void
{
$this->client->request('POST', '/api/login', [], [], [
'CONTENT_TYPE' => 'application/json',
], json_encode(compact('email', 'password')));
$token = json_decode($this->client->getResponse()->getContent(), true)['token'];
$this->client->setServerParameter('HTTP_AUTHORIZATION', 'Bearer '.$token);
}
}
One test class per resource, data providers for payload variants. This keeps the setUp cost low and makes failures readable in CI:
/** @dataProvider invalidPayloads */
public function testCreateRejectsBadPayload(array $payload): void
{
$this->loginAs('[email protected]', 'secret');
$this->client->jsonRequest('POST', '/api/products', $payload);
$this->assertResponseStatusCodeSame(422);
}
Isolate database state. Use dama/doctrine-test-bundle (transaction rollback per test) or reload fixtures in setUp(). Never rely on leftover rows from a previous test.
Integration tips:
APP_ENV=test and a dedicated .env.test (SQLite or a throwaway MySQL schema).phpunit.xml.dist env vars rather than relying on shell exports.php bin/console doctrine:schema:create --env=test before phpunit.Compatibility is the biggest risk. Symfony 5.4 is past end-of-life for feature work and only recently received security support. This bundle makes no promises about Symfony 6 or 7. Check vendor/experteam/api-testing-bundle/composer.json for symfony/framework-bundle constraints before upgrading anything.
Zero stars, zero dependents, one-line README, no tests of its own. Treat this as a source snippet, not a dependency. For a single test-case class, the lowest-risk move is to copy the class into tests/Support/ and drop the Composer dependency entirely. You get the same behaviour with no supply-chain or upgrade exposure.
Do not commit it to require. If it ever pulls in a transitive dependency, composer install --no-dev on production will still resolve it unless it is require-dev.
static::createClient(), not self::. The client reboots the kernel between requests; using self:: or a stale client instance across requests causes "kernel already booted" errors.
Bundle registration ambiguity. If the class only extends WebTestCase, you likely do not need to register the bundle in config/bundles.php. Registering it unnecessarily in bundles.php means it also loads in dev/prod, which is avoidable noise.
Failures are opaque. When an assertion fails, dump the raw response:
$this->assertResponseIsSuccessful(
$this->client->getResponse()->getContent()
);
And disable exception catching to see the real stack trace:
$this->client->catchExceptions(false);
Container/test config drift. The classic error — "You cannot create the client used in functional tests if the 'framework.test' option is not set to true" — means your test environment config is missing. Fix config/packages/test/framework.yaml, not the bundle.
Version pinning. There is no evidence of semantic versioning discipline. In composer.json, pin to an exact tag ("experteam/api-testing-bundle": "1.0.0") rather than ^1.0.
Where to extend: since no extension points are documented, your only levers are (a) subclassing the test case, (b) traits for shared assertions/auth, and (c) a project-level AbstractApiTestCase. Plan accordingly — there is no configuration surface to hook into.
How can I help you explore Laravel packages today?