Back

[Laravel 5] Passing parameters to middleware handlers


I would like to pass arbitrary data to the middleware annotation like

/**
 * @Middleware("permissions", requires_permission="comment")
 */

and have this received by the permissions middleware. Is there any way I can do this, or otherwise get data to the middleware from the controller action?

Robindfuller replied 4 years ago

I second this. I really need it!

landjea replied 4 years ago

Based on the API and the available sources of information on Laravel 5's implementation of Middleware (at the current moment - things are in flux with L5 right now) - I don't think you can directly pass parameters in like that.

I think you would need to set a session variable for your permission inside whatever method you are working on and then pull it out from inside your middleware.

Something like the following in you PermissionsMiddleware

public function handle($request, Closure $next)
{
    // get required permission set by controller method calling middleware
    $requiredPermission= app('session')->get('requires_permission');
    $userPermissions= app('session')->get('user_permissions');

    if ( in_array($requiredPermission, $userPermissions) ) {
        // do stuffs
    } else {
        throw new \Exception("Access Denied.");
    }

    return $next($request);
}

Of course, this is quick code to show the idea, might have missing braces / etc...

landjea replied 4 years ago

I asked your question on another website specifically about L5 middleware and they confirm what I mentioned and suggest using config files for permissions based on route names.

http://www.codeheaps.com/php-programming/laravel-5-middleware-stack-decoded/

Look in the comments on that link for the answer provided there.

usm4n replied 4 years ago

Hi, I am not sure if my solution at codeheaps is the best one. Maybe someone else could come up with a better one, or, we just wait for the final release.

Best Regards!

ollieread replied 4 years ago

I'm actually currently looking into this.

My particular need was for certain route groups to only be available to certain roles, but also if I wanted I could use the same method for limiting based on permission.

I essentially created two pieces of middleware, is and has. Both are duplicates of IsGuest with different handle methods. This is the one for is:

public function handle($request, Closure $next)
{
    $user = $this->auth->user;
    $route = $request->route();
        
    if($user && $route) {
        $actions = $route->getAction();
            
        if(array_key_exists('role', $actions)) {
            $role = $actions['role'];
                
            if(!$user->is($role)) {
                return new RedirectResponse(url('/'));
            }
        }
    }

    return $next($request);
}

Then I just define my route in my routing service provider like so:

$router->get('/admin', [
    'as' => 'admin.dashboard', 
    'uses' => '[email protected]', 
    'middleware' => ['authenticated', 'is'], 
    'role' => 'admin'
]);

In my user system I have simple is() and has() methods on the user model that allows me to do this (using whereHas).

To summarise, if I want to limit access to route or to a route group by role, I can add the 'is' middleware and then add a parameter to the definition called 'role' which states the role. Likewise, if I want to limit by permission, I use the 'has' middleware and add 'permissions' to the definition (which works with an array).

Hope that helps.

cgrossde replied 4 years ago

I wrote a permission module for Laravel 5 called Laraguard. You can define permissions in a YAML file and protect controllers and/or methods:

controllerActionPermissions:
  admin:
    - "*@*"
  guest:
    - "[email protected]"
  user:
    - "[email protected]"
    - "[email protected]"
  manager:
    - "[email protected]*"

To protect your controller all you need to do is call Laraguard in the constructor:

public function __construct()
    {
        $this->middleware('laraguard');
    }
Ehesp replied 4 years ago

Doesn't help if this is managed through a database :(

cgrossde replied 4 years ago

Actually the permissions of each user are stored in the database. (Also roles if you want to implement that too)


Sign in to participate in this thread!



We'd like to thank these amazing companies for supporting us