回顾yii2用户注册与登陆

简介: 前言:很久没用yii2写登陆了。有些细节都有些忘了,写一篇加深下印象,本次做的用户登陆,使用的是yii2 user组件中的login方法来保存用户登陆状态,这也是yii2比较优秀的地方,很多地方不用我们操心目录:使用数据迁移,完成建表完成注册...

前言:

很久没用yii2写登陆了。有些细节都有些忘了,写一篇加深下印象,本次做的用户登陆,使用的是yii2 user组件中的login方法来保存用户登陆状态,这也是yii2比较优秀的地方,很多地方不用我们操心

目录:

  1. 使用数据迁移,完成建表
  2. 完成注册
  3. 完成登陆

  1. 使用数据迁移,完成建表
    yii2中自带了一个user表的数据迁移
数据迁移

我们在控制台目录下找到它的位置
然后用命令行来执行数据迁移

image.png

当数据表建好了之后,我们需要在表中添加一个字段

数据表

就是最后的salt(盐值),字符形 32位,这个主要是用于密码加密,是目前比较流行的也是安全性比较高的加密方式


  1. 完成注册

注册页面我选择使用ActiveForm来做一个表单,需要使用ActiveForm就必须在渲染视图方法中给页面传递一个模型对象来配合使用

    /**
     * 渲染注册页面
     */
    public function actionRegist()
    {
        $userModle = new User();
        return $this->render('regist', ['usermodel' => $userModle]);
    }

由于只是测试使用,并不是实际工作开发,这里注册就只做了账号密码和邮箱,并且没有涉及发邮件技术,如果对发邮件感兴趣的朋友可以点击看我另一篇博客yii2发邮件。这里就不多介绍了

页面我选用了bootstrap框架来做一个简单的表单

image.png

下面来看控制器部分

  /**
     * 完成注册
     */
    public function actionRegistTodo()
    {
        //通过自己封装的私有方法来接收前台提交的表单数据
        $formData = $this->_getRequest();
        //创建模型对象
        $userModel = new User();
        //将数据绑定到模型对象中
        if (!$userModel->load($formData)) {
            exit('绑定数据错误');
        }
        try {
            //调用模型中的创建用户的方法
            if ($userModel->createUser()) {
                echo '注册成功';
            }
            //捕获创建新用户方法中抛出的异常
        } catch (Exception $exception) {
            //打印异常的信息
            var_dump($exception->getMessage());
        }
    }

控制器部分方法比较简洁,重点是控制器中调用的模型层的createUser方法

在创建用户之前,我们需要对前台传递过来的数据进行验证,我们知道程序员永远不能相信用户提交的数据,对于用户的提交,验证是必须的

由于我们的模型类继承了ActiveRecord

class User extends \yii\db\ActiveRecord

所以我们可以使用父类中的validate方法来验证表单数据

     if (!$this->validate()) {
            throw new Exception($this->getErrors());
     }

当调用validate方法后,它会获取到们之前写好的rules方法里面的验证规则,如果数据符合验证规则,返回true,不符合返回false,并且会将不匹配的提示信息绑定到模型对象上,我们可以通过getErrors方法来获取

验证方法

当验证通过后,我们就可以对密码进行加密了,我们使用加盐加密。

  1. 首先我们需要生成随机的盐值
$salt=Yii::$app->security->generateRandomString();

我们调用secrurity组件上的generateRandomString方法来生成一个32位的随机数

  1. 将用户输入的密码和盐值拼接,随后用security组件中的哈希方法进行加密
 $this->password_hash=Yii::$app->security->generatePasswordHash($this->password_hash.$salt);

加密方式按个人喜好,也可使用md5加密

  1. 将生成的盐值绑定到模型对象上
$this->salt=$salt;

盐值需要保存到数据库中,用于用户登陆时进行加密对比

  1. 保存到数据库中
    if (!$this->save(false)) {
            throw new Exception($this->getErrors());
    }

由于其他数据在通过load方法绑定到模型上,我们将加密后的密码和盐值绑定上后,就可以保存到数据库中了

这里有个小细节,当我们调用模型中的save方法保存数据的时候,save方法还会调用validate来验证数据,由于我的验证规则中有验证两次输入密码必须一致,当我们的密码加密后,就和之前的重复密码不一致了,这样就会导致报错。解决方法就是在save方法中传入一个false,这样就不会在save的同时进行验证了


  1. 完成登陆

同样的,登陆我们也是使用的ActiveForm和Bootstrap框架来写表单,不同的是,我们登陆还加入了验证码 (验证码这次就不细谈了)

  1. 前端页面部分
<?php $form = \yii\bootstrap\ActiveForm::begin(['action' => \yii\helpers\Url::to(['login/login-check'])]) ?>
<table>
    <tr>
<!--        用户名-->
        <?= $form->field($model, 'username') ?>
    </tr>
    <tr>
<!--        密码-->
        <?= $form->field($model, 'password_hash') ?>
    </tr>
    <tr>
<!--        重复密码-->
        <?= $form->field($model, 'repassword') ?>
    </tr>
    <tr>
<!--        验证码图片-->
        <td><img style="cursor:pointer;" id="captchaImg" src="<?= \yii\helpers\Url::to(['login/captcha']) ?>" alt=""></td>
    </tr>
    <tr>
        <td>
            <label for="captcha">验证码</label>
