Been trying to incorporate an external authentication with Laravel's authentication and I don't seem to make it work
Read and tried this article I've found here in stackoverflow, Custom user authentication base on the response of an API call, based on this article I've successfully put the externally authenticated user info to Laravel's Auth System.
My problem is when I do login and use that credential to login to the external API(assuming we fetch successfully the user info from the API) and redirect to another page, Auth::user()
don't seem to work and always return null
value, it looks like the session is not persisting...
I have also tried creating custom session to put the return data from the API inside the ApiUserProvider to access it later in other routes, but the session becomes missing....
I hope some could help me, Thank you
PS: I'm using Laravel 5.4
config/auth.php
'providers' => [
'users' => [
'driver' => 'api',
],
],
app/Providers/AuthServiceProvider
namespace App\Providers;
use Illuminate\Support\Facades\Auth;
use Illuminate\Foundation\Support\Providers\AuthServiceProvider as ServiceProvider;
class AuthServiceProvider extends ServiceProvider
{
protected $policies = [
'App\Model' => 'App\Policies\ModelPolicy',
];
public function boot()
{
$this->registerPolicies();
Auth::provider('api', function ($app, array $config) {
return new \App\Providers\ApiUserProvider($this->app['hash']);
});
}
}
app/Providers/ApiUserProvider.php
namespace App\Providers;
use Illuminate\Support\Facades\Auth;
use Illuminate\Contracts\Auth\UserProvider;
use Illuminate\Contracts\Hashing\Hasher as HasherContract;
use Illuminate\Contracts\Auth\Authenticatable as UserContract;
class ApiUserProvider implements UserProvider
{
protected $hasher;
public function __construct(HasherContract $hasher)
{
$this->hasher = $hasher;
}
public function retrieveByCredentials(array $credentials)
{
$user = [];
$post = [
'username' => $credentials['username'],
'password' => $credentials['password']
];
$ch = curl_init();
curl_setopt($ch, CURLOPT_FOLLOWLOCATION, true);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
curl_setopt($ch, CURLOPT_URL, 'https://sample.com/dev/admin/login');
curl_setopt($ch, CURLOPT_POST, 1);
curl_setopt($ch, CURLOPT_POSTFIELDS, json_encode($post));
curl_setopt($ch, CURLOPT_HTTPHEADER, array('Content-Type:application/json'));
$response = curl_exec($ch);
$response = json_decode($response, true);
curl_close($ch);
if(isset($response['successful']) && $response['successful']) {
$response['claims'] = json_decode(base64_decode(explode('.', $response['token'])[1]));
$response['password'] = bcrypt($credentials['password']);
$response['username'] = $credentials['username'];
$response['id'] = $response['claims']->client_id;
$response['remember_token'] = null;
$user = $response;
session()->put($response['claims']->client_id, $response); //<--- I attempt to put it in session
}
$user = $user ? : null;
return $this->getApiUser($user);
}
public function retrieveById($identifier)
{
//$user = $this->getUserById($identifier);
$user = session()->get($identifier); //<---- attempted to retrieve the user, but session don't exists if I go in other route
return $this->getApiUser($user);
}
public function validateCredentials(UserContract $user, array $credentials)
{
return $this->hasher->check(
$credentials['password'], $user->getAuthPassword()
);
}
protected function getApiUser($user)
{
if ($user !== null) {
return new \App\ApiUser((array) $user);
}
}
protected function getUserById($id)
{
$user = session()->get($id);
return $user ?: null;
}
public function retrieveByToken($identifier, $token) { }
public function updateRememberToken(UserContract $user, $token) { }
}
UserController.php
namespace App\Http\Controllers;
use Illuminate\Support\Facades\Auth;
use Illuminate\Http\Request;
use Illuminate\Contracts\Auth\SessionGuard;
class UserController extends Controller
{
protected function attemptLogin(Request $request)
{
return $this->guard()->attempt($this->credentials($request));
}
protected function guard()
{
return Auth::guard();
}
protected function credentials(Request $request)
{
return $request->only('username', 'password');
}
public function login(Request $request)
{
if ($this->attemptLogin($request)) {
dd(auth());
return "T";
}
return "F";
}
public function getCurrentUserInfo(Request $request)
{
dd(auth()); //<------------- user info no longer exist here
}
}