使用Symfony Security组件实现基于角色的访问控制,配合API-Platform的自定义数据提供程序实现角色过滤。
首先,在Symfony Security中定义角色:
// src/Security/CustomUserChecker.php
namespace App\Security;
use Symfony\Component\Security\Core\Exception\CustomUserMessageAuthenticationException;
use Symfony\Component\Security\Core\User\UserInterface;
use Symfony\Component\Security\Core\User\UserCheckerInterface;
class CustomUserChecker implements UserCheckerInterface
{
public function checkPreAuth(UserInterface $user)
{
// ...
}
public function checkPostAuth(UserInterface $user)
{
if (!$user->getEnabled()) {
// 用户已禁用
throw new CustomUserMessageAuthenticationException('user.disabled');
}
}
}
在api/config/packages/security.yaml
中配置Symfony Security,启用角色验证:
# api/config/packages/security.yaml
security:
# ...
role_hierarchy:
ROLE_ADMIN: [ROLE_USER]
providers:
custom_provider:
entity:
class: App\Entity\User
property: email
# ...
firewalls:
main:
# ...
pattern: ^/
anonymous: ~
# 添加认证器
guard:
authenticators:
- App\Security\CustomAuthenticator
# 配置登陆、注销路由
logout:
path: app_logout
target: /
# ...
在自定义数据提供程序中实现角色过滤:
// src/DataProvider/UserDataProvider.php
namespace App\DataProvider;
use ApiPlatform\Core\DataProvider\ContextAwareCollectionDataProviderInterface;
use ApiPlatform\Core\DataProvider\RestrictedDataProviderInterface;
use App\Entity\User;
use App\Repository\UserRepositoryInterface;
use Symfony\Component\Security\Core\Security;
class UserDataProvider implements ContextAwareCollectionDataProviderInterface, RestrictedDataProviderInterface
{
private $userRepository;
private $security;
public function __construct(UserRepositoryInterface $userRepository, Security $security)
{
$this->userRepository = $userRepository;
$this->security = $security;
}
public function getCollection(string $resourceClass, string $operationName = null, array