Error with Laravel and DTO
API Platform version(s) affected: api-platform/laravel 4.0.3
Description
When attempting to use Data Transfer Objects (DTOs) with Laravel, as described in the documentation, I encounter a 404 error on the newly added route:
{
"@context": "/api/contexts/Error",
"@id": "/api/errors/404.jsonld",
"@type": "hydra:Error",
"trace": [
{
"file": "XXXX\\project\\vendor\\api-platform\\laravel\\State\\SwaggerUiProvider.php",
"line": 57,
"function": "provide",
"class": "ApiPlatform\\State\\Provider\\ReadProvider",
"type": "->"
},
....
}
How to reproduce
- Create a DTO resource class:
<?php
namespace App\ApiResource;
use ApiPlatform\Metadata\Get;
use App\State\CatProvider;
#[Get(uriTemplate: '/cats/{id}', provider: CatProvider::class)]
class Cat
{
public string $id;
public string $name;
public int $age;
}
- Configure
api-platform.phpto include the DTO resource path:
// config/api-platform.php
// ...
return [
'resources' => [
app_path('ApiResource'),
app_path('Models'),
],
// ...
];
- Implement the
CatProviderclass that fetches data from the model:
<?php
namespace App\State;
use ApiPlatform\Metadata\Operation;
use ApiPlatform\State\ProviderInterface;
use App\Models\Animal as AnimalModel;
final class CatProvider implements ProviderInterface
{
public function provide(Operation $operation, array $uriVariables = [], array $context = []): object|array|null
{
$animal = AnimalModel::find($uriVariables['id']);
return new AnimalModel([
'id' => $animal->id,
'name' => $animal->name,
'age' => $animal->age
]);
}
}
- Register the provider in the AppServiceProvider:
<?php
namespace App\Providers;
use App\State\CatProvider;
use Illuminate\Support\ServiceProvider;
use Illuminate\Contracts\Foundation\Application;
class AppServiceProvider extends ServiceProvider
{
/**
* Register any application services.
*/
public function register(): void
{
$this->app->singleton(CatProvider::class, function (Application $app) {
return new CatProvider();
});
$this->app->tag([CatProvider::class], 'provider');
}
/**
* Bootstrap any application services.
*/
public function boot(): void
{
//
}
}
Expected Behavior
The GET /cats/{id} route should return the correct data for the Cat resource using the CatProvider.
@noweh Thanks for your report.
There is an error in the following documentation. You need in your CatProvider to return the DTO ApiResource/Cat.php and not the model Models/Animal.php.
However, if you still want to do this you need to add the $fillable property to your Dto, like this:
<?php
namespace App\Models;
use ApiPlatform\Metadata\ApiResource;
use Illuminate\Database\Eloquent\Model;
#[ApiResource]
class Animal extends Model
{
protected $fillable = ['id', 'name', 'age'];
}
This PR https://github.com/api-platform/docs/pull/2036 will solve the issue in the documentation
This issue has been automatically marked as stale because it has not had recent activity. It will be closed if no further activity occurs. Thank you for your contributions.