role; $codes = $role->codes; if (!$role->valid) { throw new CatchException("角色‘{$role->name}’已被禁用,如有疑问,请联系管理员", 403); } // 超级管理员可以做任何事 if (in_array(Role::CODE_SUPER_ADMIN, $codes)) { return $next($request); } // 获取权限注解 $controller = $request->controller(); $controllerNameSpace = 'app\\admin\\controller\\' . $controller; $ref = new \ReflectionClass($controllerNameSpace); $attrs = $ref->getAttributes(Permission::class); $methodName = $request->action(); $method = $ref->getMethod($methodName); $methodAttrs = $method->getAttributes(Permission::class); // 如果有具体的方法权限 if ($methodAttrs) { foreach ($methodAttrs as $attrRaw) { /** * @var Permission */ $attr = $attrRaw->newInstance(); // 忽略权限要求 if ($attr->ignore) { return $next($request); } /* * 权限值设置 */ $permission = $attr->value; // 继承权限 if ($attr->inherit) { if (count($attrs) > 1) { throw new \InvalidArgumentException('使用了继承权限值,但是controller的权限Attribute不止一个'); } $controllerAttr = $attrs[0]->newInstance(); $controllerPermission = $controllerAttr->value; // 是否使用控制器名 // 尽管在方法上没有权限Attr的话,不会进入foreach循环中,但是还是有可能传一个空的permission进来 if (!$permission) { if ($controllerAttr->useMethodName) { $permission = "$controllerPermission.$methodName"; } else { $permission = $controllerPermission; } } } else { // 不继承权限,直接使用$permission, 但是检查权限值是否为空 if (!$permission) { if (count($attrs) > 1) { throw new \InvalidArgumentException('没有使用继承,而且权限值为空,尝试使用controller权限值规则,但是controller的权限Attribute不止一个'); } $controllerAttr = $attrs[0]->newInstance(); $controllerPermission = $controllerAttr->value; // 使用控制器attr规则 // 使用方法名 if ($controllerAttr->useMethodName) { $permission = $methodName; } else { // 使用控制器名 $permission = strtolower($controller); } } // 直接使用$permission } /* * 检查权限 */ if (!in_array($permission, $codes)) { throw new CatchException("未具有权限$permission, 禁止访问", 403); } // 成功 return $next($request); } } // 只有控制器权限 /** * @var \ReflectionAttribute $attrRaw */ foreach ($attrs as $attrRaw) { /** * @var Permission */ $attr = $attrRaw->newInstance(); $permission = $attr->value; // 自动使用方法名作为权限值 if ($attr->useMethodName) { $permission = "$permission.$methodName"; } elseif (!$permission) { // 没有标注要什么权限而且useMethodName设为了false,使用controller的小写作为权限值 $permission = strtolower($controller); } if (!in_array($permission, $codes)) { throw new CatchException("未具有权限$permission, 禁止访问", 403); } } return $next($request); } }