介绍
介绍
今天我们和福哥一起来好好设计一下安全问题功能,安全问题用来识别账号的安全保护身份。用户在指定若干问题里面挑出三个问题,并提供这三个问题的自己的答案。在验证安全保护身份的时候,用户需要答出这三个问题的答案,且答案要一字不差。这种验证的安全系数是非常高的,即便是和用户本人非常熟悉的人也很难得出三个问题的正确答案。
设置安全问题
代码
/** * note: * 1 - user is not exists * 2 - exception * * @param int $userID * @param int $q1 * @param string $a1 * @param int $q2 * @param string $a2 * @param int $q3 * @param string $a3 * @return int */ public function setSecurityQuestions(int $userID, int $q1, string $a1, int $q2, string $a2, int $q3, string $a3):int { $tfdo = $this->tfphp->getDatabase()->getTFDO(); $userInfo = $tfdo->fetchOne("select * from user where userID = @int", $userID); if($userInfo == null){ return 1; } $sqInfo = $tfdo->fetchOne("select * from user_security_questions where userID = @int", $userID); if($sqInfo == null){ $ret = $tfdo->insert("user_security_questions", array( 'userID'=>$userID, 'q1'=>$q1, 'a1'=>$a1, 'q2'=>$q2, 'a2'=>$a2, 'q3'=>$q3, 'a3'=>$a3, ), array( 'userID'=>"int", 'q1'=>"int", 'q2'=>"int", 'q3'=>"int", )); } else{ $ret = $tfdo->update("user_security_questions", array( 'q1'=>$q1, 'a1'=>$a1, 'q2'=>$q2, 'a2'=>$a2, 'q3'=>$q3, 'a3'=>$a3, ), array( 'q1'=>"int", 'q2'=>"int", 'q3'=>"int", ), "userID = @int", $userID); } if(!$ret){ return 2; } return 0; }
获取安全问题
代码
/** * @param int $userID * @return array|null */ public function getSecurityQuestions(int $userID):?array { $tfdo = $this->tfphp->getDatabase()->getTFDO(); return $tfdo->fetchOne("select * from user_security_questions where userID = @int", $userID); }
验证安全问题
代码
/** * note: * 1 - security questions is not set * 2 - answer is wrong * 3 - question is invalid * * @param int $userID * @param int $q1 * @param string $a1 * @param int $q2 * @param string $a2 * @param int $q3 * @param string $a3 * @return bool */ public function verifySecurityQuestions(int $userID, int $q1, string $a1, int $q2, string $a2, int $q3, string $a3):bool { $tfdo = $this->tfphp->getDatabase()->getTFDO(); $sqInfo = $tfdo->fetchOne("select * from user_security_questions where userID = @int", $userID); if($sqInfo == null){ return 1; } $userSecurityQuestionInfo = array( array('q'=>$sqInfo['q1'], 'a'=>$sqInfo['a1']), array('q'=>$sqInfo['q2'], 'a'=>$sqInfo['a2']), array('q'=>$sqInfo['q3'], 'a'=>$sqInfo['a3']), ); $verifySecurityQuestionInfo = array( array('q'=>$q1, 'a'=>$a1), array('q'=>$q2, 'a'=>$a2), array('q'=>$q3, 'a'=>$a3), ); foreach ($verifySecurityQuestionInfo as $key => $item){ $passed = false; foreach($userSecurityQuestionInfo as $key2 => $item2){ if($item['q'] == $item2['q']){ if($item['a'] != $item2['a']){ return 2; } else{ $passed = true; unset($userSecurityQuestionInfo[$key2]); break; } } } if(!$passed){ return 3; } } return 0; }
讲解
设置安全问题
首先我们要检查当前用户$userID是不是存在的,不存在就没必要继续了。
接着我们要判断当前用户是不是有设置过安全问题,如果有就更新,没有就写入。
三个问题和答案对应三组六个字段,名字不要对应错了。
获取安全问题
直接判断当前用户是不是有设置过安全问题即可,没有这个用户或者没有设置过安全问题都一样。
验证安全问题
首先我们要检查当前用户$userID是不是存在的,不存在就没必要继续了。
取出数据库里的安全问题和答案后,循环和验证的问题和答案逐一判断,通过一组删除一组,不通过就报错。
这里面需要一个小技巧,就是把三组问题和答案放入数组里,数据库里的数据一组,验证数据一组,双重循环进行比较。
总结
今天童鞋们和福哥一起把安全问题的功能的逻辑部分全部都实现了,安全问题将成为用户忘记密码时候作为重置密码的方式之一。
下一课我们将实现个人资料修改的功能,敬请期待~~