4
votes

Currently I have a login, register, update and delete functionality using my api made in Laravel using passport feature. Everything works fine the insertion of data and fetching the data from the database using this api. Now I wonder, how can I customize the response of the api when the token is expired. The expiration of token is working fine too. It automatically show this message

{ "message": "Unauthenticated" }

This is the code of routes where it is protected by my Oauth token where if the user did not login first then the user is not authenticated to browse the routes

 Route::middleware('auth:api')->get('/user', function (Request $request){return $request->user();});



Route::post('/timekeeping','Auth\Api\AuthController@timekeeping');

Route::post('/login','Auth\Api\AuthController@login');

 Route::middleware('auth:api')->group(function () {Route::post('/timekeeping_app','Auth\Api\AuthController@timekeeping_app');

Route::post('/logout','Auth\Api\AuthController@logout');

Route::post('/register','Auth\Api\AuthController@register');

Route::post('/show_dtr_list','Auth\Api\AuthController@show_dtr_list');

Route::post('/update','Auth\Api\AuthController@update');

Route::post('/delete','Auth\Api\AuthController@delete');

 });

Then this is how I response whenever the user successfully logged in, registered, or even logged out their accounts.

return response(['status'=>'oK','message'=>'Successful!']);

What I want is when everytime the user is using the expired token. The api should response something like this

{ "message": "Token is expired" }

not just

{ "message": "Unathenticated" }

Some threads discussed that I need to overwrite some functionalities of laravel but I don't know where and how am I going to start.

5
any updates on this situation?abr

5 Answers

5
votes

Here's how I solved it. If you are using Laravel 5.5 or above you can override the default exception handler by editing app/Exceptions/Handler.php to add the following:

use Illuminate\Auth\AuthenticationException;

protected function unauthenticated($request, AuthenticationException $exception)
{
    if ($request->expectsJson()) {
        $json = [
            'isAuth'=>false,
            'message' => $exception->getMessage()
        ];
        return response()
            ->json($json, 401);
    }
    $guard = array_get($exception->guards(),0);
    switch ($guard) {
        default:
            $login = 'login';
            break;
    }
    return redirect()->guest(route($login));
}

In the JSON return, you can add any parameters per your requirement.

2
votes

This solution worked for me, found in the Laravel Docs. You can override the unauthenticated function in the Handler like this:

protected function unauthenticated($request, AuthenticationException $exception)
{
    return $request->expectsJson()
                ? response()->json(['message' => $exception->getMessage()], 401)
                : redirect()->guest(route('login'));
}

then, handle and provide the response you want.

Don't forget to import this as well in the Handle.php file:

use Illuminate\Auth\AuthenticationException;

I hope it does work well for you!

1
votes

Add following at top of Handler.php file:

use Illuminate\Auth\AuthenticationException;

And just add following function:

protected function unauthenticated($request, AuthenticationException $exception)
{
   if ($request->expectsJson()){
       return response()->json(['message' => "Token is expired"], 401);
   }

   return parent::render($request, $exception); // TODO: Change theautogenerated stub
}
0
votes

Override auth:api middleware, and modify it accordingly to give the response you want.

0
votes

1- create new middleware UserAccessible

 <?php

namespace App\Http\Middleware;

use Closure;
use Illuminate\Support\Facades\Auth;

class UserAccessible
{

    /**
     * Handle an incoming request.
     *
     * @param  \Illuminate\Http\Request  $request
     * @param  \Closure  $next
     * @return mixed
     */
    public function handle($request, Closure $next)
    {

        $isAuth = Auth::guard('api')->check();

        if(!$isAuth){
            // redirect page or error.

            $code = 401;

            $output = ['code' => $code,
                'status' => false,
                'msg' => 'Unauthenticated',
                'data' => []];

            return response()->json($output, $code);
        }

        return $next($request);
    }
}

2- Define middleware in Kernal.php

protected $routeMiddleware = [
    'user_accessible' => \App\Http\Middleware\UserAccessible::class,
];

}

3- In Controller

class XController extends Controller
{

    /**
     * Create a new controller instance.
     *
     * @return void
     */
    public function __construct()
    {
        $this->middleware('user_accessible');
    }

Or in routes

Route::middleware('user_accessible')->get('/user', function (Request $request) {
    return $request->user();
});