绑定QQ登录 PHP OAuth详解(转)

越来越多的网站开始采用 第三方账号登录 如qq 微博 开心网 等诸多流行的社交平台,利用第三方账号登录,可以更好地省去用户的注册时间,并且极大地提高用户体验,吸引更多的潜在用户。

让用户拥有 一个号码走web天下的感觉。。。,对我们开发者来说 这也是一个主要的学习新知识点 主要原理即Oauth。

<span style="font-family: SimHei, 黑体, tahoma, arial, helvetica, sans-serif;">OAUTH协议为用户资源的授权提供了一个安全的、开放而又简易的标准。与以往的授权方式不同之处是OAUTH的授权不会使第三方触及到用户的帐号信息(如用户名与密码),即第三方无需使用用户的用户名与密码就可以申请获得该用户资源的授权,因此OAUTH是安全的。</span>  

步骤详细介绍 

1.去qq、微博的第三方开发平台 去review一下他们的API

2.申请AppId和AppKey ,对于qq来说 网址 http://connect.opensns.qq.com/ 点击首页的 <网站接入>

注册自己的开发者信息 随便百度一下 输入一个备案号 即可 然后我们就可以获得 AppId和AppKey

<span style="font-family: SimHei, 黑体, tahoma, arial, helvetica, sans-serif;"><?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",//这里修改为当前脚本
    '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(!empty($_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);
    }
}
</span>

 转载自:http://www.iteye.com/topic/1129210

 

转载于:https://www.cnblogs.com/JoannaQ/p/3172885.html

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值