浜松のWEBシステム開発・スマートフォンアプリ開発・RTK-GNSS関連の開発はお任せください
株式会社シーポイントラボ
TEL:053-543-9889
営業時間:9:00~18:00(月〜金)
住所:静岡県浜松市中区富塚町1933-1 佐鳴湖パークタウンサウス2F

【Laravel】APIトークンによる認証のドキュメントにない部分

 LaravelにはAPIトークンを用いてユーザを認証する仕組みが組み込まれています。拡張機能であるLaravel Passportというものもありますが、この記事では組み込みのAPI認証についてのみ述べます。
API認証 6.x Laravel
 LaravelのAPI認証の説明はあっさりしています。認証対象のユーザやら管理者やらのテーブルにapi_tokenカラムを用意し、ミドルウェアで囲って認証範囲のルーティングを指定し、リクエストでのapi_tokenの渡し方を紹介して終わりです。実装を読んでみるとドキュメントにありませんが、外部から設定されるべき値がいくつか見つかります。
 最たるものはconfigです。通常Laravelの認証設定はconfig/auth.phpに次の様に書くだけです。

    /*
    |--------------------------------------------------------------------------
    | Authentication Guards
    |--------------------------------------------------------------------------
    |
    | 次に、アプリケーションのすべての認証ガードを定義できます。
    | もちろん、ここではセッションストレージとEloquentユーザープロバイダーを使用する優れたデフォルト構成が定義されています。
    |
    | すべての認証ドライバーにはユーザープロバイダーがあります。
    | これは、ユーザーのデータを保持するためにこのアプリケーションで使用されるデータベース
    | または他のストレージメカニズムからユーザーを実際に取得する方法を定義します。
    |
    | Supported: "session", "token"
    |
    */
    'guards' => [
        'web' => [
            'driver'   => 'session',
            'provider' => 'users',
        ],
        'api'         => [
            'driver'      => 'token',
            'provider'    => 'users',
        ],
    ],

    /*
    |--------------------------------------------------------------------------
    | User Providers
    |--------------------------------------------------------------------------
    |
    | すべての認証ドライバーにはユーザープロバイダーがあります。
    | これは、ユーザーのデータを保持するためにこのアプリケーションで使用されるデータベース
    | または他のストレージメカニズムからユーザーを実際に取得する方法を定義します。
    |
    | 複数のユーザーテーブルまたはモデルがある場合は、複数を構成できます
    | 各モデル/テーブルを表すソース。 これらのソースはその後
    | 定義した追加の認証ガードに割り当てられます。
    | Supported: "database", "eloquent"
    |
    */
    'providers' => [
        'users'  => [
            'driver' => 'eloquent',
            'model'  => App\Models\Eloquents\User::class,
        ],
    ],

 APIトークンによる認証(gurads.driver === ‘token’)の場合はさらに設定を追加できます。

    'guards' => [
        'api'         => [
            'driver'      => 'token',
            'provider'    => 'users',
            'input_key'   => 'authToken', // リクエストのキー指定
            'storage_key' => 'auth_token', // カラム名指定
            'hash'        => true, // トークンをハッシュ化して保存するか否か.これはドキュメントにある
        ],
    ],

 これは\Illuminate\Auth\AuthManager::createTokenDriverにあります。次の様に設定があるならばそれを、なければapi_token等デフォルト値を選ぶようになっています。

    /**
     * Create a token based authentication guard.
     *
     * @param  string  $name
     * @param  array  $config
     * @return \Illuminate\Auth\TokenGuard
     */
    public function createTokenDriver($name, $config)
    {
        // The token guard implements a basic API token based guard implementation
        // that takes an API token field from the request and matches it to the
        // user in the database or another persistence layer where users are.
        $guard = new TokenGuard(
            $this->createUserProvider($config['provider'] ?? null),
            $this->app['request'],
            $config['input_key'] ?? 'api_token',
            $config['storage_key'] ?? 'api_token',
            $config['hash'] ?? false
        );

        $this->app->refresh('request', $guard, 'setRequest');

        return $guard;
    }

 また、ここからトークン認証定義クラスTokenGuardを追って\Illuminate\Auth\TokenGuard::getTokenForRequestまで行くとドキュメントにないキーであるリクエストヘッダのPHP_AUTH_PWにトークンを渡すことでも認証を動かせることが分かります。

// vendor/laravel/framework/src/Illuminate/Auth/TokenGuard.php
    /**
     * Get the token for the current request.
     *
     * @return string
     */
    public function getTokenForRequest()
    {
        $token = $this->request->query($this->inputKey);

        if (empty($token)) {
            $token = $this->request->input($this->inputKey);
        }

        if (empty($token)) {
            $token = $this->request->bearerToken();
        }

        if (empty($token)) {
    // これがドキュメントにないやり方
            $token = $this->request->getPassword();
        }

        return $token;
    }
// vendor/symfony/http-foundation/Request.php
    /**
     * Returns the password.
     *
     * @return string|null
     */
    public function getPassword()
    {
        return $this->headers->get('PHP_AUTH_PW');
    }
  • この記事いいね! (2)