3
votes

tried to implement a simple user register/login function on my site using the laravel default controllers (auth/password), but as soon as I login, the class RedirectIfAuthenticated handle function prevents all access to auth url's, thus I cannot logout anymore. Is there a bug and I need to write an exception on the handle function or have I missed something? Here is how the class looks like by default:

class RedirectIfAuthenticated
{
    /**
     * Handle an incoming request.
     *
     * @param  \Illuminate\Http\Request  $request
     * @param  \Closure  $next
     * @param  string|null  $guard
     * @return mixed
     */
    public function handle($request, Closure $next, $guard = null)
    {
        //dd($next($request));
        if (Auth::guard($guard)->check()) {
            return redirect('/articles');
        }

        return $next($request);
    }
}
2

2 Answers

5
votes

The AuthController's constructor should look similar to this:

public function __construct()
{
    $this->middleware('guest', ['except' => 'logout']);
}

The guest middleware is handled by the RedirectIfAuthenticated class and, in order to have the logout functionality working, you should choose one:

  • call the logout method from your AuthController.
  • call whichever method you use for logout and exclude it in AuthController's constructor:

    public function __construct()
    {
        $this->middleware('guest', ['except' => '<whichever_method>']);
    }
    
0
votes

For potentially more-advanced reasons and needs, I will show a different idea.

Inside any middleware, a person could implement their own except list. Here is a reference:

<?php

namespace App\Http\Middleware;

use Closure;

class CustomThing
    protected $except = [
        'api/logout',
        'api/refresh',
    ];

    public function handle($request, Closure $next)
    {
        foreach ($this->except as $excluded_route) {
            if ($request->path() === $excluded_route) {
                \Log::debug("Skipping $excluded_route in this middleware...");

                return $next($request);
            }
        }

        \Log::debug('Doing middleware stuff... '. $request->url());

    }

}

I will leave it up to imagination to extend that to support other types of URLs. For example, investigate matchers such as $request->url(), $request->fullUrl(), and $request->is('admin/*').

A person could investigate the vendor code for the VerifyCsrfToken middleware and make their custom one support something like this:

    protected $except = [
        'api/logout',
        'api/refresh',
        'foo/*',
        'http://www.external.com/links',
    ];

If you want it to be a reuseable solution, make that matching algorithm a Trait and import it into any middleware you want to exclude routes from.