首頁 >php框架 >YII >yii怎麼做登入

yii怎麼做登入

尚
原創
2019-12-31 14:56:201997瀏覽

yii怎麼做登入

yii做登入的方法範例:

1、LoginForm.php

使用者登陸模組,所提交的是username和password,所以我們要先建立一個Model,專門處理用戶提交的數據,所以先新建一個LoginForm.php,以下為程式碼:

<?php
 
namespace app\modules\backend\models;
 
use Yii;
use yii\base\Model;
 
/**
 * LoginForm is the model behind the login form.
 */
class LoginForm extends Model
{
    public $username;
    public $password;
    public $rememberMe = true;
 
    private $_user = false;
 
 
    /**
     * @return array the validation rules.
     */
    public function rules()<span style="white-space:pre">		</span>//①
    {
        return [
            // username and password are both required
            [[&#39;username&#39;, &#39;password&#39;], &#39;required&#39;,&#39;message&#39;=>""],
            // rememberMe must be a boolean value
            [&#39;rememberMe&#39;, &#39;boolean&#39;],
            // password is validated by validatePassword()
            [&#39;password&#39;, &#39;validatePassword&#39;],
        ];
    }
 
    /**
     * Validates the password.
     * This method serves as the inline validation for password.
     *
     * @param string $attribute the attribute currently being validated
     * @param array $params the additional name-value pairs given in the rule
     */
    public function validatePassword($attribute, $params)
    {
        if (!$this->hasErrors()) {
            $user = $this->getUser();
 
            if (!$user || !$user->validatePassword($this->password)) {
                $this->addError($attribute, &#39;Incorrect username or password.&#39;);
            }
        }
    }
 
    /**
     * Logs in a user using the provided username and password.
     * @return boolean whether the user is logged in successfully
     */
    public function login()
    {
        if ($this->validate()) {
            if($this->rememberMe)
            {
                $this->_user->generateAuthKey();//③
            }
            return Yii::$app->user->login($this->getUser(), $this->rememberMe ? 3600*24*30 : 0);
        }
        return false;
    }
 
    /**
     * Finds user by [[username]]
     *
     * @return User|null
     */
    public function getUser()
    {
        if ($this->_user === false) {
            $this->_user = User::findByUsername($this->username); //②
        }
 
        return $this->_user;
    }
}

該Model是根據basic模板自帶的LoginForm修改而成,程式碼中大多有註釋,這裡關注以下程式碼:

①號程式碼處是rules規則,rules規則定義了填滿過來的資料的規則,驗證所填的資料是否為空,是否符合格式之類的,其中有一欄位是password,對應的規則是validatePassword,會自動呼叫目前類別的validatePassword()方法,注意與下文的User類別對應的方法區分。

②號程式碼,呼叫了User類別裡面的findByUsername方法,這個User類別下面會寫到,主要是為了傳回一個AR類別實例,與目前LoginForm的資料進行比較。

③號代碼,這裡暫時不提,等講到cookie登陸的時候再提。

2、User.php

(1)ActiveRecord 類別

#在完成LoginForm後,我們還缺少一些東西,從使用者接受到資料了,那麼還需要從資料庫取出相應的數據來進行比較,所以我們接下來需要完成的是一個從數據庫獲取的數據的類——AR類,全稱是ActiveRecord,活動記錄類,方便用於查找數據,只要類名和數據表的表名相同,那麼它就能從這個數據表中獲取數據,比如說這樣:

<?php
namespace app\modules\backend\models;
use yii\db\ActiveRecord;
 
class User extends ActiveRecord{       } ?>

還能自己添加返回的表名,只要在這個類別中重寫以下方法:

public static function tableName(){
		return &#39;user&#39;;
	}

(2)IdentityInterface 介面

一般來說,從資料庫中找到數據,只需要繼承AR類別即可,但是,我們這個是使用者登入模型,核心是驗證,所以自然需要實現核心的驗證功能,就像LoginForm模型提到的validatePassword一樣,實際的驗證邏輯是在目前的User模型完成的。一般來說,實作IdentityInterface接口,需要實作以下方法:

    public static function findIdentity($id);  //①
 
    public static function findIdentityByAccessToken($token, $type = null);   //②
 
    public function getId();    //③
 
    public function getAuthKey();   //④
 
    public function validateAuthKey($authKey);    //⑤

①findIdentity:是根據id查找資料表對應的資料

②findIdentityByAccessToken是根據AccessToken(上文提到的)來尋找對應的數據,而AccessToken我們在數據表也有這個字段,那麼它到底有什麼用呢?其實AccessToken在我們目前的用戶登陸模型中用處並不大,它是專門用於Resetful登陸驗證用到的,具體可自行百度,這裡不展開說明。

③getId:傳回目前AR類別所對應的id

④getAuthKey:傳回目前AR類別所對應的auth_key

⑤validateAuthKey:這個方法比較重要,是我們後面要講到的cookie登陸驗證的核心所在。

在我們的User.php實作接口,然後重寫以上方法,完整的User.php的程式碼如下:

$token]);
	}
 
	public static function findByUsername($username){     //①
		return static::findOne(['username'=>$username]); 
	}
 
	public function getId(){
		return $this->id;
	}
 
	public function getAuthkey(){
		return $this->auth_key;
	}
 
	public function validateAuthKey($authKey){
		return $this->auth_key === $authKey;
	}
 
	public function validatePassword($password){          //②
		return $this->password === md5($password);
	}
 
   	 /**
    	 * Generates "remember me" authentication key
    	 */
        public function generateAuthKey()                    //③
        {
       		$this->auth_key = \Yii::$app->security->generateRandomString();
       		$this->save();
        }
 
}
?>

①findByUsername():在LoginForm的程式碼中,引用了這個方法,目的是根據使用者提交的username傳回一個在資料表與username相同的資料項,即AR實例。

②validatePassword():這裡將使用者提交的密碼以及目前AR類別的密碼進行比較。

③generateAuthKey():產生隨機的auth_key,用於cookie登陸。

總共寫了兩個Model類別:LoginForm和User,一個用來接收使用者提交的數據,一個用來取得資料庫的資料。

控制器(Controller)

控制器,主要用於資料的提交,把使用者提交的資料填入對應的模型(Model)中,然後根據模型傳回的資訊進一步渲染視圖(View),或執行其他邏輯。

這裡,把控制器命名為LoginController.php,以下是完整的實作程式碼:

<?php
 
namespace app\controllers;
 
use Yii;
use yii\filters\AccessControl;
use yii\web\Controller;
use yii\filters\VerbFilter;
use app\models\LoginForm;
use app\models\ContactForm;
 
class SiteController extends Controller
{
    public function actionIndex()
    {
        return $this->render(&#39;index&#39;);
    }
 
    public function actionLogin()
    {
        if (!\Yii::$app->user->isGuest) {     //①
            return $this->goHome();
        }
 
        $model = new LoginForm();             //②
        if ($model->load(Yii::$app->request->post()) && $model->login()) {      //③
            return $this->goBack();          //④
        }
        return $this->render(&#39;login&#39;, [      //⑤
            &#39;model&#39; => $model,
        ]);
    }
 
