Dedecms和discuz -x2.5同步登录
1:先配置好ucenter通信成功;添加dedecms和discuz两个应用,
最关键的是两个应用的配置文件:
比如dedecms的配置文件是include/common.inc.php,所以在这个文件里面加入下面的代码:
define('UC_CONNECT','mysql');
define('UC_DBHOST','127.0.0.1');
define('UC_DBUSER','root');
define('UC_DBPW','123456');
define('UC_DBNAME','ucenter');
define('UC_DBCHARSET','gbk');
define('UC_DBTABLEPRE','`ucenter`.uc_');
define('UC_DBCONNECT','0');
define('UC_KEY','2erwr34gthy5uy78hku7k'); //这里的uc_key对应与ucenter的key,要一模一样。
define('UC_API','http://test.juniar.com/ ucenter1.6'); //ucenter的安装的网站地址
define('UC_CHARSET','gbk');
define('UC_IP','');
define('UC_APPID','1');
define('UC_PPP','20');
discuz的配置文件config/config_ucenter.php,参考下,不多说。
各应用必须开启同步登录。
ucenter一般从目录data下的cache/apps.php读取。
2:说下原理,要实现的是 我从dedecms登录,同步登录到bbs下面,这个过程是这样的
1) 从dedecms登录,在登录文件index_do.php里面处理,通过dedecms自身网站的验证后,再调用同步登录函数uc_user_synlogin,这个函数在本应用(dedecms)下的uc_client下的client.php文件里面;
2) Uc_user_synlogin函数调用了uc_api_post,向ucenter的index.php页面发送请求,获得model为user,action为syslogin的值。
3) Ucenter之后调用control目录下的user.php文件的onsynlogin函数,通过foreach循环,以javascript的方式通知ucenter下的各应用,对开启同步登录的应用进行同步登录。
形如这样的:
$synstr .='<script type="text/javascript"src="'.$app['url'].'/api/'.$app['apifilename'].'?time='.$this->time.'&code='.urlencode($this->authcode('action=synlogin&username='.$this->user['username'].'&uid='.$this->user['uid'].'&password='.$this->user['password'].'&email='.$this->user['email']."&time=".$this->time,'ENCODE', $app['authkey'])).'" reload="1"></script>';
这里传过去的url就对应到了各应用api下的uc.php文件了。
4) (各应用的)这里是bbs下的uc.php文件,这个文件下的synlogin函数,用$get处理请求过来的数据,通过P3P 协议,设置本站的cookie,就实现了同步登录。
3:代码附录
Dedecms登录处理:
1)index_do.php
if(defined('UC_API') && @include_onceDEDEROOT.'/uc_client/client.php')
{
//检查帐号
list($uid, $username,$password, $email) = uc_user_login($userid, $pwd);
if($uid > 0) {
echouc_user_synlogin($uid);
//echo '登录成功!';
} elseif($uid == -1) {
//echo '用户不存在,或者被删除';
$result =$dsql->GetOne("SELECT email FROM `#@__member` WHERE userid='{$userid}'");
$uid_=uc_user_register($userid , $pwd , $result['email']);
echouc_user_synlogin($uid_);
} elseif($uid == -2) {
echo '密码错';
} else {
echo '未定义';
}
}
Discuz一般不用改,集成了。
2)如果dedecms 表member的字段uid存储的是email或者更长的字符的话,需要修改应用下的uc_client/model/user.php文件check_username函数,
if($len > 15|| $len < 3 …修改 15 为更大的值,起码要容纳下字段uid的存储空间。
3)最后修改的就是各应用下的api/uc.php文件了。
Dedecms应用下api/uc.php函数synlogin:
function synlogin($get, $post)
{
$uid = $get['uid'];
$username = $get['username'];
$password = $get['password'];
$email = $get['email'];
if(!API_SYNLOGIN)
{
return API_RETURN_FORBIDDEN;
}
//note 同步登录 API 接口
header('P3P: CP="CURa ADMa DEVaPSAo PSDo OUR BUS UNI PUR INT DEM STA PRE COM NAV OTC NOI DSP COR"');
$result =$this->db->GetOne("SELECT mid,pwd FROM `#@__member` WHERE userid='{$uid}' or email='{$email}'");
if(!empty($result))
{
include_onceDEDEINC.'/memberlogin.class.php';
$cfg_ml = new MemberLogin(86400);
$cfg_ml->PutLoginInfo($result['mid']);
}else{
$sql = "insert into`#@__member`(userid,pwd,uname,email) values('{$email}','{$password}','{$username}','{$email}')";
$this->db->query('me',$sql);
$mid=$this->db->GetLastID();
include_onceDEDEINC.'/memberlogin.class.php';
$cfg_ml = new MemberLogin(86400);
$cfg_ml->PutLoginInfo($mid);
}
}
Discuz(bbs)下api/uc.php函数synlogin:
function synlogin($get, $post) {
global $_G;
if(!API_SYNLOGIN) {
return API_RETURN_FORBIDDEN;
}
header('P3P: CP="CURa ADMa DEVaPSAo PSDo OUR BUS UNI PUR INT DEM STA PRE COM NAV OTC NOI DSP COR"');
$cookietime = 31536000;
$uid = intval($get['uid']);
$username = $get['username'];
$password = $get['password'];
$email = $get['email'];
if(($member = getuserbyuid($uid, 1))) {
dsetcookie('auth',authcode("$member[password]\t$member[uid]", 'ENCODE'), $cookietime);
} else {
$time = time();
DB::query("INSERT INTO" . $this -> tablepre ."common_members(uid,username,password,email,groupid,regdate,timeoffset)VALUES ($uid,'$username','$password','$email',10,{$time},9999)");
dsetcookie('auth',authcode("$password\t$uid", 'ENCODE'), $cookietime);
}
}
同步登录处理完成。