微信公众平台-第三方平台开发(三)扫码授权第三方平台

 这张图是官方提供的扫码授权流程

Controller

/**
     * 刷新公共授权码,由于component_access_token需要2个小时刷新一次,所以需要判断本地表中存在的第三方接口调用凭据updateTime和当前时间的差值
     * 如果超过1小时50分就调用微信接口更新,否则不做任何操作
     *  componentVerifyTicket 根据最近可用的component_verify_ticket来获得componentAccessToken和preAuthCode
     */
    @ApiOperation(value = "获取预授权码")
    @RequestMapping(value = "/platform/getpreAuthCode",
            method = { RequestMethod.GET, RequestMethod.POST })
    public String getpreAuthCode() {
        return weChatService.getpreAuthCode();
    }

 Service处理

public String getpreAuthCode() {
        try{
        String componentVerifyTicket = redisService.getCacheObject("component_verify_ticket");
        if(StringUtils.isEmpty(componentVerifyTicket)) throw new ServiceException("第三方平台获取【验证票据Ticket】失败");
        WeChatPlatFormAuth weChatPlatFormAuth = redisService.getCacheObject("component_access_token");
        if (weChatPlatFormAuth!=null) { // component_access_token没有过期
            //刷新component_access_token
            //weChatPlatFormAuth = refreshComponentAccessToken(PLATFORM_APP_ID,PLATFORM_APP_SECRET,componentVerifyTicket);
            //获取预授权码
            WeChatPlatFormAuth preAuth = redisService.getCacheObject("pre_auth_code");
            if(preAuth!=null){
                return preAuth.getPre_auth_code();
            }else{
                //刷新预授权码
                preAuth = refreshPreAuthCode(weChatPlatFormAuth.getComponentAccessToken(),PLATFORM_APP_ID);
                return preAuth.getPre_auth_code();
            }
        } else { //首次接收ticket,需要走一遍整个流程,获取component_access_token和pre_auth_code,添加进本地数据库
          
            // 首先获取component_access_token
            JSONObject params = new JSONObject();
            params.put("component_verify_ticket", componentVerifyTicket);
            params.put("component_appsecret", PLATFORM_APP_SECRET);
            params.put("component_appid", PLATFORM_APP_ID);
            String result = HttpUtils.httpRequest("https://api.weixin.qq.com/cgi-bin/component/api_component_token", "POST", params.toString()).toString();
            String componentAccessToken = com.alibaba.fastjson.JSONObject.parseObject(result).getString("component_access_token");
            // 获取pre_auth_code
            JSONObject preParams = new JSONObject();
            preParams.put("component_appid", PLATFORM_APP_ID);
            JSONObject preAuth = HttpUtils.httpRequest("https://api.weixin.qq.com/cgi-bin/component/api_create_preauthcode?component_access_token=" + componentAccessToken, "POST", preParams.toString());
            WeChatPlatFormAuth preAuthCodeInfo = (WeChatPlatFormAuth) JSONObject.toBean(preAuth,WeChatPlatFormAuth.class);
            String preAuthCode = preAuthCodeInfo.getPre_auth_code();
            // 封装参数,添加进本地数据库
            if (!StringUtils.isEmpty(componentAccessToken) && !StringUtils.isEmpty(preAuthCode)) {
                weChatPlatFormAuth = new WeChatPlatFormAuth();
                weChatPlatFormAuth.setComponentVerifyTicket(componentVerifyTicket);
                weChatPlatFormAuth.setComponentAccessToken(componentAccessToken);
                redisService.setCacheObject("component_access_token", weChatPlatFormAuth, (long) 7100, TimeUnit.SECONDS);
                redisService.setCacheObject("pre_auth_code", preAuthCodeInfo, (long) preAuthCodeInfo.getExpires_in(), TimeUnit.SECONDS);
            } else {
                throw new ServiceException("获取授权码失败,请联系管理员");
            }
        return preAuthCode;
        }
        }catch (Exception e){
           throw new ServiceException("获取授权码失败,请联系管理员");
        }
    }

 web接收preAuthCode

引导用户进入扫码画面


getPreAuthCode().then(res=>{
    #component_appid :第三方平台id
    #pre_auth_code : 后天返回的授权码字符串
    #redirect_uri : 授权完成后需要跳转的地址
          const url = "https://mp.weixin.qq.com/cgi-bin/componentloginpage?component_appid=" + this.component_appid + "&pre_auth_code=" +res+ '&redirect_uri='+this.basePath+'&auth_type=1'
          // window.open(url)
            location.href= url
        }).catch(error=>{
          this.msgError(error)
        })

授权完成后跳转的地址会带有两个  参数分别是 auth_code 和 expires_in

这是公众号获取调用令牌所需要的code,带着auth_code去后台获取调用令牌并保存下来

let auth_code = that.$route.query.auth_code;
      let expires_in =  that.$route.query.expires_in;
      if(auth_code&&expires_in){
        getAuthorizerInfo({authCode:auth_code,expiresIn:expires_in}).then(res=>{
          that.msgSuccess("保存成功!");
          
        })
      }

