前言

在微信公众号开发中,微信网页授权是一个非常重要的功能。通过OAuth2.0网页授权机制,可以获取用户的基本信息,进而实现自己的业务逻辑。本文将详细介绍在ThinkPHP5框架下实现微信网页授权的完整流程。

一、准备工作

1. 配置微信参数

将需要使用到的微信配置放在config.php配置文件中方便获取(这里使用的是微信测试号):

<?php
return array(
    //'配置项'=>'配置值'
    'appID' => 'wxf58**********f2e',
    'appSecret' => '2dd3de4141aadd088**********6264b'
);

2. 配置网页授权回调域名

在微信公众平台中更改网页授权的回调域名为我们当前项目的域名。注意这个域名要是能线上访问的,配置路径为:开发 - 接口权限 - 网页服务 - 网页帐号 - 网页授权获取用户基本信息。

二、验证用户是否进行过微信登录

1. 创建微信授权类AuthController

该类用于完成微信授权,将用户的信息保存在数据库,将每个用户在数据库中的唯一标识user_id保存在session中。

2. 创建基类BaseController

该类是每个控制器的基类(除认证类外),用于验证用户是否进行过微信授权:

class BaseController extends Controller
{
    //使用tp框架提供的构造函数验证session中是否有用户的信息的唯一标识user_id
    public function _initialize()
    {
        $user_id = session('user_id');
        if (!$user_id) {
            //获取当前网页,授权后跳回
            $path = $_SERVER['REQUEST_URI'];
            //跳转到微信授权
            header('Location:/home/auth/index?path=' . $path);
        }
    }
}

3. 使用基类验证授权状态

所有需要验证登录的控制器继承BaseController,如果用户未授权,则自动跳转到微信授权页面。

三、网页授权,获取用户的基本信息

1. 用户授权获取code

在AuthController中实现用户授权跳转:

//用户授权获取code
public function index()
{
    //授权完跳转的网址
    $path = $_REQUEST['path'];
    
    //用户同意授权后回调的网址,必须使用url对回调网址进行编码
    $redirect_uri = urlencode('http://' . $_SERVER['HTTP_HOST'] . '/home/auth/callback');
    
    header('Location:https://open.weixin.qq.com/connect/oauth2/authorize?appid='
        . C('appID') . '&redirect_uri=' . $redirect_uri . '&response_type=code&scope=snsapi_userinfo&state=' . $path . '#wechat_redirect');
}

注意事项:

  • redirect_uri回调网址需要使用urlencode进行编码
  • scope参数值为snsapi_userinfo时,是用户确实授权才能获取到用户基本信息
  • 回调时会带上code参数和state参数,这里将state参数值设置为授权完成后跳转回的原网页地址

2. 获取access_token和用户信息

用户授权跳转到回调网址后,根据获取到的code换取网页授权access_token,然后获取用户的基本信息并保存在数据库中:

//获取code后的回调函数
public function callBack()
{
    //获取到的code
    $code = $_REQUEST['code'];
    
    //授权结束后的回调网址
    $path = $_REQUEST['state'];
    
    //获取access_token
    $curl = curl_init();
    curl_setopt($curl, CURLOPT_URL, 'https://api.weixin.qq.com/sns/oauth2/access_token?appid='
        . C('appID') . '&secret=' . C('appSecret') . '&code=' . $code . '&grant_type=authorization_code');
    curl_setopt($curl, CURLOPT_RETURNTRANSFER, true);
    
    //获取access_token和openid,转换为数组
    $data = json_decode(curl_exec($curl), true);
    
    //如果获取成功,根据access_token和openid获取用户的基本信息
    if ($data != null && $data['access_token']) {
        
        //获取用户的基本信息
        curl_setopt($curl, CURLOPT_URL, 'https://api.weixin.qq.com/sns/userinfo?access_token='
            . $data['access_token'] . '&openid=' . $data['openid'] . '&lang=zh_CN');
        
        $user_data = json_decode(curl_exec($curl), true);
        
        if ($user_data != null && $user_data['openid']) {
            
            curl_close($curl);
            
            //将用户信息存在数据库中,同时将用户在数据库中唯一的标识保存在session中
            $array = [];
            $array['openid'] = $user_data['openid'];
            $array['nickname'] = $user_data['nickname'];
            $array['headimgurl'] = $user_data['headimgurl'];
            
            $model = M('user');
            
            //先判断用户数据是不是已经存储了,如果存储了获取用户在数据库中的唯一标识
            $user_id = $model->where(['openid' => $array['openid']])->getField('user_id');
            
            if ($user_id) {
                session('user_id', $user_id);
            } else {
                $user_id = $model->add($array);
                //将用户在数据库中的唯一标识保存在session中
                session('user_id', $user_id);
            }
            
            //跳转回原来的网页
            header('Location:' . $path);
            
        } else {
            curl_close($curl);
            exit('获取用户信息失败!');
        }
        
    } else {
        curl_close($curl);
        exit('微信授权失败');
    }
}

四、完整流程总结

微信网页授权的完整流程如下:

  1. 用户访问页面:用户访问需要授权的页面
  2. 检测登录状态:BaseController检查session中的user_id
  3. 跳转授权页面:如果未登录,跳转到微信授权页面
  4. 用户同意授权:用户在微信中确认授权
  5. 跳转到回调地址:微信跳转到回调URL,带上code参数
  6. 获取access_token:通过code换取网页授权access_token
  7. 获取用户信息:通过access_token和openid获取用户基本信息
  8. 保存用户数据:将用户信息存入数据库,user_id存入session
  9. 跳转回原页面:授权完成,跳回用户原来访问的页面

常见问题

1. redirect_uri参数错误

确保回调域名已经在微信公众平台中配置,并且redirect_uri进行了urlencode编码。

2. 40163 code been used

code只能使用一次,如果重复使用会出现这个错误。需要重新发起授权获取新的code。

3. 微信授权失败

检查appID和appSecret是否正确,确认使用的是否为已认证的微信公众号。

结语

以上就是ThinkPHP5框架下实现微信网页授权的完整流程。通过这种方式,可以保持用户一直在授权后的登录状态,实现用户信息的持久化。如果在实际开发中遇到问题,欢迎交流讨论。

点赞(0) 打赏

评论列表 共有 0 条评论

暂无评论
立即
投稿

微信公众账号

微信扫一扫加关注

发表
评论
返回
顶部