自動ログインの原理は非常に簡単です。これは主に Cookie を使用して実現されます。初回ログイン時にログインに成功し、次回から自動ログインを選択すると、ユーザーの認証情報が Cookie に保存されます。Cookie の有効期間は 1 年間です。もっと月。
次回ログインするときに、まずユーザーの情報が Cookie に保存されているかどうかを確認し、保存されている場合は、Cookie に保存されているユーザー情報を使用してログインします。
User コンポーネントを設定します設定ファイルのコンポーネント内のユーザーコンポーネント
'user' => [ 'identityClass' => 'app\models\User', 'enableAutoLogin' => true, ],
が使用されていることがわかります。これは、インターフェイスでの次回の自動ログインとは関係がありません。
enableAutoLoginがtrueの場合のみ、次回から自動的にログインすることを選択すると、ユーザー情報はCookieに保存され、次回のCookieの有効期間は3600*24*30秒に設定されますログイン それでは、Yii でどのように実装されるかを見てみましょう。
1. 初回ログイン時にCookieを保存する
1. ログイン関数public function login($identity, $duration = 0) { if ($this->beforeLogin($identity, false, $duration)) { $this->switchIdentity($identity, $duration); $id = $identity->getId(); $ip = Yii::$app->getRequest()->getUserIP(); Yii::info("User '$id' logged in from $ip with duration $duration.", __METHOD__); $this->afterLogin($identity, false, $duration); } return !$this->getIsGuest(); }
メソッドを実行して設定します認証情報。
2. switchIdentity は認証情報を設定しますpublic function switchIdentity($identity, $duration = 0) { $session = Yii::$app->getSession(); if (!YII_ENV_TEST) { $session->regenerateID(true); } $this->setIdentity($identity); $session->remove($this->idParam); $session->remove($this->authTimeoutParam); if ($identity instanceof IdentityInterface) { $session->set($this->idParam, $identity->getId()); if ($this->authTimeout !== null) { $session->set($this->authTimeoutParam, time() + $this->authTimeout); } if ($duration > 0 && $this->enableAutoLogin) { $this->sendIdentityCookie($identity, $duration); } } elseif ($this->enableAutoLogin) { Yii::$app->getResponse()->getCookies()->remove(new Cookie($this->identityCookie)); } }
この方法には主に3つの機能があります
①セッションの有効期限を設定します
②Cookieの有効期限が0より大きく、自動ログインが許可されている場合、ユーザーの認証情報をCookieに保存します
③自動ログインを許可している場合は、Cookie情報を削除してください。これは終了時に呼び出されます。終了時に渡される
$identity は null ですprotected function sendIdentityCookie($identity, $duration) { $cookie = new Cookie($this->identityCookie); $cookie->value = json_encode([ $identity->getId(), $identity->getAuthKey(), $duration, ]); $cookie->expire = time() + $duration; Yii::$app->getResponse()->getCookies()->add($cookie); }
$identity->getId()</p>$identity->getAuthKey () <p>$duration
$identity->getId()<br/>$identity->getAuthKey()<br/>$duration
getId()和getAuthKey()是在IdentityInterface接口中的。我们也知道在设置User组件的时候,这个User Model是必须要实现IdentityInterface接口的。所以,可以在User Model中得到前两个值,第三值就是cookie的有效期。
二、自动从cookie登录
从上面我们知道用户的认证信息已经存储到cookie中了,那么下次的时候直接从cookie里面取信息然后设置就可以了。
1、AccessControl用户访问控制
Yii提供了AccessControl来判断用户是否登录,有了这个就不需要在每一个action里面再判断了
public function behaviors() { return [ 'access' => [ 'class' => AccessControl::className(), 'only' => ['logout'], 'rules' => [ [ 'actions' => ['logout'], 'allow' => true, 'roles' => ['@'], ], ], ], ]; }
2、getIsGuest、getIdentity判断是否认证用户
isGuest是自动登录过程中最重要的属性。
在上面的AccessControl访问控制里面通过IsGuest属性来判断是否是认证用户,然后在getIsGuest方法里面是调用getIdentity来获取用户信息,如果不为空就说明是认证用户,否则就是游客(未登录)。
public function getIsGuest($checkSession = true) { return $this->getIdentity($checkSession) === null; } public function getIdentity($checkSession = true) { if ($this->_identity === false) { if ($checkSession) { $this->renewAuthStatus(); } else { return null; } } return $this->_identity; }
3、renewAuthStatus 重新生成用户认证信息
protected function renewAuthStatus() { $session = Yii::$app->getSession(); $id = $session->getHasSessionId() || $session->getIsActive() ? $session->get($this->idParam) : null; if ($id === null) { $identity = null; } else { /** @var IdentityInterface $class */ $class = $this->identityClass; $identity = $class::findIdentity($id); } $this->setIdentity($identity); if ($this->authTimeout !== null && $identity !== null) { $expire = $session->get($this->authTimeoutParam); if ($expire !== null && $expire < time()) { $this->logout(false); } else { $session->set($this->authTimeoutParam, time() + $this->authTimeout); } } if ($this->enableAutoLogin) { if ($this->getIsGuest()) { $this->loginByCookie(); } elseif ($this->autoRenewCookie) { $this->renewIdentityCookie(); } } }
这一部分先通过session来判断用户,因为用户登录后就已经存在于session中了。然后再判断如果是自动登录,那么就通过cookie信息来登录。
4、通过保存的Cookie信息来登录 loginByCookie
protected function loginByCookie() { $name = $this->identityCookie['name']; $value = Yii::$app->getRequest()->getCookies()->getValue($name); if ($value !== null) { $data = json_decode($value, true); if (count($data) === 3 && isset($data[0], $data[1], $data[2])) { list ($id, $authKey, $duration) = $data; /** @var IdentityInterface $class */ $class = $this->identityClass; $identity = $class::findIdentity($id); if ($identity !== null && $identity->validateAuthKey($authKey)) { if ($this->beforeLogin($identity, true, $duration)) { $this->switchIdentity($identity, $this->autoRenewCookie ? $duration : 0); $ip = Yii::$app->getRequest()->getUserIP(); Yii::info("User '$id' logged in from $ip via cookie.", __METHOD__); $this->afterLogin($identity, true, $duration); } } elseif ($identity !== null) { Yii::warning("Invalid auth key attempted for user '$id': $authKey", __METHOD__); } } } }
先读取cookie值,然后$data = json_decode($value, true);
IdentityInterface インターフェースにあります。また、User コンポーネントを設定する場合、User Model は IdentityInterface インターフェイスを実装する必要があることもわかっています。したがって、ユーザー モデルの最初の 2 つの値を取得でき、3 番目の値は Cookie の有効期間です。
2. Cookie から自動的にログインします
上記のことから、ユーザーの認証情報が Cookie に保存されていることがわかりますので、次回からは Cookie から直接情報を取得して設定するだけで済みます。
1. AccessControl ユーザーのアクセス制御Yii は、ユーザーがログインしているかどうかを判断する AccessControl を提供します。これにより、getIsGuest と getIdentity がログインしているかどうかを判断する必要がなくなります。認証されたユーザー
isGuest は、自動ログイン プロセスで最も重要な属性です。
上記の AccessControl アクセス制御では、
IsGuest🎜 属性を使用して認証されたユーザーであるかどうかを判断し、🎜getIsGuest メソッド🎜で 🎜getIdentity🎜 を呼び出してユーザー情報を取得します。それが空でない場合は、それを意味します。これは認証されたユーザーであり、それ以外の場合はゲスト (ログインしていません) です。 🎜🎜🎜🎜$this->switchIdentity($identity, $this->autoRenewCookie ? $duration : 0);
public function logout($destroySession = true) { $identity = $this->getIdentity(); if ($identity !== null && $this->beforeLogout($identity)) { $this->switchIdentity(null); $id = $identity->getId(); $ip = Yii::$app->getRequest()->getUserIP(); Yii::info("User '$id' logged out from $ip.", __METHOD__); if ($destroySession) { Yii::$app->getSession()->destroy(); } $this->afterLogout($identity); } return $this->getIsGuest(); } public function switchIdentity($identity, $duration = 0) { $session = Yii::$app->getSession(); if (!YII_ENV_TEST) { $session->regenerateID(true); } $this->setIdentity($identity); $session->remove($this->idParam); $session->remove($this->authTimeoutParam); if ($identity instanceof IdentityInterface) { $session->set($this->idParam, $identity->getId()); if ($this->authTimeout !== null) { $session->set($this->authTimeoutParam, time() + $this->authTimeout); } if ($duration > 0 && $this->enableAutoLogin) { $this->sendIdentityCookie($identity, $duration); } } elseif ($this->enableAutoLogin) { Yii::$app->getResponse()->getCookies()->remove(new Cookie($this->identityCookie)); } }
$data = json_decode($value, true);
に逆シリアル化します。配列 。 🎜🎜上記のコードから、自動ログインを実現するには、これら 3 つの値に値が必要であることがわかります。さらに、2 つのメソッド 🎜findIdentity🎜 と 🎜validateAuthKey🎜 もユーザー モデルに実装する必要があります。 🎜🎜ログイン後、Cookieの有効期間をリセットして、Cookieが常に有効になるようにすることができます。 🎜🎜🎜🎜rrreee🎜🎜🎜3. ログアウトを終了します🎜🎜🎜🎜🎜🎜rrreee🎜 終了するときは、まず現在の認証を null に設定し、自動ログイン機能であるかどうかを確認してから、関連する Cookie 情報を削除します。 🎜以上がYii2フレームワークの自動ログインとログイン・終了機能の実装方法の詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。