web-dev-qa-db-ja.com

Laravel複数の役割を持つミドルウェア

Laravelのミドルウェアでいくつかの問題に遭遇しました。私が達成しようとしていることの基本的な考え方を教えてください:

サイトに登録されているユーザーには、次の4つのロールのいずれかがあります。

  1. 学生(デフォルト):「index」および「show」ビューにアクセスできます
  2. 承認者:以前のアクセスに加えて、「概要」、「更新
  3. エディター:以前のバージョンに加えて、「create」、「edit」、「store」にアクセスできます
  4. 管理者:アクセス可能すべて

fyi:「概要」は一種のインデックスビューですが、承認者以上の役割のみを対象としています

これを行うための最善の方法は何ですか?これは私がこれまでにやったことですが、うまくいかないようです:


Kernel.php

protected $middlewareGroups = [
...
    'approver+' => [
        \App\Http\Middleware\Approver::class,
        \App\Http\Middleware\Editor::class,
        \App\Http\Middleware\Admin::class,
    ],
];

protected $routeMiddleware = [
...
    'student' => \App\Http\Middleware\Student::class,
    'approver' => \App\Http\Middleware\Approver::class,
    'editor' => \App\Http\Middleware\Editor::class,
    'admin' => \App\Http\Middleware\Admin::class,
];

Http\Middleware\Admin.php

public function handle($request, Closure $next)
{
   if (Auth::check())
   {

        if(Auth::user()->isAdmin())
        {
            return $next($request);
        }
   }

    return redirect('login');
}

「ユーザー」雄弁モデル:

public function isAdmin()
{
    if($this->role_id === 4)
    { 
        return true; 
    } 
    else 
    { 
        return false; 
    }
}

ApproverおよびEditorミドルウェアファイル、およびUserモデルのisApproverおよびisEditor関数でまったく同じことを行い、ifステートメントでチェックされた値のみをそれぞれ2および3に編集しました。

最後に、routes\webファイルで行ったことを示します。

Route::get('scholen', 'SchoolsController@index');
Route::get('admin/scholen/overzicht', 'SchoolsController@overview')->middleware('approver+');
Route::get('admin/scholen/maken', 'SchoolsController@create')->middleware('approver+');
Route::post('scholen', 'SchoolsController@store')->middleware('approver+');
Route::get('scholen/{id}', 'SchoolsController@show');
Route::get('admin/scholen/{id}/bewerken', 'SchoolsController@edit')->middleware('admin');
Route::patch('admin/scholen/{id}', 'SchoolsController@update')->middleware('admin');
Route::delete('admin/scholen/{id}', 'SchoolsController@destroy')->middleware('admin');

まだすべてが正確ではありませんが、承認者権限を持つユーザーとしてログインして学校の概要にアクセスしようとすると、ホームページにリダイレクトされてしまうため、行き詰まりました。

一般的に、私はあまりにも無秩序に働いており、まったく正しくないように感じていますが、誰かがそれをより効率的に行う方法についてアドバイスしてもらえますか?

事前にどうもありがとうございました!

10
Jesse

役割ごとに個別のミドルウェアを用意しないでください。それは非常に速く非常に乱雑になります。渡された任意のロールに対してチェックできる単一のロールチェックミドルウェアを用意することをお勧めします。

Http\Kernel.php

protected $routeMiddleware = [
    ...
    'role' => \App\Http\Middleware\Role::class,
];

Http\Middleware\Role.php

public function handle($request, Closure $next, ... $roles)
{
    if (!Auth::check()) // I included this check because you have it, but it really should be part of your 'auth' middleware, most likely added as part of a route group.
        return redirect('login');

    $user = Auth::user();

    if($user->isAdmin())
        return $next($request);

    foreach($roles as $role) {
        // Check if user has the role This check will depend on how your roles are set up
        if($user->hasRole($role))
            return $next($request);
    }

    return redirect('login');
}

最後に、Webルートで

Route::get('admin/scholen/overzicht', 'SchoolsController@overview')->middleware('role:editor,approver');
Route::get('admin/scholen/{id}/bewerken', 'SchoolsController@edit')->middleware('role:admin');
22
jfadich