feat(auth): add OAuth installer
Fixes #1582
OAuth can be installed optionally during ./tempest install auth or directly via ./tempest install auth --oauth.
Not sure how to best handle the UserModel for different OAuth providers, feedback is welcome!
Not sure how to best handle the UserModel for different OAuth providers, feedback is welcome!
I think it's fair to keep a // todo in the generated controller, where people should fill in their own logic. Personally, I have one oauth controller action that handles all callbacks, but that's only possible because I only use it for simple logins:
#[Get('/auth/{type}')]
public function auth(string $type, Request $request): Response
{
if ($response = $this->autoLogin()) {
return $response;
}
$oauth = $this->container->get(OAuthClient::class, tag: $type);
$code = $request->get('code');
if ($code === null) {
$this->session->set('back', $request->get('back'));
return $oauth->createRedirect();
}
$oauth->authenticate($request, function (OAuthUser $oauthUser): Authenticatable {
$user = User::select()
->where('email = ?', $oauthUser->email)
->first();
if (! $user) {
$user = User::create(
email: $oauthUser->email,
name: $oauthUser->name ?? $oauthUser->nickname,
role: Role::USER,
);
} else {
$user->name = $oauthUser->name ?? $oauthUser->nickname;
$user->save();
}
return $user;
});
$back = $this->session->consume('back', '/');
return new Redirect($back);
}
Maybe having one such controller is enough? OTOH, I do see value in having one per oauth provider as well. WDYT?
By the way, apart from the question about controllers, I think this is a very solid PR and I'm happy to merge it once we settled on an answer 👍
I think it's fair to keep a
// todoin the generated controller, where people should fill in their own logic. Personally, I have one oauth controller action that handles all callbacks, but that's only possible because I only use it for simple logins:
That works for me. I'll add a // TODO comment in the handler and comment out the current implementation in the stub file, so users have a reference to start from.
Maybe having one such controller is enough? OTOH, I do see value in having one per oauth provider as well. WDYT?
I initially considered combining multiple providers into one controller, but switched to the current approach (one controller per provider) because that's how it was described in #1582.
This approach also makes the OAuth installer easier to maintain since the stub file remains straightforward and doesn't require the installer to generate PHP code dynamically (which would be necessary for a multi-provider controller).
True. Let's keep it as is then. Ping me when this is ready for review :)
@brendt should be ready now.
Sorry for not getting back to this earlier. I got distracted 🫣
Awesome PR and I'm so happy that you tackled this! Appreciate it!