Created
August 29, 2019 23:57
-
-
Save acidjazz/40d9967ffa6316f77a41fe9774d67102 to your computer and use it in GitHub Desktop.
Auth Example using acidjazz/humble and laravel socialite
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<?php | |
namespace App\Http\Controllers; | |
use App\Models\User; | |
use App\Models\Provider; | |
use App\Models\Activity; | |
use acidjazz\Humble\Models\Session; | |
use Illuminate\Http\Request; | |
use App\Notifications\LoginAttempt; | |
use Socialite; | |
class AuthController extends Controller | |
{ | |
private $appends = [ 'location', 'hearts' ]; | |
/** | |
* Supply the appropiate callback URL | |
* | |
* @return String | |
*/ | |
public function redirect(Request $request, $provider) | |
{ | |
if (!in_array($provider, Provider::$allowed)) { | |
return $this->error('auth.provider.allowed', 'Auth Provider is not allowed'); | |
} | |
return Socialite::driver($provider)->redirect(); | |
} | |
/** | |
* Process and verify an idToken from a sign-in | |
* | |
* @param String | |
* @return Illuminate\Http\Response | |
*/ | |
public function verifyIdToken(String $token) | |
{ | |
$client = new \Google_Client(['client_id' => config('services.google.client_id')]); | |
$payload = $client->verifyIdToken($token, 'google'); | |
if (!isset($payload['sub'])) { | |
return $this->error('auth.invalid_token'); | |
} | |
if (!$user = $this->_oaUser((object) $payload, 'google')) { | |
$this->error('auth.user_save', 'Error saving user'); | |
} | |
auth()->login($user, 'google'); | |
return $this | |
->render(auth()->user()->append($this->appends)->makeHidden('heart')) | |
->cookie('token', auth()->token(), 0, '', config('app.domain')); | |
} | |
private function _oaUser($oaUser, $type, $state=false) { | |
$user = User::where('email', $oaUser->email)->first(); | |
if ($user == null) { | |
$user = new User([ | |
'name' => $oaUser->name, | |
'email' => $oaUser->email, | |
'avatar' => $oaUser->picture ?? $oaUser->avatar_original ?? $oaUser->avatar, | |
'is_admin' => in_array($oaUser->email, User::$whitelist), | |
]); | |
if (!$user->save()) { | |
return $this->error('auth.user_save', 'Error saving user'); | |
} | |
Activity::log('register', $user, $user); | |
} | |
if ($user == null || !in_array($type, $user->providers->pluck('type')->toArray())) { | |
$provider = new Provider([ | |
'user_id' => $user->id, | |
'type' => $type, | |
'avatar' => $oaUser->avatar_original ?? $oaUser->avatar ?? $oaUser->picture, | |
'payload' => $state != false ? $state : (array) $oaUser, | |
]); | |
if (!$provider->save()) { | |
return false; | |
} | |
if ($user->avatar == null) { | |
$user->avatar = $provider->avatar; | |
$user->save(); | |
} | |
} | |
return $user; | |
} | |
/** | |
* Process and result the oAUth providers callback | |
* | |
* @param Illuminate\Http\Request | |
* @param String | |
* @return Illuminate\Http\Response | |
*/ | |
public function callback(Request $request, String $type) | |
{ | |
if (!in_array($type, Provider::$allowed)) { | |
return $this->error('auth.provider.allowed', 'Auth Provider is not allowed'); | |
} | |
$oaUser = Socialite::driver($type)->stateless()->user(); | |
if (!$user = $this->_oaUser($oaUser, $type, $request->state)) { | |
$this->error('auth.user_save', 'Error saving user'); | |
} | |
auth()->login($user, $type); | |
$user = auth()->user(); | |
return response( | |
view('complete', [ | |
'json' => json_encode([ | |
'provider' => $type, | |
'token' => auth()->token(), | |
'user' => auth()->user()->append($this->appends)->makeHidden('heart'), | |
'to' => auth()->session()->to, | |
]) | |
]))->cookie('token', auth()->token(), 0, '', config('app.domain')); | |
} | |
/** | |
* Passwordless login attempt | |
* | |
* @param Illuminate\Http\Request | |
* @return Illuminate\Http\Response | |
*/ | |
public function attempt(Request $request) | |
{ | |
$this->option('email', 'required|email'); | |
$this->option('to', 'string'); | |
$this->verify(); | |
if (!$user = User::where('email', $request->email)->first()) { | |
$user = new User([ | |
'email' => $request->email, | |
'name' => explode('@', $request->email)[0], | |
'is_admin' => in_array($request->email, User::$whitelist), | |
]); | |
$user->save(); | |
Activity::log('register', $user, $user); | |
} | |
$attempt = auth()->attempt($user); | |
$user->notify(new LoginAttempt($attempt)); | |
return $this->render(['cookie' => $attempt->cookie]); | |
} | |
/** | |
* Process a link from an Login e-mail | |
* | |
* @param Illuminate\Http\Request | |
* @return Illuminate\Http|Response | |
*/ | |
public function login(Request $request) | |
{ | |
$this->option('token', 'required|alpha_num|size:64'); | |
$this->option('cookie', 'required|alpha_num|size:64'); | |
if (!$this->verify()) { | |
return $this->error(); | |
} | |
if (auth()->user() != null) { | |
return $this->error('auth.already'); | |
} | |
if (!$login = auth()->verify($request->token, $request->cookie)) { | |
return $this->error('auth.invalid'); | |
} | |
return $this->render([ | |
'token' => auth()->token(), | |
'user' => auth()->user()->append($this->appends)->makeHidden('heart'), | |
'to' => auth()->session()->to, | |
])->cookie('token', auth()->token(), 0, '', config('app.domain')); | |
} | |
/** | |
* Provide current login information | |
* | |
* @param Illuminate\Http\Request | |
* @return Illuminate\Http\Response | |
*/ | |
public function me(Request $request) | |
{ | |
auth()->user()->session->touch(); | |
return $this->render(auth()->user()->append($this->appends)->makeHidden('heart')); | |
} | |
/** | |
* Provide a way to update an active section | |
* | |
* @param Illuminate\Http\Request | |
* @return Illuminate\Http\Response | |
*/ | |
public function active(Request $request) | |
{ | |
$this->option('path', 'string|nullable')->verify(); | |
auth()->user()->session->active($request->path); | |
return $this->render(auth()->user()->append($this->appends)->makeHidden('heart')); | |
} | |
/** | |
* Log out of the current session | |
* | |
* @param Illuminate\Http\Request | |
* @return Illuminate\Http\Response | |
*/ | |
public function logout(Request $request) | |
{ | |
return $this->render(auth()->logout())->cookie('token', false, 0, '', config('app.domain')); | |
} | |
/** | |
* Log In as a specified user | |
* | |
* @param Illuminate\Http\Request | |
* @return Illuminate\Http\Response | |
*/ | |
public function loginAs(Request $request, User $user) | |
{ | |
auth()->login($user); | |
return $this | |
->render([ | |
'token' => auth()->token(), | |
'user' => auth()->user(), | |
'success' => true, | |
'message' => __('auth.success'), | |
])->cookie('token',auth()->token(), 0, '', config('app.domain')); | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment