From c71fbdf8efe890b886e0cc06a5ab06b0efead3e2 Mon Sep 17 00:00:00 2001 From: Daniel Subiabre Date: Thu, 18 Apr 2024 14:33:08 +0200 Subject: [PATCH] Allow to filter users by email, name or username --- src/Entity/User.php | 7 ++-- src/Filter/UserQueryFilter.php | 64 ++++++++++++++++++++++++++++++++++ 2 files changed, 66 insertions(+), 5 deletions(-) create mode 100644 src/Filter/UserQueryFilter.php diff --git a/src/Entity/User.php b/src/Entity/User.php index 52bc4da..a918236 100644 --- a/src/Entity/User.php +++ b/src/Entity/User.php @@ -2,9 +2,9 @@ namespace App\Entity; -use ApiPlatform\Doctrine\Orm\Filter\SearchFilter; use ApiPlatform\Metadata as API; use App\Entity\Interface\UserOwnedInterface; +use App\Filter\UserQueryFilter; use App\Repository\UserRepository; use Doctrine\Common\Collections\ArrayCollection; use Doctrine\Common\Collections\Collection; @@ -29,10 +29,7 @@ use Symfony\Component\Validator\Constraints as Assert; #[API\Put(security: 'is_granted("USER_EDIT", object)')] #[API\Delete(security: 'is_granted("USER_EDIT", object)')] #[API\Patch(security: 'is_granted("USER_EDIT", object)')] -#[API\ApiFilter(filterClass: SearchFilter::class, properties: [ - 'username' => 'partial', - 'name' => 'partial' -])] +#[API\ApiFilter(filterClass: UserQueryFilter::class, properties: ['query'])] #[UniqueEntity(fields: ['username'], message: 'This usernames already exists.')] #[UniqueEntity(fields: ['email'], message: 'This email address is already registered.')] #[ORM\Entity(repositoryClass: UserRepository::class)] diff --git a/src/Filter/UserQueryFilter.php b/src/Filter/UserQueryFilter.php new file mode 100644 index 0000000..4be1eaf --- /dev/null +++ b/src/Filter/UserQueryFilter.php @@ -0,0 +1,64 @@ +isPropertyEnabled($property, $resourceClass) + ) { + return; + } + + $rootAlias = $queryBuilder->getRootAliases()[0]; + $parameterName = $queryNameGenerator->generateParameterName($property); + + $queryBuilder + ->andWhere(sprintf('%s.email LIKE :%s', $rootAlias, $parameterName)) + ->orWhere(sprintf('%s.name LIKE :%s', $rootAlias, $parameterName)) + ->orWhere(sprintf('%s.username LIKE :%s', $rootAlias, $parameterName)) + ->setParameter($parameterName, $value); + } + + public function getDescription(string $resourceClass): array + { + $description = []; + foreach ($this->properties as $property => $strategy) { + $description["$property"] = [ + 'property' => $property, + 'type' => Type::BUILTIN_TYPE_STRING, + 'required' => false, + 'description' => 'Query Users by email, name or username. Fuzzy.', + ]; + } + + return $description; + } +}