cakedc/users 注册后自动登录

cakedc/users autologin after registration

我正在使用带有 cakedc/users 插件的 cakephp 4.2.6。我想在注册后自动登录用户,而不需要首先通过点击电子邮件中的link激活帐户。

我的想法是创建一个事件监听器并监听 Users.Global.afterRegister 事件,但是我不知道如何使用新的身份验证登录用户。

插件文档中有一个类似的用例https://github.com/CakeDC/users/blob/master/Docs/Documentation/Events.md

你的方法在我看来是正确的,使用 afterRegister 事件在你有权访问 Authenticatication 组件的控制器中创建侦听器,

// note this example is handling auto-login after the user validated the email sent (click the validation token link sent to his email address)
EventManager::instance()->on(
    \CakeDC\Users\Plugin::EVENT_AFTER_EMAIL_TOKEN_VALIDATION,
    function($event){
        $users = $this->getTableLocator()->get('Users');
        $user = $users->get($event->getData('user')->id);
        $this->Authentication->setIdentity($user);
    }
);

或使用请求检索身份验证服务并设置身份,就像在此处完成的那样https://github.com/cakephp/authentication/blob/master/src/Controller/Component/AuthenticationComponent.php#L273

这是我最终得到的结果,到目前为止它似乎有效:

<?php
namespace App\Event;
use Authentication\AuthenticationService;
use Authentication\AuthenticationServiceInterface;
use Authentication\AuthenticationServiceProviderInterface;
use Authentication\Middleware\AuthenticationMiddleware;
use Psr\Http\Message\ServerRequestInterface;

use Cake\Event\EventListenerInterface;
use Cake\Datasource\FactoryLocator;
use Cake\Log\Log;

class UserEventListener implements EventListenerInterface
{
    public function implementedEvents(): array
    {
        return [
            'Users.Global.afterRegister' => 'autoLogin',
        ];
    }

    public function autoLogin($event)
    {

        $user = $usersTable->get($event->getData('user')->id);
        $request = $event->getSubject()->getRequest();
        $response = $event->getSubject()->getResponse();
        $authenticationService = $this->getAuthenticationService($request);
        $authenticationService->persistIdentity($request, $response,  $user);
        
    }
        

    public function getAuthenticationService(ServerRequestInterface $request): AuthenticationServiceInterface
    {
        $authenticationService = new AuthenticationService([
            'unauthenticatedRedirect' => \Cake\Routing\Router::url([
            'controller' => 'Users',
            'action' => 'login',
            'plugin' => null,
            'prefix' => null
            ]),
            'queryParam' => 'redirect',
        ]);

        // Load identifiers, ensure we check email and password fields
        $authenticationService->loadIdentifier('Authentication.Password', [
            'fields' => [
                'username' => 'email',
                'password' => 'password',
            ]
        ]);

        // Load the authenticators, you want session first
        $authenticationService->loadAuthenticator('Authentication.Session');
        // Configure form data check to pick email and password
        $authenticationService->loadAuthenticator('Authentication.Form', [
            'fields' => [
                'username' => 'email',
                'password' => 'password',
            ],
            'loginUrl' => \Cake\Routing\Router::url([
            'controller' => 'Users',
            'action' => 'login',
            'plugin' => null,
            'prefix' => null
            ]),
        ]);

        return $authenticationService;
    }

}