QQ登录 PHP OAuth示例代码


Posted in PHP onJuly 20, 2011

根据官方文档编写

<?php 
/** 
* 申请http://connect.opensns.qq.com/apply 
* 列表http://connect.opensns.qq.com/my 
*/ 
session_start(); 
$qq_oauth_config = array( 
'oauth_consumer_key'=>'*******',//APP ID 
'oauth_consumer_secret'=>'******************',//APP KEY 
'oauth_callback'=>"http://www.955.cc/qq.php?action=reg",//这里修改为当前脚本,但是要保留?action=reg 
'oauth_request_token_url'=>"http://openapi.qzone.qq.com/oauth/qzoneoauth_request_token", 
'oauth_authorize_url'=>'http://openapi.qzone.qq.com/oauth/qzoneoauth_authorize', 
'oauth_request_access_token_url'=>'http://openapi.qzone.qq.com/oauth/qzoneoauth_access_token', 
'user_info_url' => 'http://openapi.qzone.qq.com/user/get_user_info', 
); 
$action = isset($_GET['action']) ? $_GET['action'] : ''; 
$qq = new qq_oauth($qq_oauth_config); 
switch($action){ 
//用户登录 Step1:请求临时token 
case 'login': 
$token = $qq->oauth_request_token(); 
$_SESSION['oauth_token_secret'] = $token['oauth_token_secret']; 
$qq->authorize($token['oauth_token']); 
break; 
//Step4:Qzone引导用户跳转到第三方应用 
case 'reg': 
$qq->register_user(); 
$access_token = $qq->request_access_token(); 
if($token = $qq->save_access_token($access_token)){ 
//保存,一般发给用户cookie,以及用户入库 
//var_dump($token); 
$_SESSION['oauth_token'] = $token['oauth_token']; 
$_SESSION['oauth_token_secret'] = $token['oauth_token_secret']; 
$_SESSION['openid'] = $token['openid']; 
header('Content-Type: text/html; charset=utf-8'); 
$user_info = json_decode($qq->get_user_info()); 
if($user_info->ret!=0){ 
exit("获取头像昵称时发生错误".$user_info->msg); 
} else { 
echo 'QQ昵称:',$user_info->nickname, 
'<img src="',$user_info->figureurl,'" />', 
'<img src="',$user_info->figureurl_1,'" />', 
'<img src="',$user_info->figureurl_2,'" />'; 
} 
} 
break; 
default : 
} 
class qq_oauth{ 
private $config; 
function __construct($config){ 
$this->config = $config; 
} 
/** 
* 返回配置 
* @param string $name 
* 
*/ 
function C($name){ 
return isset($this->config[$name]) ? $this->config[$name] : FALSE; 
} 
/** 
* 构建请求URL 
* @param string $url 
* @param array $params 
* @param string $oauth_token_secret 
* 
*/ 
function build_request_uri($url,$params=array(),$oauth_token_secret=''){ 
$oauth_consumer_key = $this->C('oauth_consumer_key'); 
$oauth_consumer_secret = $this->C('oauth_consumer_secret'); 
$params = array_merge(array( 
'oauth_version'=>'1.0', 
'oauth_signature_method'=>'HMAC-SHA1', 
'oauth_timestamp'=>time(), 
'oauth_nonce'=>rand(1000,99999999), 
'oauth_consumer_key'=>$oauth_consumer_key, 
),$params); 
$encode_params = $params; 
ksort($encode_params); 
$oauth_signature = 'GET&'.urlencode($url).'&'.urlencode(http_build_query($encode_params)); 
$oauth_signature = base64_encode(hash_hmac('sha1',$oauth_signature,$oauth_consumer_secret.'&'.$oauth_token_secret,true)); 
$params['oauth_signature'] = $oauth_signature; 
return $url.'?'.http_build_query($params); 
} 
/** 
* 校验回调是否返回约定的参数 
*/ 
function check_callback(){ 
if(isset($_GET['oauth_token'])) 
if(isset($_GET['openid'])) 
if(isset($_GET['oauth_signature'])) 
if(isset($_GET['timestamp'])) 
if(isset($_GET['oauth_vericode'])) 
return true; 
return false; 
} 
function get_contents($url){ 
$curl = curl_init(); 
curl_setopt($curl,CURLOPT_RETURNTRANSFER,true); 
curl_setopt($curl,CURLOPT_URL,$url); 
return curl_exec($curl); 
} 
/** 
* Step1:请求临时token、Step2:生成未授权的临时token 
*/ 
function oauth_request_token(){ 
$url = $this->build_request_uri($this->C('oauth_request_token_url')); 
$tmp_oauth_token = $this->get_contents($url); 
parse_str($tmp_oauth_token); 
/* 
oauth_token 未授权的临时token 
oauth_token_secret token的密钥,该密钥仅限于临时token 
error_code 错误码 
*/ 
if(isset($error_code)) exit($error_code); 
return array( 
'oauth_token'=>$oauth_token, 
'oauth_token_secret'=>$oauth_token_secret 
); 
} 
/** 
* Step3:引导用户到Qzone的登录页 
* @param string $oauth_token 未授权的临时token 
*/ 
function authorize($oauth_token){ 
$str = "HTTP/1.1 302 Found"; 
header($str); 
$url = $this->C('oauth_authorize_url'); 
$query_strings = http_build_query(array( 
'oauth_consumer_key'=>$this->C('oauth_consumer_key'), 
'oauth_token'=>$oauth_token, 
'oauth_callback'=>$this->C('oauth_callback'), 
)); 
header('Location: '.$url.'?'.$query_strings); 
} 
/** 
* Step4:Qzone引导用户跳转到第三方应用 
* @return bool 验证是否有效 
*/ 
function register_user(){ 
/* 
* oauth_token 已授权的临时token 
* openid 腾讯用户对外的统一ID,该OpenID与用户QQ号码一一对应 
* oauth_signature 签名值,方便第三方来验证openid以及来源的可靠性。 
* 使用HMAC-SHA1算法: 
* 源串:openid+timestamp(串中间不要添加'+'符号) 
* 密钥:oauth_consumer_secret 
* timestamp openid的时间戳 
* oauth_vericode 授权验证码。 
*/ 
if($this->check_callback()){ 
//校验签名 
$signature = base64_encode(hash_hmac('sha1',$_GET['openid'].$_GET['timestamp'],$this->C('oauth_consumer_secret'),true)); 
if(!emptyempty($_GET['oauth_signature']) && $signature==$_GET['oauth_signature']){ 
$_SESSION['oauth_token'] = $_GET['oauth_token']; 
$_SESSION['oauth_vericode'] = $_GET['oauth_vericode']; 
return; 
} 
} 
//校验未通过 
exit('UNKNOW REQUEST'); 
} 
/** 
* Step5:请求access token 
*/ 
function request_access_token(){ 
$url = $this->build_request_uri($this->C('oauth_request_access_token_url'),array( 
'oauth_token'=>$_SESSION['oauth_token'], 
'oauth_vericode'=>$_SESSION['oauth_vericode'] 
),$_SESSION['oauth_token_secret']); 
return $this->get_contents($url); 
} 
/** 
* Step6:生成access token (保存access token) 
* 
* 关于access_token 
* 目前access_token(及其secret)是长期有效的,和某一个openid对应,目前可以支持线下获取该openid的信息。 
* 当然,用户有权限在Qzone这边删除对第三方的授权,此时该access_token会失效,需要重新走整个流程让用户授权。 
* 以后会逐步丰富access_token的有效性,长期有效、短期有效、用户登录时才有效等。 
*/ 
function save_access_token($access_token_str){ 
parse_str($access_token_str,$access_token_arr); 
if(isset($access_token_arr['error_code'])){ 
return FALSE; 
} else { 
return $access_token_arr; 
} 
} 
/** 
* 目前腾讯仅开放该API 
* 获取登录用户信息,目前可获取用户昵称及头像信息。 
* http://openapi.qzone.qq.com/user/get_user_info 
*/ 
function get_user_info(){ 
$url = $this->build_request_uri($this->C('user_info_url'),array( 
'oauth_token'=>$_SESSION['oauth_token'], 
'openid'=>$_SESSION['openid'], 
),$_SESSION['oauth_token_secret']); 
return $this->get_contents($url); 
} 
}

