164 lines
5.7 KiB
PHP
164 lines
5.7 KiB
PHP
![]() |
<?php
|
||
|
|
||
|
class clientPlugin extends PluginBase{
|
||
|
function __construct(){
|
||
|
parent::__construct();
|
||
|
}
|
||
|
public function regist(){
|
||
|
$this->hookRegist(array(
|
||
|
'user.commonJs.insert' => 'clientPlugin.echoJs',
|
||
|
'user.view.options.after' => 'clientPlugin.tfa.index.options',
|
||
|
'user.index.loginAfter' => 'clientPlugin.tfa.index.loginAfter',
|
||
|
));
|
||
|
}
|
||
|
|
||
|
public function echoJs(){
|
||
|
$this->echoFile('static/main.js');
|
||
|
}
|
||
|
|
||
|
// tfa相关功能
|
||
|
public function tfa(){
|
||
|
Action($this->pluginName . "Plugin.tfa.index")->index();
|
||
|
}
|
||
|
|
||
|
private function needPost(){
|
||
|
if(REQUEST_METHOD != 'POST'){exit;}
|
||
|
}
|
||
|
/**
|
||
|
* 生成二维码
|
||
|
* 有效期: 10分钟; 超过时间不再可用;
|
||
|
* 使用次数: 3次; 超过则不再可用;
|
||
|
* 每个人一个业务只保留一个,重新生成之前的不再可用;
|
||
|
*
|
||
|
* 扫码登录web端需要确认;
|
||
|
*/
|
||
|
public function qrcodeToken(){
|
||
|
$this->needPost();
|
||
|
$systemPassword = Model('SystemOption')->get('systemPassword');
|
||
|
$currentKey = rand_string(8);
|
||
|
Session::set('pluginsClientQrcode',array('count'=>0,'time'=>time(),'key'=>$currentKey));
|
||
|
$token = Mcrypt::encode(Session::sign(),$systemPassword.$currentKey);
|
||
|
show_json($currentKey.$token,true);
|
||
|
}
|
||
|
private function qrcodeParse($token){
|
||
|
$codeTimeout = 5*60; // 二维码有效期; 默认5分钟
|
||
|
$timeCanUse = 1; // 二维码可用次数;
|
||
|
|
||
|
$currentKey = substr($token,0,8);
|
||
|
$token = substr($token,8);
|
||
|
$systemPassword = Model('SystemOption')->get('systemPassword');
|
||
|
$sessionSign = Mcrypt::decode($token,$systemPassword.$currentKey);
|
||
|
if(!$sessionSign){$this->qrError('sign');}
|
||
|
|
||
|
$result = array('code'=>true,'data'=>$sessionSign);
|
||
|
$sessionData = $this->sessionValue($sessionSign);
|
||
|
$scanData = $sessionData['pluginsClientQrcode'];
|
||
|
if(!$scanData || !is_array($scanData) ){return $this->qrError('disable');}
|
||
|
if($scanData['key'] != $currentKey){return $this->qrError('replace');}
|
||
|
if(time() - $scanData['time'] > $codeTimeout){return $this->qrError('timeout');}
|
||
|
if($scanData['count'] >= $timeCanUse){$result = $this->qrError('count');}
|
||
|
|
||
|
$scanData['count'] += 1;
|
||
|
$sessionData['pluginsClientQrcode'] = $scanData;
|
||
|
$this->sessionValue($sessionSign,$sessionData);
|
||
|
return $result;
|
||
|
}
|
||
|
private function qrError($error){
|
||
|
return array('code'=>0,'data'=>LNG('client.app.scanError').'('.$error.')');
|
||
|
}
|
||
|
public function checkPass(){
|
||
|
$userInfo = Session::get('kodUser');
|
||
|
if(!$userInfo || !isset($userInfo['userID'])){show_json(LNG('user.loginFirst'),false);}
|
||
|
|
||
|
$password = Mcrypt::decode($this->in['pass'],$this->in['sign']);
|
||
|
if(!$password){show_json(LNG("ERROR_USER_PASSWORD_ERROR"),false);}
|
||
|
$user = Hook::trigger("user.index.userInfo",$userInfo['name'], $password);
|
||
|
if (!is_array($user)) $user = Model("User")->userLoginCheck($userInfo['name'],$password);
|
||
|
if(!is_array($user) || !isset($user['userID'])){show_json(LNG("ERROR_USER_PASSWORD_ERROR"),false);}
|
||
|
show_json(LNG("explorer.success"),true);
|
||
|
}
|
||
|
|
||
|
|
||
|
/**
|
||
|
* App扫码登录web端; 扫码跳转到url;
|
||
|
* 1. 打开url: HOST/#?loginWeb=xxx; 未登录则先登录; 已登录则弹出确认框 [生成验证key,并附带到页面]
|
||
|
* 2. 弹出确认框; [确认; 取消]
|
||
|
*/
|
||
|
public function loginWeb(){
|
||
|
$this->needPost();
|
||
|
$userInfo = Session::get('kodUser');
|
||
|
if(!$userInfo || !isset($userInfo['userID'])){show_json(LNG('user.loginFirst'),false);}
|
||
|
|
||
|
$targetData = $this->qrcodeParse($this->in['token']);
|
||
|
$sessionSign = $targetData['data'];
|
||
|
if(!$targetData['code']){show_json($targetData['data'],false);}
|
||
|
|
||
|
// 更新目标用户的session数据;
|
||
|
$sessionData = $this->sessionValue($sessionSign);
|
||
|
if($this->in['status'] != '1'){ // 取消登录;
|
||
|
$sessionData['_kodUserLoginApp'] = array('status'=>'cancel');
|
||
|
$this->sessionValue($sessionSign,$sessionData);
|
||
|
show_json(LNG('explorer.success'),true);
|
||
|
}
|
||
|
if(!is_array($sessionData['kodUser'])){
|
||
|
$sessionData['_kodUserLoginApp'] = $userInfo;
|
||
|
$this->sessionValue($sessionSign,$sessionData);
|
||
|
}
|
||
|
show_json(LNG('explorer.success'),true);
|
||
|
}
|
||
|
|
||
|
// APP扫码登录web端,自动检查是否自动登录;
|
||
|
public function check(){
|
||
|
$userInfo = Session::get('kodUser');// 同sessionid 在其他地方登录
|
||
|
if($userInfo && isset($userInfo['userID'])){
|
||
|
show_json(LNG('explorer.success'),true);
|
||
|
}
|
||
|
|
||
|
$loginUser = Session::get('_kodUserLoginApp');
|
||
|
$code = $loginUser && isset($loginUser['userID']);
|
||
|
Session::remove('_kodUserLoginApp');
|
||
|
if($code){
|
||
|
Action("user.index")->loginSuccessUpdate($loginUser);
|
||
|
}
|
||
|
show_json($loginUser,$code);
|
||
|
}
|
||
|
|
||
|
|
||
|
// ===============================================================
|
||
|
// App扫码登录App; 扫码后构造请求; 支持浏览器扫描登录(手机浏览器/微信等扫描web端登录);
|
||
|
public function loginApp(){
|
||
|
$this->needPost();
|
||
|
|
||
|
// 追加了跳转页面的情况,App请求兼容(url中 ?#loginAppID= 后面部分)
|
||
|
$token = $this->in['token'];$find = strpos($token,'&_page=');
|
||
|
if($find){$token = substr($token,0,$find);}
|
||
|
|
||
|
$targetData = $this->qrcodeParse($token);
|
||
|
$sessionSign = $targetData['data'];
|
||
|
if(!$targetData['code']){
|
||
|
show_json($targetData['data'],false);
|
||
|
}
|
||
|
|
||
|
// 更新目标用户的session数据;(切换账号)
|
||
|
$sessionData = $this->sessionValue($sessionSign);
|
||
|
$userInfo = $sessionData['kodUser'];
|
||
|
if(!$userInfo){show_json(LNG('common.loginError').',userInfo error!',false);}
|
||
|
|
||
|
$this->sessionValue($sessionSign,$sessionData);
|
||
|
Action("user.index")->loginSuccessUpdate($userInfo);
|
||
|
$accessToken = Action("user.index")->accessToken();
|
||
|
show_json($accessToken,true,$userInfo['userID']);
|
||
|
}
|
||
|
|
||
|
|
||
|
private function sessionValue($sign,$data=false){
|
||
|
CacheLock::lock($sign);
|
||
|
if($data === false){
|
||
|
$result = unserialize(Session::$handle->get($sign));
|
||
|
}else{
|
||
|
$result = Session::$handle->set($sign,serialize($data),Session::$sessionTime);
|
||
|
}
|
||
|
CacheLock::unlock($sign);
|
||
|
return $result;
|
||
|
}
|
||
|
}
|