我正在使用symfony4开发应用程序,但我使用的是api平台。我已经为特定实体(例如Car)创建了一个自定义数据提供程序。 CarCollectionDataProvider还原所有蓝色汽车。
<?php
namespace App\DataProvider;
use ApiPlatform\Core\Bridge\Doctrine\Orm\Extension\PaginationExtension;
use ApiPlatform\Core\Bridge\Doctrine\Orm\Util\QueryNameGenerator;
use ApiPlatform\Core\DataProvider\CollectionDataProviderInterface;
use ApiPlatform\Core\DataProvider\RestrictedDataProviderInterface;
use App\Entity\Car;
use Doctrine\Common\Persistence\ManagerRegistry;
use Generator;
final class CarCollectionDataProvider implements CollectionDataProviderInterface, RestrictedDataProviderInterface
{
private $managerRegistry;
private $paginationExtenstion;
public function __construct(ManagerRegistry $managerRegistry, PaginationExtension $paginationExtension)
{
$this->managerRegistry = $managerRegistry;
$this->paginationExtenstion = $paginationExtension;
}
public function supports(string $resourceClass, string $operationName = null, array $context = []): bool
{
return Car::class === $resourceClass;
}
public function getCollection(string $resourceClass, string $operationName = null): Generator
{
$queryBuilder = $this->managerRegistry
->getManagerForClass($resourceClass)
->getRepository($resourceClass)->createQueryBuilder('car')
->where('car.color = :color')
->setParameter('color', 'blue');
$this->paginationExtenstion->applyToCollection($queryBuilder, new QueryNameGenerator(), $resourceClass, $operationName, []);
yield $this->paginationExtenstion->getResult($queryBuilder, $resourceClass, $operationName, []);
}
}
我如何在自定义项中注入api平台的分页扩展名 dataprovider(CarCollectionDataProvider)。
答案 0 :(得分:1)
如果您一直想要添加标准,例如-> where('car.color =:color')到某种资源的所有收集操作的查询中,则自定义扩展名更合适,并且可以使用默认分页(和过滤器):
// api/src/Doctrine/CarCollectionExtension.php
namespace App\Doctrine;
use ApiPlatform\Core\Bridge\Doctrine\Orm\Extension\QueryCollectionExtensionInterface;
use ApiPlatform\Core\Bridge\Doctrine\Orm\Util\QueryNameGeneratorInterface;
use App\Entity\Car;
use Doctrine\ORM\QueryBuilder;
final class CarCollectionExtension implements QueryCollectionExtensionInterface
{
public function applyToCollection(QueryBuilder $queryBuilder, QueryNameGeneratorInterface $queryNameGenerator, string $resourceClass, string $operationName = null): void
{
if ($resourceClass != Car::class) return;
$rootAlias = $queryBuilder->getRootAliases()[0];
$queryBuilder->andWhere($rootAlias. '.color = :color');
$queryBuilder->setParameter('color', 'blue');
}
}
您可以通过在if语句中添加以下内容来使此扩展程序特定于某个操作:
|| $operationName == 'get_blue'
({from the docs)如果您不使用自动配置,则必须注册自定义扩展名:
# api/config/services.yaml
services:
# ...
'App\Doctrine\CarCollectionExtension':
tags:
- { name: api_platform.doctrine.orm.query_extension.collection }
如果您还想为项目操作添加条件,请参见the docs on Extensions
答案 1 :(得分:0)
这对我来说很好:
<?php
namespace App\DataProvider;
use ApiPlatform\Core\Bridge\Doctrine\Orm\Extension\PaginationExtension;
use ApiPlatform\Core\Bridge\Doctrine\Orm\Extension\QueryResultCollectionExtensionInterface;
use ApiPlatform\Core\Bridge\Doctrine\Orm\Util\QueryNameGenerator;
use ApiPlatform\Core\DataProvider\CollectionDataProviderInterface;
use ApiPlatform\Core\DataProvider\RestrictedDataProviderInterface;
use App\Entity\Car;
use Doctrine\Common\Persistence\ManagerRegistry;
final class CarCollectionDataProvider implements CollectionDataProviderInterface, RestrictedDataProviderInterface
{
private $managerRegistry;
private $paginationExtension;
private $context;
public function __construct(ManagerRegistry $managerRegistry, PaginationExtension $paginationExtension)
{
$this->managerRegistry = $managerRegistry;
$this->paginationExtension = $paginationExtension;
}
public function supports(string $resourceClass, string $operationName = null, array $context = []): bool
{
$this->context = $context;
return Car::class === $resourceClass;
}
public function getCollection(string $resourceClass, string $operationName = null)
{
$queryBuilder = $this->managerRegistry
->getManagerForClass($resourceClass)
->getRepository($resourceClass)->createQueryBuilder('car')
->where('car.color = :color')
->setParameter('color', 'blue');
$this->paginationExtension->applyToCollection($queryBuilder, new QueryNameGenerator(), $resourceClass, $operationName, $this->context);
if ($this->paginationExtension instanceof QueryResultCollectionExtensionInterface
&& $this->paginationExtension->supportsResult($resourceClass, $operationName, $this->context)) {
return $this->paginationExtension->getResult($queryBuilder, $resourceClass, $operationName, $this->context);
}
return $queryBuilder->getQuery()->getResult();
}
}