Laravel5.7でOauth認証を実装します。
https://readouble.com/laravel/5.7/ja/passport.html
LaravelではPassportを使うことで、非常に簡単にOAuth2サーバの実装が可能になります。
Passportはleague/oauth2-serverというライブラリ上に構築されています。
cakephpなど他のフレームワークでも利用されており、信頼性の高いライブラリです。
https://oauth2.thephpleague.com/
実装
インストール
composerでインストールします。
composer require laravel/passport
Migration
client, accessTokenを格納するテーブルを作成します。
これもコマンド打つだけです。
php artisan migrate
accessToken生成のため、キーを作成しておきます。
強固なセキュリティにするため重要です。
php artisan passport:install
Model
Userモデルへ、traitを追加します。
User.php
namespace App;
use Laravel\Passport\HasApiTokens;
use Illuminate\Notifications\Notifiable;
use Illuminate\Contracts\Auth\MustVerifyEmail;
use Illuminate\Foundation\Auth\User as Authenticatable;
class User extends Authenticatable
{
use HasApiTokens, Notifiable;
AuthServiceProvider
AuthServiceProviderへ、メソッドを追加します。
ここでAccessTokenの発行・失効を管理出来るようになります。
AuthServiceProvider.php
public function boot()
{
Passport::routes();
}
設定
設定ファイルで、認証APIリクエストの方式を変更しておきます。
driverをpassportへ変更します。
config/auth.php
'guards' => [
'web' => [
'driver' => 'session',
'provider' => 'users',
],
'api' => [
'driver' => 'passport',
'provider' => 'users',
],
],
ルーティング
APIのルーティングを行います。
routes/api.phpで定義します。
Route::middleware('auth:api')->get('/user', function (Request $request) {
return $request->user();
});
もしくはコントローラに関連するアクションが下の方法で一度に定義可能です。
Route::group(['middleware' => 'auth:api'], function () {
Route::resource('cotrollerName', 'ConditionController');
});
このとき設定されるアクションは以下が詳しいです。
https://readouble.com/laravel/5.7/ja/controllers.html#resource-controllers
ただし記載あるように不要なアクションも定義されてしまうので、実際は部分的なリソースルートとして定義が良いと思います。
接続テスト
Tokenの受け取りなど、APIのテストを行います。
Laravelに元々パッケージされている、ユーザ認証システムは実装済みの前提です。
※以下の「認証」のところまで
https://blog.shnr.net/?p=813
なおユーザーも作成済み、とします。
APIのテストには、Chrome addonのRestlet Client が便利でした。
https://chrome.google.com/webstore/detail/restlet-client-rest-api-t/aejoelaoggembcahagimdiliamlcdmfm
クライアントの登録
Oauthを実装する、クライアントを登録します。
grant typeはpasswordとします。
php artisan passport:client --password
成功すると、ID&secretが表示されるので、保管しておきます。
Password grant client created successfully.
Client ID: 2
Client Secret: xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx
Request Token
アクセストークンのリクエストを行います。
トークンの有効期間は、AuthServiceProvider で設定した内容となります。
Method: POST
URL: youredomein.com/oauth/token
Header: [Content-Type: application/json;]
body:
{
"grant_type": "password",
"client_id": 2,
"client_secret": "xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx",
"username": "my.name@mail.com",
"password": "test",
"scope": "*"
}
Result:
{
"token_type": "Bearer",
"expires_in": 1296000,
"access_token": "xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx",
"refresh_token": "xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx"
}
無事にTokenが取得できました。
このTokenはその他のAPI接続で使うので、cookieなどに保管しておきます。
なおexpires_inは、tokenが無効になるまでの秒数とのこと。
AuthServiceProviderクラスのboot()で指定できます。
Passport::tokensExpireIn(now()->addDays(15));
Passport::refreshTokensExpireIn(now()->addDays(30));
※ただし認証時に正しくチェックされないとの情報あり(未検証)
Get user information
次にユーザー情報を取得します。
ヘッダーのAuthorizationで、アクセストークンを渡します。
Method: Get
URL: youredomein.com/api/user
Header: [Accept => application/json,
Authorization => Bearer xxxxxxxxxxxxxxxxx]
Result:
{
"id": 1,
"name": "My Name",
"email": "my.name@mail.com",
"email_verified_at": null,
"created_at": "2018-00-00 00:00:00",
"updated_at": "2018-00-00 00:00:00"
}
無事、ユーザー情報が取得できました。