こんにちは!
個人開発者の南です。
今回はLaravelで、各ページのアクセスをユーザーのもつ権限によりページのアクセスを割り振る方法を紹介します。
ちなみに、今回使用するLaravelのバージョンは6系になります。
Laravelのauthでデフォルトの認証機能をセットアップする
Laravel6では、artisanコマンドのmake:authで認証を追加できなくなりました。
認証機能を追加するには、下記の手順で追加します。
Laravel uiのインストール
まずは、下記のコマンドでLaravel uiをインストールします。
1 |
composer require Laravel/ui |
ログインのUIを生成
下記コマンドでログインのUIを生成するのに必要なものをセットアップします。
1 |
php artisan ui vue --auth |
ちなみに、上記ではVueJsを使うことになっていますが、Reactなどを使いたい場合は下記のように記述することができます。
1 |
php artisan ui react --auth |
migratefileのセットアップ
最後に下記コマンドでログイン機能のデータベースを作成します。
1 |
php artisan migrate |
これで「ドメイン名.com/login」で下記のようにログイン画面が表示されます。
ユーザー権限の追加
ログイン画面が表示できたら、今度はユーザーに権限をもたせるための「role」を記述していきます。
それぞれ下記2つのファイルに追加します。
・database/migrations/create_users_table.php
・app/User.php
create_users_tableの編集
ファイルを開いて、ENUM型でユーザーの権限を追加します。
ちなみに、ENUM型は設定した文字列(今回では’member’と’admin’)以外の文字列は受け付けないという型になります。
1 2 3 |
# database/migrations/create_users_table.php $table->enum('role', ['member', 'admin'])->default('member'); |
roleの項目を追加したあとは下記のような記述になります。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 |
use Illuminate\Database\Migrations\Migration; use Illuminate\Database\Schema\Blueprint; use Illuminate\Support\Facades\Schema; class CreateUsersTable extends Migration { /** * Run the migrations. * * @return void */ public function up() { Schema::create('users', function (Blueprint $table) { $table->bigIncrements('id'); $table->string('name'); $table->string('email')->unique(); $table->enum('role', ['member', 'admin'])->default('member'); $table->timestamp('email_verified_at')->nullable(); $table->string('password'); $table->rememberToken(); $table->timestamps(); }); } /** * Reverse the migrations. * * @return void */ public function down() { Schema::dropIfExists('users'); } } |
設定ができたら、freshコマンドでデータベースを更新します。
※ちなみに、このコマンドを入力すると一度全てのテーブルが削除され、もう一度migrationが走ります。
そのため、現在稼働しているものがあれば、別の方法でテーブルの項目を追加しましょう。
1 |
php artisan migrate:fresh |
User.phpの編集
現状のままだと、「mass assignment」エラーが出るので、「app/User.php」にguardedを加えておきます。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 |
namespace App; use Illuminate\Contracts\Auth\MustVerifyEmail; use Illuminate\Foundation\Auth\User as Authenticatable; use Illuminate\Notifications\Notifiable; class User extends Authenticatable { use Notifiable; ##他の項目省略 # 追加 /** * The attributes that are gureded * @var array */ protected $guarded = [ 'role' ]; ##他の項目省略 } |
middlewareの追加
次は、ユーザーの権限を見て認証を制御する方法を追加します。
今回はユーザーの権限が「admin」だった場合、管理画面のアクセスを許可するといったことを想定した実装を行います。
artisanコマンドでmiddlewareを作成しましょう。
1 |
php artisan make:middleware Admin |
middleware artisanコマンドを実行すると、下記ディレクトリに作成したものが生成されます。
「app/Http/Middleawre/Admin.php」
デフォルトの中身を下記のように変更します。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 |
namespace App\Http\Middleware; use Closure; use Auth; class Admin { private $auth; /** * Handle an incoming request. * * @param \Illuminate\Http\Request $request * @param \Closure $next * @return mixed */ public function handle($request, Closure $next) { #ユーザーがログインしていない場合は、ログイン画面へリダイレクト if( empty( auth()->user() ) ){ return redirect()->route('login'); } //ユーザーの権限チェック if (auth()->user()->role === 'admin') { $this->auth = true; } else { $this->auth = false; } //ユーザーの権限がadminだった場合は、アクセスを許可。 if ($this->auth === true) { return $next($request); } //それ以外はログイン画面にリダイレクト return redirect()->route('login')->with('error', '権限がありません'); } } |
これでユーザーの権限を見て認証を制御する方法を追加できました。
Kernelに追加
作成したミドルウェアを使用するには、Laravelの「app/Http/Kernel.php」に追加する必要があります。
app/Http/Kernel.phpを開いて、「$routeMiddleware」の箇所に作成したmiddlewareを追加しておきましょう。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 |
/** * The application's route middleware. * * These middleware may be assigned to groups or used individually. * * @var array */ protected $routeMiddleware = [ #作成したものを追加 'admin' => \App\Http\Middleware\Admin::class, 'auth' => \App\Http\Middleware\Authenticate::class, 'auth.basic' => \Illuminate\Auth\Middleware\AuthenticateWithBasicAuth::class, 'bindings' => \Illuminate\Routing\Middleware\SubstituteBindings::class, 'cache.headers' => \Illuminate\Http\Middleware\SetCacheHeaders::class, 'can' => \Illuminate\Auth\Middleware\Authorize::class, 'guest' => \App\Http\Middleware\RedirectIfAuthenticated::class, 'password.confirm' => \Illuminate\Auth\Middleware\RequirePassword::class, 'signed' => \Illuminate\Routing\Middleware\ValidateSignature::class, 'throttle' => \Illuminate\Routing\Middleware\ThrottleRequests::class, 'verified' => \Illuminate\Auth\Middleware\EnsureEmailIsVerified::class, ]; |
動作の確認
最後に動作の確認を行います。
artisanコマンドで、コントローラーを作成し、先程追加したmiddlewareを使用します。
1 |
php artisan make:controller AdminController |
コントローラーが作成できたら、中身を下記のように記述します。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 |
namespace App\Http\Controllers; use Illuminate\Http\Request; class AdminController extends Controller { public function __construct() { # 追加したmiddlewareを追加。 $this->middleware('admin'); } public function index(){ dd('admin画面です。'); } } |
コントローラーの中身が追加できたら、web.phpに「admin」のルートを追加します。
1 |
Route::get('/admin', 'AdminController@index')->name('admin'); |
ルートの追加ができたら、roleが「member」のユーザー、「admin」のユーザーを作成してそれぞれで管理画面へのアクセスを試してみましょう。
admin権限を持ったユーザーの場合は、下記画面にアクセスできます。
これで、ユーザー権限により認証を制御することができました。
まとめ
今回は、Laravelでユーザー権限によりページのアクセスを割り振る方法を紹介しました。
ユーザー権限でアクセスの制御を行うという処理は、色んなところで使うことが多い処理だと思います。
今回の記事がお役に立てれば幸いです。