50
59

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 5 years have passed since last update.

Laravelのログイン処理にemailやpassword以外の条件を加える方法

Last updated at Posted at 2015-11-17

前回の記事に引き続きLaravel5にデフォルトで用意されているログイン処理についてメモっておきます。

デフォルトではemailとpasswordの情報で認証してくれるわけだけど、
例えば論理削除用のフラグも条件に加えたいなんて事があるんじゃないでしょうか。
###ログイン処理を追ってみる
まずはpostLoginアクションを覗いてみましょう。

app/Http/Controllers/Auth/AuthController.php にはpostLoginが実装されていませんが、
AuthenticatesAndRegistersUsersトレイトをuseしています。

このトレイトを見てみると、更に別のトレイトをuseしています。

vendor/laravel/framework/src/Illuminate/Foundation/Auth/AuthenticatesAndRegistersUsers.php
<?php

namespace Illuminate\Foundation\Auth;

trait AuthenticatesAndRegistersUsers
{
    use AuthenticatesUsers, RegistersUsers {
        AuthenticatesUsers::redirectPath insteadof RegistersUsers;
    }
}

そしてAuthenticatesUsersトレイトを覗いてみるとpostLoginアクションが実装されています。

vendor/laravel/framework/src/Illuminate/Foundation/Auth/AuthenticatesUsers.php
    /**
     * Handle a login request to the application.
     *
     * @param  \Illuminate\Http\Request  $request
     * @return \Illuminate\Http\Response
     */
    public function postLogin(Request $request)
    {
        $this->validate($request, [
            $this->loginUsername() => 'required', 'password' => 'required',
        ]);

        // If the class is using the ThrottlesLogins trait, we can automatically throttle
        // the login attempts for this application. We'll key this by the username and
        // the IP address of the client making these requests into this application.
        $throttles = $this->isUsingThrottlesLoginsTrait();

        if ($throttles && $this->hasTooManyLoginAttempts($request)) {
            return $this->sendLockoutResponse($request);
        }

        $credentials = $this->getCredentials($request);

        if (Auth::attempt($credentials, $request->has('remember'))) {
            return $this->handleUserWasAuthenticated($request, $throttles);
        }

        // If the login attempt was unsuccessful we will increment the number of attempts
        // to login and redirect the user back to the login form. Of course, when this
        // user surpasses their maximum number of attempts they will get locked out.
        if ($throttles) {
            $this->incrementLoginAttempts($request);
        }

        return redirect($this->loginPath())
            ->withInput($request->only($this->loginUsername(), 'remember'))
            ->withErrors([
                $this->loginUsername() => $this->getFailedLoginMessage(),
            ]);
    }

どうやら$credentials変数に認証するためのwhere区情報が配列で入っているようです。
$this->getCredentials($request)では$requestからemailとpasswordだけに絞って返却していました。
ということはgetCredentialsメソッドの挙動を変えることが出来れば良さそうです。
###認証に必要な条件を加える

app/Http/Controllers/Auth/AuthController.php

    use AuthenticatesAndRegistersUsers { getCredentials as _getCredentials; }

    /**
     * Get the needed authorization credentials from the request.
     *
     * @param  \Illuminate\Http\Request  $request
     * @return array
     */
    protected function getCredentials(Request $request)
    {
        $credentials = $this->_getCredentials($request);

        return array_merge($credentials, ['active' => 1]);
    }

トレイトはクラスのようにオーバーライドすることが出来ませんので
こんなふうにuseする際getCredentialsメソッドを別名にし、改めて定義したgetCredentialsメソッド内から
呼び出すことで、これまでのgetCredentialsメソッドをラップしました。

これにてemailとpasswordが一致するだけでなく、activeカラムが1でないとログイン成功とならないように出来ますね。

めでたし。めでたし。

50
59
1

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
50
59

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?