I am trying to implement symfony validation asset
to the request.
I am passing form-data
from the postman to the route in controller.
#[Route(path: '/test', name: 'test', methods: 'GET')]
public function login(LoginRequest $loginRequest): Response
I have created a loginRequest
DTO as following:
class LoginRequest
{
public function __construct(
/**
* @Assert\NotBlank
*/
public string $username,
/**
* @Assert\NotBlank
*/
public string $password
) {
}
}
But I am getting following error.
Cannot autowire service "App\Dto\LoginRequest": argument "$username" of method "__construct()" is type-hinted "string", you should configure its value explicitly.
Can anybody help me how can I use DTO for validation to params request ?
CodePudding user response:
You need to use the Serializer component in your method and deserialize
your DTO to create an object with your data. Create a request with header Content-Type: application/json
and send data in json format, not form-data
Your DTO should be declared like this:
use Symfony\Component\Validator\Constraints as Assert;
class LoginRequest
{
/**
* @Assert\NotBlank()
*/
public string $username;
/**
* @Assert\NotBlank()
*/
public string $password;
}
Controller method:
use Symfony\Component\Serializer\SerializerInterface;
#[Route(path: '/test', name: 'test', methods: 'GET')]
public function login(Request $request, SerializerInterface $serializer, ValidatorInterface $validator): Response
{
$dto = $serializer->deserialize($request->getContent(), LoginRequest::class, 'json');
$errors = $validator->validate($dto);
if (count($errors) > 0) {
throw new BadRequestHttpException((string) $errors);
}
// ...
}
CodePudding user response:
It's because your application tries to create a service with your DTO and autowire it's contructor arguments.
The defaut service container configuration is the following
# config/services.yaml
services:
# default configuration for services in *this* file
_defaults:
autowire: true # Automatically injects dependencies in your services.
autoconfigure: true # Automatically registers your services as commands, event subscribers, etc.
# makes classes in src/ available to be used as services
# this creates a service per class whose id is the fully-qualified class name
App\:
resource: '../src/*'
exclude: '../src/{DependencyInjection,Entity,Tests,Kernel.php}'
# ...
To exclude your DTO from your service container you could create it in a folder named Dto
and add this folder to the exclude line of the configuration file like this.
exclude: '../src/{DependencyInjection,Entity,Tests,Dto,Kernel.php}'