public void getAuthorizerInfo(String authCode, String expiresIn) {
        try {
            SysDept sysDept = tokenService.getLoginUser().getSysUser().getDept();
            VtWechatAccount wechatAccount = new VtWechatAccount();
            //获取授权公众号的刷新令牌
            logger.error("准备获取公众号主体信息======PLATFORM_APP_ID:" + PLATFORM_APP_ID  );
            WeChatPlatFormAuth weChatPlatFormAuth = redisService.getCacheObject("component_access_token");
            WeChatPlatFormAuth preAuth = redisService.getCacheObject("pre_auth_code");
            if(weChatPlatFormAuth!=null&&preAuth!=null){
                    //String componentAccessToken = com.alibaba.fastjson.JSONObject.parseObject(redisService.getCacheObject("pre_auth_code")).getString("componentAccessToken");
                    JSONObject params = new JSONObject();
                    params.put("component_appid", PLATFORM_APP_ID);
                    params.put("authorization_code", authCode);
                    //-------获取授权公众号的刷新令牌
                    String authorizerRefreshToken = HttpUtils.httpRequest("https://api.weixin.qq.com/cgi-bin/component/api_query_auth?component_access_token=" + weChatPlatFormAuth.getComponentAccessToken(),"POST", params.toString()).toString();
                    com.alibaba.fastjson.JSONObject obj = com.alibaba.fastjson.JSONObject.parseObject(com.alibaba.fastjson.JSONObject.parseObject(authorizerRefreshToken).getString("authorization_info"));
                    String authorizer_appid = obj.getString("authorizer_appid");
                    logger.error("获取授权公众号的刷新令牌======" + obj.getString("authorizer_refresh_token"));
                    //-------获取授权账号调用令牌
                    JSONObject authorizationInfo = new JSONObject();
                    authorizationInfo.put("component_appid", PLATFORM_APP_ID);
                    authorizationInfo.put("authorizer_appid", authorizer_appid);
                    authorizationInfo.put("authorizer_refresh_token", obj.getString("authorizer_refresh_token"));
                    String authorizer_access_token_info = HttpUtils.httpRequest("https://api.weixin.qq.com/cgi-bin/component/api_authorizer_token?component_access_token="+weChatPlatFormAuth.getComponentAccessToken(),"POST", authorizationInfo.toString()).toString();
                    com.alibaba.fastjson.JSONObject authInfo = com.alibaba.fastjson.JSONObject.parseObject(authorizer_access_token_info);
                    String authorizer_access_token = authInfo.getString("authorizer_access_token");
                    String authorizer_refresh_token = authInfo.getString("authorizer_refresh_token");
                    wechatAccount.setAuthorizerAccessToken(authorizer_access_token);
                    wechatAccount.setAuthorizerRefreshToken(authorizer_refresh_token);
                    long account_expires_in = Long.parseLong(authInfo.getString("expires_in"));
                    //将授权账号调用令牌写入redis缓存,避免API调用触发每日限额
                    redisService.setCacheObject(Constants.WE_CHAT.AUTH_ACCESS_TOKEN_PREFIX + authorizer_appid,wechatAccount,account_expires_in,TimeUnit.SECONDS);
                    logger.error("获取授权账号调用令牌======" + authorizer_access_token);
                    //拉取已授权的帐号信息
                    JSONObject user = new JSONObject();
                    user.put("component_appid",PLATFORM_APP_ID);
                    user.put("authorizer_appid",authorizer_appid);
                    String usersStr = HttpUtils.httpRequest("https://api.weixin.qq.com/cgi-bin/component/api_get_authorizer_info?component_access_token="+ weChatPlatFormAuth.getComponentAccessToken() ,"POST", user.toString()).toString();
                    com.alibaba.fastjson.JSONObject backObj = com.alibaba.fastjson.JSONObject.parseObject(usersStr);
                    com.alibaba.fastjson.JSONObject authorizerInfo = (com.alibaba.fastjson.JSONObject) backObj.get("authorizer_info");
                    logger.error("拉取已授权的帐号信息,公众号名称======" + authorizerInfo.getString("nick_name"));
                    //将授权的公众号基本信息保存至数据库中

                    
                    redisService.setCacheObject(authorizer_appid,wechatAccount,account_expires_in,TimeUnit.SECONDS);

                    // 初始化菜单
                    int menu  = createMenu("菜单 json",authorizer_access_token);
//                    if(menu==0){
//                        throw new ServiceException("初始化菜单失败");
//                    }
            }else{
                //response.sendRedirect("/vip/weChat");
                throw new ServiceException("令牌已失效");
            }
        } catch (Exception e) {
            throw new ServiceException("公众号信息保存失败!");
        }
    }

 初始化公众号菜单

public static final String MENU_CREATE_URL = "https://api.weixin.qq.com/cgi-bin/menu/create?access_token=ACCESS_TOKEN";
public static int createMenu(String jsonMenu, String accessToken) {
        int result = 0;
        // 拼装创建菜单的url
        String url = MENU_CREATE_URL.replace("ACCESS_TOKEN", accessToken);
        // 调用接口创建菜单
        JSONObject jsonObject = HttpUtils.httpRequest(url, "POST", jsonMenu);
        if (null != jsonObject) {
            if (0 != jsonObject.getInt("errcode")) {
                result = jsonObject.getInt("errcode");
            }
        }
        return result;
    }

至此授权流程完结!

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值