UCenter通信失败调试经历及分析应用与UCenter通信原理

对于初次接触Ucenter的人来讲,添加一个自己的应用最头疼的就是发现通信失败。
如果要解决这个问题,首先要了解Ucenter是如何和应用进行通信的。
只有知道了Ucenter和应用之间如何通信,我们才能找到通信失败的原因。
那让我们从源头找起吧!

如果用火狐来辅助查找通信失败的源头会更加简单一些【我可不是给火狐做广告啊!它真的是太好用了】。

我们先来看看是谁输出了通信失败四个字:
在火狐中右键->本帧->查看帧源代码【注意,要在“通信失败”附近】。如图:

1通过火狐查看帧代码图示

然后在源代码中查找应用访问地址。找到通信失败所在位置。
请注意,通信失败四个字是有js生成的。直接查找通信失败是找不到的。
认真研究一番之后,我们发现通信失败是由类似如下代码生成的:

<div id="status_3"></div><script id="link_3" testlink="admin.php?m=app&a=ping&inajax=1&url=http://www.seinc.com/slight&ip=&appid=3&random=30773"></script><script>apps[2] = '3';</script>

看起来是通过admin.php对应用地址进行访问,根据访问结果判断是否通信成功。
从字面上来看应该是app里边ping动作。好像还是ajax来访问的。
既然找到了通信失败的原因那我们就到admin.php的app中去找一下ping时候究竟它访问了什么,根据什么样的结果来判断通信成功还是失败。

我们看一下Ucenter的目录。很明显,操作程序代码都在control目录里边。进入control目录,哇!果然有个app.php。
先别急!没看到还有个admin目录么。既然刚刚是通过admin.php调用app的那么这个动作当然是写在admin目录里了。
其实control目录下的app.php是常规操作app。如果你打开代码查找ping方法是找不到的。

好,我们进入admin目录,打开app.php,查找ping。嗯!找到了!如下图:

2app.php里的onping方法图示

这个方法叫做onping。我们分析一下发现关键在这个地方:

if($status == '1') {
   echo 'document.getElementByIdx_x(\'status_'.$appid.'\').innerHTML = "<img src=\'images/correct.gif\' border=\'0\' class=\'statimg\' \/><span class=\'green\'>'.$this->lang['app_connent_ok'].'</span>";testlink();';
  } else {
   echo 'document.getElementByIdx_x(\'status_'.$appid.'\').innerHTML = "<img src=\'images/error.gif\' border=\'0\' class=\'statimg\' \/><span class=\'red\'>'.$this->lang['app_connent_false'].'</span>";testlink();';
  }

如果status的值是1就是ok,反之则false。再简单看一下上边的代码。我们注意到onping方法访问的地址其实是应用地址+/api/+$app['apifilename']。
那么用脚指头也明白了,其实访问的真是地址是应用目录api目录下的uc.php。
如果不是很相信,我们就把$url给输出来瞧一下。将代码作如下改动:

if($status == '1') {
   echo 'document.getElementByIdx_x(\'status_'.$appid.'\').innerHTML = "<img src=\'images/correct.gif\' border=\'0\' class=\'statimg\' \/><span class=\'green\'>'.$url.'</span>";testlink();';
  } else {
   echo 'document.getElementByIdx_x(\'status_'.$appid.'\').innerHTML = "<img src=\'images/error.gif\' border=\'0\' class=\'statimg\' \/><span class=\'red\'>'.$url.'</span>";testlink();';
  }

注意我们把输出的ok或者false替换成了上边的url。在管理后台查看一下应用列表:
呵呵,地址出来了!我们把失败的地址和成功的地址分别复制到地址栏进行访问。
洁白的页面上如果只有个1,就表示成功。如果是其他的东西就表示失败了!

既然我们知道了访问的真实地址,那么就去看看这个地址是如何告诉Ucenter通信成功还是失败的。

打开应用目录api里的uc.php之后我们注意到它首先对get过来的code进行解码,得到动作指令后进行响应:

$code = $_GET['code'];
parse_str(authcode($code, 'DECODE', UC_KEY), $get);//先做解密,就是url?code后边那一长串。
if(MAGIC_QUOTES_GPC) {
 $get = dstripslashes($get);
}
//print_r($get);
//exit;
if(time() - $get['time'] > 3600) {
 exit('Authracation has expiried');
}
if(empty($get)) {
 exit('Invalid Request');
}
$action = $get['action'];//解码后得到action 就是Ucenter传过来的指令。Ucenter到底默认会传递什么指令过来?回到Ucenter的app.php里认真研究了onping我们发现默认传递的是test指令。

那我们就查找uc.php里的test。最终发现当默认连接时候执行的代码快。
根据个人情况的不同,这里的代码每个人可能得到的不一样。认真研究一下就会发现问题出在哪里。

如果比较懒,看不懂,那就直接deleted…然后echo 1;欺骗一下Ucenter。看到通信成功的小对勾,心里舒服多了吧。

个文章只是告诉你为什么会失败。如何获得成功的字眼。到底通信成功和失败会有什么影响不在本文讨论范围之内。
最后,我们再来清洗一下Ucenter和应用之间如何交互:

ucenter通过应用里的api/uc.php获得应用通信情况,发送指令信息。比如用户更新,用户删除之类的操作。在uc.php中有对应的方法。也就是说如果你在ucenter里进行了用户操作。而应用中要同步的话就指望uc.php了。ucenter每次重要操作都会发送指令给uc.php。而且会主动监测通信情况。
应用则通过uc_client访问用户数据。比如登陆,注册等。这个我在ucenter与wordpress整合中曾经提到过。

如果无论你添加一个什么样的应用,都能得到一个“通信成功”的小对勾。那这个文章总算没白写。

转载自:
当Ucenter和应用通信失败:http://blog.sina.com.cn/s/blog_775f158f010135uz.html

参考资料:
关于Ucenter通信失败的又一次调试经历:http://www.blogguy.cn/show-780-1.html

发表评论?

0 条评论。

发表评论

此站点使用Akismet来减少垃圾评论。了解我们如何处理您的评论数据