<!--            验证码输入框-->
            <input type="text" name="captcha" class="input-xxlarge">
        </td>
    </tr>
    <tr>
        <td><input type="submit" value="提交" class="btn btn-success"></td>
        <td><a class="btn btn-warning" href="<?=\yii\helpers\Url::to(['login/regist'])?>">注册</a></td>
    </tr>
</table>
<?php $form::end(); ?>

前面已经介绍过页面,登陆页面和注册页面类似。

  1. 控制器部分

首先是判断验证码是否正确

验证码

绑定数据,验证数据

验证数据

调用模型方法,查找用户,如果账号密码匹配,调用user组件中的login方法完成登陆

完成登陆

在绑定数据验证数据的时候,有个小细节,这时我们的业务只需要验证用户名和密码,并不需要验证邮箱,可我们的验证规则中写了邮箱。或则在以后我们验证规则中别的什么字段的时候,我们可以采取部分验证

        //验证部分数据(只验证用户名,密码,重复密码)
        if (!$userModel->validate(['username','password_hash','repassword'])) {
            die('数据非法');
        }

将要验证的字段以数组形式传入validate就可以了,这样就只会验证你传入的字段的验证规则.我称之为部分验证

  1. 模型部分

首先我们要使用yii2自带的login方法来保存登陆状态,我们需要我们的user模型继承IdentityInterface身份验证接口,并且实现它里面的抽象方法

继承接口

下面是实现接口的代码

/**
     * 通过传递的id,返回查到的数据模型对象的静态方法
     * @param int|string $id
     * @return static
     */
    public static function findIdentity($id)
    {
        return User::findOne($id);
    }

    /**
     * 通过传递token,返回查到的数据模型对象的静态方法
     * @param mixed $token
     * @param null $type
     * @return static
     */
    public static function findIdentityByAccessToken($token, $type = null)
    {
        return User::findOne(['password_reset_token'=>$token]);
    }

    /**
     * 返回当前对象的id
     * @return string
     */
    public function getId()
    {
        return $this->id;
    }

    /**
     * 获取当前对象的auth_key
     * @return mixed
     */
    public function getAuthKey()
    {
        return $this->auth_key;

    }

    /**
     *对比传递过来的authkey于当前对象的auth_key
     * @param string $authKey
     * @return bool
     * 返回对比结果
     */
    public function validateAuthKey($authKey)
    {
        return $authKey===$this->getAuthKey();
    }

前面的准备工作,搞定过后,我们就可以来完成登陆验证
我们登陆分三部

  1. 获取用户输入的用户名,判断是否有这个用户
  2. 将盐值从数据库中取出,并于用户输入的密码拼接
  3. 将加密后的用户输入的密码,和数据库中存储的密码进行比对

任意一步失败,则抛出异常

第一部

        $username=$this->username;
        $password_hash=$this->password_hash;
        //查询数据表中用户名
        $userModel=User::findOne(['username'=>$username]);
        if (empty($userModel)) {
            throw new Exception('用户或密码错误');
        }

第二部

        //账号存在,对比密码
        $salt=$userModel->salt;
        //用户表单提交的密码加密
        $securityPassword=$password_hash.$salt;

拼接后的密码不需要进行hash加密,我们使用yii2 security组件中的validatePassword的方法来比对

第三部

      if (!Yii::$app->security->validatePassword($securityPassword,$userModel->password_hash)) {
            throw new Exception('用户或密码错误');
      }
        return $userModel;

密码验证通过后,则返回查找到的数据模型对象
控制器获取到了数据模型对象后就可以调用user组件中的login方法,进行保存用户登陆的状态了

好了,本次回顾yii2登陆注册的介绍了就写到这里了,如果有什么地方不对,希望大神指正.谢谢

以上

相关文章
|
1月前
|
存储 数据库 数据安全/隐私保护
实现一个简单的Web应用,要求可以进行用户注册和登录。
实现一个简单的Web应用,要求可以进行用户注册和登录。
21 3
|
7月前
JavaWeb用户信息管理系统-在登录中添加验证码功能
JavaWeb用户信息管理系统-在登录中添加验证码功能
47 0
|
6月前
|
PHP 数据库 数据安全/隐私保护
PHP写用户注册、登录和密码重置功能
PHP写用户注册、登录和密码重置功能
|
4月前
uniapp获取微信用户信息登录
uniapp获取微信用户信息登录
uniapp手机号授权登录-现在只能通过手机号授权登录,后台来获取用户信息了效果demo(整理)
uniapp手机号授权登录-现在只能通过手机号授权登录,后台来获取用户信息了效果demo(整理)
Uni-App - 用户没有登录自动跳转登录页面方案
Uni-App - 用户没有登录自动跳转登录页面方案
853 0
Uni-App - 用户没有登录自动跳转登录页面方案
Beego学习——实现用户登录登出
Beego学习——实现用户登录登出
81 0
uniapp授权登陆获取用户信息和code
uniapp授权登陆获取用户信息和code
360 0
uniapp授权登陆获取用户信息和code
|
PHP
【laravel项目】@2 账号密码登录验证(2)
【laravel项目】@2 账号密码登录验证
60 0
【laravel项目】@2 账号密码登录验证(2)
|
PHP
【laravel项目】@2 账号密码登录验证(1)
【laravel项目】@2 账号密码登录验证
62 0
【laravel项目】@2 账号密码登录验证(1)