    public function actionLogout()
    {
        Yii::$app->user->logout();
 
        return $this->goHome();
    }
}

①先從\Yii::$app->user->isGuest中判斷,目前是否為遊客模式,即未登陸狀態,如果使用者已經登陸,會在user類別中儲存目前登陸使用者的資訊。

②如果目前是遊客,會先實例化一個LoginForm模型

③這行程式碼是整個login方法的核心所在,首先:$model->load(Yii::$ app->request->post())把post過來的資料填入$model,即LoginForm模型,如果回傳true,則填入成功。接著:$model->login():執行LoginForm類別裡面的login()方法,可以從login()方法裡面看到,將會執行一系列的驗證。

視圖(View)

在實作了model和controller,接下來是視圖部分,由於使用者需要輸入數據,所以我們要提供一個表單,在Yii2中,提供了ActiveForm快速產生表單,程式碼如下:

<?php
 
/* @var $this yii\web\View */
/* @var $form yii\bootstrap\ActiveForm */
/* @var $model app\models\LoginForm */
 
use yii\helpers\Html;
use yii\bootstrap\ActiveForm;
 
$this->title = &#39;Login&#39;;
$this->params[&#39;breadcrumbs&#39;][] = $this->title;
?>
<div class="site-login">
    <h1><?= Html::encode($this->title) ?></h1>
    <p>Please fill out the following fields to login:</p>
    <?php $form = ActiveForm::begin([
        &#39;id&#39; => &#39;login-form&#39;,
        &#39;options&#39; => [&#39;class&#39; => &#39;form-horizontal&#39;],
        &#39;fieldConfig&#39; => [
            &#39;template&#39; => "{label}\n<div class=\"col-lg-3\">{input}</div>\n<div class=\"col-lg-8\">{error}</div>",
            &#39;labelOptions&#39; => [&#39;class&#39; => &#39;col-lg-1 control-label&#39;],
        ],
    ]); ?>
        <?= $form->field($model, &#39;username&#39;)->textInput([&#39;autofocus&#39; => true]) ?>
        <?= $form->field($model, &#39;password&#39;)->passwordInput() ?>
        <?= $form->field($model, &#39;rememberMe&#39;)->checkbox([
            &#39;template&#39; => "<div class=\"col-lg-offset-1 col-lg-3\">{input} {label}</div>\n<div class=\"col-lg-8\">{error}</div>",
        ]) ?>
        <div class="form-group">
            <div class="col-lg-offset-1 col-lg-11">
                <?= Html::submitButton(&#39;Login&#39;, [&#39;class&#39; => &#39;btn btn-primary&#39;, &#39;name&#39; => &#39;login-button&#39;]) ?>
            </div>
        </div>
    <?php ActiveForm::end(); ?>
    <div class="col-lg-offset-1" style="color:#999;">
        You may login with <strong>admin/admin</strong> or <strong>demo/demo</strong>.<br>
        To modify the username/password, please check out the code <code>app\models\User::$users</code>.
    </div>
</div>

推薦學習:yii框架

#

以上是yii怎麼做登入的詳細內容。更多資訊請關注PHP中文網其他相關文章!

陳述:
本文內容由網友自願投稿,版權歸原作者所有。本站不承擔相應的法律責任。如發現涉嫌抄襲或侵權的內容,請聯絡admin@php.cn