文件打包下载 qq_php.rar
转自: http://dev.meettea.com
PHP 相关文章推荐
一个php作的文本留言本的例子(三)
Oct 09 PHP
非常不错的MySQL优化的8条经验
Mar 24 PHP
php access 数据连接与读取保存编辑数据的实现代码
May 12 PHP
php基础学习之变量的使用
Jun 09 PHP
php设计模式 Chain Of Responsibility (职责链模式)
Jun 26 PHP
PHP-CGI进程CPU 100% 与 file_get_contents 函数的关系分析
Aug 15 PHP
基于php伪静态的实现详细介绍
Apr 28 PHP
phpmyadmin配置文件现在需要绝密的短密码(blowfish_secret)的2种解决方法
May 07 PHP
PHP中使用BigMap实例
Mar 30 PHP
php将金额数字转化为中文大写
Jul 09 PHP
PHP 等比例缩放图片详解及实例代码
Sep 18 PHP
Thinkphp框架使用list_to_tree 实现无限级分类列出所有节点示例
Apr 04 PHP
模板引擎正则表达式调试小技巧
Jul 20 #PHP
php中批量替换文件名的实现代码
Jul 20 #PHP
关于php连接mssql:pdo odbc sql server
Jul 20 #PHP
PHP mcrypt可逆加密算法分析
Jul 19 #PHP
PHP中date()日期函数有关参数整理
Jul 19 #PHP
php URL验证正则表达式
Jul 19 #PHP
PHP中static关键字原理的学习研究分析
Jul 18 #PHP
You might like
PHP 和 MySQL 基础教程(三)
2006/10/09 PHP
PHP正则匹配反斜杠'\'和美元'$'的方法
2017/02/08 PHP
THINKPHP3.2使用soap连接webservice的解决方法
2017/12/13 PHP
《JavaScript高级程序设计》阅读笔记(一) ECMAScript基础
2012/02/27 Javascript
jQuery事件 delegate()使用方法介绍
2012/10/30 Javascript
web开发人员学习jQuery的6大理由及jQuery的优势介绍
2013/01/03 Javascript
firefox下jquery ajax返回object XMLDocument处理方法
2014/01/26 Javascript
Javascript获取CSS伪元素属性的实现代码
2014/09/28 Javascript
jQuery不兼容input的change事件问题解决过程
2014/12/05 Javascript
angularjs 处理多个异步请求方法汇总
2015/01/06 Javascript
js操作table元素实现表格行列新增、删除技巧总结
2015/11/18 Javascript
Bootstrap 附加导航(Affix)插件实例详解
2016/06/01 Javascript
jQuery原理系列-常用Dom操作详解
2016/06/07 Javascript
详解Angular2中的编程对象Observable
2016/09/17 Javascript
ReactJs快速入门教程(精华版)
2016/11/28 Javascript
JS使用正则截取两个字符串之间的字符串实现方法详解
2017/01/06 Javascript
基于JavaScript实现飘落星星特效
2017/08/10 Javascript
node.js+captchapng+jsonwebtoken实现登录验证示例
2017/08/17 Javascript
浅谈Vue 数据响应式原理
2018/05/07 Javascript
python实现对一个完整url进行分割的方法
2015/04/29 Python
Python下实现的RSA加密/解密及签名/验证功能示例
2017/07/17 Python
python向字符串中添加元素的实例方法
2019/06/28 Python
python_array[0][0]与array[0,0]的区别详解
2020/02/18 Python
Django认证系统user对象实现过程解析
2020/03/02 Python
使用python执行shell脚本 并动态传参 及subprocess的使用详解
2020/03/06 Python
完美解决torch.cuda.is_available()一直返回False的玄学方法
2021/02/06 Python
CSS3 仿微信聊天小气泡实例代码
2017/04/05 HTML / CSS
C语言面试题
2015/10/30 面试题
机械系大学毕业生推荐信
2013/11/27 职场文书
教师纪念9.18事件演讲稿范文
2014/09/14 职场文书
出资证明书范本(标准版)
2014/09/24 职场文书
三严三实学习心得体会
2014/10/13 职场文书
圣诞节开幕词
2015/01/29 职场文书
刑事上诉状(量刑过重)
2015/05/23 职场文书
Spark SQL 2.4.8 操作 Dataframe的两种方式
2021/10/16 SQL Server
苹果M1芯片安装nginx 并且部署vue项目步骤详解
2021/11/20 Servers