【问题标题】:Laravel Redirection doesn't workLaravel 重定向不起作用
【发布时间】:2015-12-31 00:29:22
【问题描述】:

我正在使用 Laravel 5.1。我的控制器专门用于管理员用户。所以我检查用户是否是管理员。这是我的代码。

public function getAdminData()
  {
    $this->checkAdminStatus();
    return response()->json(array('admin-data'));
  }
public function checkAdminStatus()
  {
    $userManager = new UserManager();
    if(!$userManager->isAdmin())
    {
        return redirect()->route('returnForbiddenAccess');
    }
  }

我的路线是

Route::any('api/app/forbidden',['uses' =>'ErrorController@returnNonAdminErrorStatus','as'=>'returnForbiddenAccess']);

现在如果用户不是管理员,那么它不应该返回 admin-data 但它会返回。 redirect()->route 调用后不应该停止处理逻辑吗? 这也是纯粹的 REST 应用程序。

【问题讨论】:

  • 如果控制器仅供管理员使用,为什么还要检查某人是否是控制器中的管理员?使用将为您进行检查的中间件,如果有人经过身份验证和授权 - 让他们通过控制器。否则将它们发送到授权页面。这个逻辑不是在控制器中完成的,而是在中间件中完成的,就像 Jiedara 的回答一样。

标签: php laravel-5 laravel-routing


【解决方案1】:

您为什么不使用 Laravel 中间件解决方案来满足您的需求?您可以将中间件链接到您的控制器,检查当前用户是否是管理员,如果不是则重定向:

//You Middleware Handle method
public function handle($request, Closure $next)
{
  if ($this->auth->guest() || !($this->auth->user()->isAdmin))
  {
        return redirect('your/url')->with('error','no admin');;
  }
return $next($request);
}

您可以在其构造方法中为控制器添加一个或多个中间件

//your controller
public function __construct(Guard $auth, Request $request){
    $this->middleware('auth', ['except' => ['index', 'show']]); //here one 'auth' middleware
    $this->middleware('admin', ['only' => ['index', 'show', 'create','store']]); //here the admin middleware
}

注意 onlyexcept 参数允许或禁止某些控制器方法的中间件

查看中间件上的laravel documentation 了解更多信息:)

【讨论】:

  • 嗯,这似乎是正确的做法,你能告诉我如何向控制器添加多个中间件吗?
【解决方案2】:

不,你的逻辑有点缺陷。您从checkAdminStatus() 发回的返回值只是被忽略并丢弃:

public function getAdminData()
{
    // You don't have $redirectValue in your code, but imagine it 
    // is there. To actually redirect, you need to return this value
    // from your controller method
    $redirectValue = $this->checkAdminStatus();

没有对该重定向进行任何操作。 只有次从你的控制器返回的东西发生在每一个请求上。我会建议更像这样的东西:

public function getAdminData(UserManager $userManager)
{
    if($userManager->isAdmin()) {
        return response()->json(array('admin-data'));
    }

    return redirect()->route('forbidden-access');
}

我认为这抓住了您的问题的精神:这里返回的唯一时间是 如果用户是管理员


顺便说一句,您在一种情况下返回 JSON 数据,在另一种情况下返回 redirect。这可能不是一个好主意。我的理由是,通常情况下,JSON 数据是为了响应 AJAX 请求而返回的,根据我的经验,在失败的情况下很少会跟进 actual 重定向。 (YMMV)

【讨论】:

  • 其实我以前只是这样做的。但随后我将在整个控制器中再次重写相同的代码,并且我试图应用 DRY 原则。如果我将中间件注入其中会怎样,因为这对于整个控制器来说很常见?
  • 是的,如果要反复使用此代码,将其放在中间件中是有意义的。在这种情况下,我会否定 if 语句(if(!$manager->isAdmin())),然后在这种情况下只返回重定向。在您的控制器中,您只需返回管理数据 JSON。
  • 嗯是的,你能告诉我是否可以向我的控制器添加更多的中间件,如果可以,那么如何?
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2014-03-05
  • 2012-09-13
  • 1970-01-01
  • 2023-04-08
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多