pdfloresjdav/api-doc-bundle
pdfloresjdav/api-doc-bundle is a Symfony bundle that turns PHP API metadata into readable documentation, helping teams publish endpoint references, schemas, and request/response details with minimal setup. It fits into existing Symfony projects and aims to make API docs easier to generate and mainta...
This is a Symfony bundle, not a Laravel package — despite the framing, the first thing a Laravel developer needs to accept is that you cannot drop this into a Laravel app. pdfloresjdav/api-doc-bundle is a fork of the classic nelmio/api-doc-bundle, which means it hooks into Symfony's bundle registration, DI container, and annotation reader. If you're maintaining a legacy Symfony service and stumbled onto this fork, here's the shortest path to value:
Install and register
composer require pdfloresjdav/api-doc-bundle
In a modern Symfony (config/bundles.php):
return [
// ...
Nelmio\ApiDocBundle\NelmioApiDocBundle::class => ['all' => true],
];
On legacy Symfony 2/3, add it to AppKernel::registerBundles() instead.
Route + config skeleton — create config/packages/nelmio_api_doc.yaml:
nelmio_api_doc:
name: 'My API'
areas:
default:
path_patterns: ['^/api']
And add the doc route in config/routes/nelmio_api_doc.yaml:
nelmio_api_doc:
resource: '@NelmioApiDocBundle/Resources/config/routing.yml'
prefix: /api/doc
First use case — annotate a single controller action with a @ApiDoc / @SWG block (depending on which generation of this fork you're pinned to; check composer.json — if it pulls swagger-php you're on the v3-style annotations, otherwise it's the v2 @ApiDoc style). Something like:
/**
* @ApiDoc(
* resource=true,
* description="List users",
* statusCodes={200="OK"}
* )
*/
public function listUsersAction() { ... }
Then hit /api/doc — you should see the HTML renderer or JSON spec, depending on the Accept header (application/json gives you the raw spec).
Where to look first: the Resources/doc/ directory in the installed vendor folder. The README is minimal; the real documentation lives in the Symfony docs of the upstream nelmio/api-doc-bundle project, and this fork's docs are a snapshot of that at whatever commit it forked from. Also inspect the fork's git log (git log --oneline -20 in vendor/pdfloresjdav/api-doc-bundle) to see how far behind upstream you are — that number tells you how much of the official docs apply.
Annotation-driven endpoint docs (the core workflow). Every public API controller action gets a doc block. This is verbose but centralizing the contract in the controller keeps docs adjacent to behavior, which is the whole point of the package. Group related actions with @ApiDoc(resource=true) and use input/output class references so the bundle introspects your DTOs for field listings:
/**
* @ApiDoc(
* resource=true,
* input="App\DTO\CreateUser",
* output="App\Entity\User",
* statusCodes={201="Created", 422="Validation failed"}
* )
*/
Areas for multi-surface APIs. If you have /api/v1, /api/v2, and internal /admin/api, define separate "areas" in config and let the bundle filter by path_patterns. This is the cleanest way to ship distinct Swagger docs per audience without duplicating annotations. Pair with documentation blocks for shared schemas so you don't retype your Error model forty times.
YAML-defined global metadata + annotation-defined per-endpoint details. The single most maintainable pattern is: all cross-cutting info (info, host, basePath, security definitions, reusable definitions) in nelmio_api_doc.yaml under documentation:, and only endpoint-specific annotations in code. The documentation: key accepts a full OpenAPI/Swagger fragment, so you can paste in a spec you've validated elsewhere.
Frontend integration. Once /api/doc.json (or /api/doc with Accept: application/json) returns a spec, point any Swagger UI / ReDoc / Stoplight Elements build at it. If you're building a Vue/React SPA, generate a typed client (e.g. openapi-generator) against that URL in CI — that's the highest-leverage thing you can do with this bundle.
CI / static artifact pattern. In CI, boot a kernel, dump the spec to a file (bin/console + a small command or a scripted HTTP GET against a local server), and commit or artifact it. This lets frontend devs build against the spec without running the Symfony app. Watch out for auth: the doc route is often behind a firewall role; either allow IS_AUTHENTICATED_ANONYMOUSLY for it or generate the spec via kernel boot, bypassing HTTP.
Versioning via spec generation, not code. Don't try to have one controller serve two doc versions. Instead, copy the spec artifact per release tag and diff it. The bundle gives you no diff tooling, but the JSON spec is deterministic enough that git diff on committed spec files works fine as a contract-change review mechanism.
nelmio/api-doc-bundle. Before committing to it, diff against the upstream tags and, if you're on anything recent, strongly prefer the upstream nelmio/api-doc-bundle directly. A fork with no stars is a liability for security patches and Symfony version compatibility.Nelmio\ApiDocBundle namespace. If any other dependency pulls upstream nelmio/api-doc-bundle, Composer will either conflict or (worse) replace-shadow it silently and you'll get a Frankenstein autoloader. Explicitly composer why nelmio/api-doc-bundle and check replace/provide in the fork's composer.json before assuming you're in control.use statement missing at the top of the file (use Nelmio\ApiDocBundle\Annotation\ApiDoc;), (b) path_patterns in the area excluding your route, or (c) annotation reader not enabled in config.yml (framework.annotations false on older Symfony). Check in that order.bin/console cache:clear after touching nelmio_api_doc.yaml — always. Also on some versions the annotation metadata cache lives in var/cache/.../annotations/; nuke it if you see phantom endpoints.@Rest\Get / @Route vs @ApiDoc order. The bundle resolves the HTTP method from routing. If you have two actions with the same route name or use @Method({"GET","POST"}) without a @ApiDoc per-method block, the spec merges methods incorrectly. One @ApiDoc per HTTP verb per route.Nelmio\ApiDocBundle\Formatter\FormatterInterface lets you write custom output (e.g., JSON:API-flavored docs). Nelmio\ApiDocBundle\Extractor\Handler\AbstractHandler is the documented way to inject auth/header schemas automatically — far better than copy-pasting security blocks into every annotation.@OA (via darkaonline/l5-swagger), areas ≈ @OA\Server, the config documentation: block ≈ l5-swagger's api.docs.info config. If you're actually in Laravel, use darkaonline/l5-swagger instead; this bundle will not work there.How can I help you explore Laravel packages today?