如何实现基于FOSOAuthServerBundle而不使用FOSUserBundle的OAuth服务器?
我的用户类像这样开始:
<?php
namespace AppBundleEntity;
use DoctrineORMMapping as ORM;
use SymfonyComponentSecurityCoreUserUserInterface;
/**
*
* @ORMEntity
* @ORMTable(name="user")
* @ORMEntity(repositoryClass="AppBundleEntityUserRepository")
*/
class User implements UserInterface
我的用户存储库类是这样开始的:
<?php
namespace AppBundleEntity;
use SymfonyBridgeDoctrineSecurityUserUserLoaderInterface;
use SymfonyComponentSecurityCoreUserUserProviderInterface;
use SymfonyComponentSecurityCoreUserUserInterface;
use SymfonyComponentSecurityCoreExceptionUnsupportedUserException;
use DoctrineORMEntityRepository;
use DoctrineORMNoResultException;
class UserRepository extends EntityRepository implements UserLoaderInterface, UserProviderInterface
在我的安全。我包含了以下内容:
providers:
user_db:
entity:
class: AppBundleEntityUser
property: username
最后是config.yml:
fos_oauth_server:
db_driver: orm
client_class: AppBundleEntityOAuthClient
access_token_class: AppBundleEntityOAuthAccessToken
refresh_token_class: AppBundleEntityOAuthRefreshToken
auth_code_class: AppBundleEntityOAuthAuthCode
service:
options:
access_token_lifetime: 3600
user_provider: user_db
#user_provider: AppBundleEntityUserRepository
#user_provider: AppBundleEntityUser
现在它抛出一个异常:
[1] SymfonyComponentDebugExceptionFatalThrowableError: Call to a member function loadUserByUsername() on null
at n/a
in /home/wanderson/api/vendor/friendsofsymfony/oauth-server-bundle/Storage/OAuthStorage.php line 161
at FOSOAuthServerBundleStorageOAuthStorage->checkUserCredentials(object(OAuthClient), 'admin', 'admin')
in /home/wanderson/api/vendor/friendsofsymfony/oauth2-php/lib/OAuth2.php line 929
at OAuth2OAuth2->grantAccessTokenUserCredentials(object(OAuthClient), array('grant_type' => 'password', 'scope' => null, 'code' => null, 'redirect_uri' => null, 'username' => 'admin', 'password' => 'admin', 'refresh_token' => null))
in /home/wanderson/api/vendor/friendsofsymfony/oauth2-php/lib/OAuth2.php line 815
at OAuth2OAuth2->grantAccessToken(object(Request))
in /home/wanderson/api/vendor/friendsofsymfony/oauth-server-bundle/Controller/TokenController.php line 42
at FOSOAuthServerBundleControllerTokenController->tokenAction(object(Request))
in line
at call_user_func_array(array(object(TokenController), 'tokenAction'), array(object(Request)))
in /home/wanderson/api/vendor/symfony/symfony/src/Symfony/Component/HttpKernel/HttpKernel.php line 153
at SymfonyComponentHttpKernelHttpKernel->handleRaw(object(Request), '1')
in /home/wanderson/api/vendor/symfony/symfony/src/Symfony/Component/HttpKernel/HttpKernel.php line 68
at SymfonyComponentHttpKernelHttpKernel->handle(object(Request), '1', true)
in /home/wanderson/api/vendor/symfony/symfony/src/Symfony/Component/HttpKernel/Kernel.php line 169
at SymfonyComponentHttpKernelKernel->handle(object(Request))
in /home/wanderson/api/web/app_dev.php line 30
at require('/home/wanderson/api/web/app_dev.php')
in /home/wanderson/api/vendor/symfony/symfony/src/Symfony/Bundle/FrameworkBundle/Resources/config/router_dev.php line 40
创建一个用户提供者,或者如果你想使用你的存储库类来读取'如何定义像服务一样的存储库'(我不知道它是否在最新版本中工作):
https://stackoverflow.com/a/17230333/6848076https://stackoverflow.com/a/31807608/6848076
但我不建议这样做
<?php
namespace AppBundleSecurityProviderUserProvider;
use DoctrineCommonPersistenceObjectRepository;
use DoctrineORMNoResultException;
use SymfonyComponentSecurityCoreExceptionUsernameNotFoundException;
use SymfonyComponentSecurityCoreUserUserInterface;
use SymfonyComponentSecurityCoreUserUserProviderInterface;
use SymfonyComponentSerializerExceptionUnsupportedException;
use DoctrineORMEntityManager;
class UserProvider implements UserProviderInterface
{
protected $class;
protected $userRepository;
public function __construct(EntityManager $entityManager, $class)
{
$this->class = $class;
$this->userRepository = $entityManager->getRepository($class);
}
public function loadUserByUsername($username)
{
$user = $this->userRepository->findOneBy(array('username' => $username));
if (null === $user) {
$message = sprintf(
'Unable to find an active User object identified by "%s"',
$username
);
throw new UsernameNotFoundException($message, 0, $failed);
}
return $user;
}
public function refreshUser(UserInterface $user)
{
$class = get_class($user);
if (false == $this->supportsClass($class)) {
throw new UnsupportedException(
sprintf(
'Instances of "%s" are not supported',
$class
)
);
}
return $this->userRepository->find($user->getId());
}
public function supportsClass($class)
{
return $this->class === $class
|| is_subclass_of($class, $this->class);
}
}
关于服务,您可以阅读:http://symfony.com/doc/current/service_container.html在{project_directory}/src/AppBundle/Resources/config/service.yml
parameters:
user.class: AppBundleEntityUser
user.provider.class: AppBundleSecurityProviderUserProvider
services:
user.provider:
class: %user.provider.class%
arguments: [@doctrine.orm.entity_manager, %user.class%]
修改config.yml:
fos_oauth_server:
db_driver: orm
client_class: AppBundleEntityOAuthClient
access_token_class: AppBundleEntityOAuthAccessToken
refresh_token_class: AppBundleEntityOAuthRefreshToken
auth_code_class: AppBundleEntityOAuthAuthCode
service:
options:
access_token_lifetime: 3600
user_provider: user.provider
关于安全。Yml你可以阅读:http://symfony.com/doc/current/security.html