微信开发平台 第三方平台 后台接口的实现 授权事件接收URL 消息与事件接收URL Java

2 篇文章 0 订阅

1、授权事件接收 URL

此处要注意5个参数和1个xml响应体,其中xml要注意先Unicode解码一下,然后需要再按照指定格式解析出来encrypt,然后注意wxBizMsgCrypt.decryptMsg的最后一个参数是经过格式转换的,不是原来微信直接返回的xml,此处是关键,很多博主的代码中这一块被工具类代码隐藏了。具体代码如下:

@ApiOperation("授权事件接收URL")
    @RequestMapping(value = "/receiveAuth", method ={RequestMethod.POST, RequestMethod.GET})
    public Object receiveAuth(@RequestBody String postData,
                              @RequestParam(value = "signature", required = false) String signature,
                              @RequestParam(value = "timestamp", required = false) String timeStamp,
                              @RequestParam(value = "nonce", required = false) String nonce,
                              @RequestParam(value = "encrypt_type", required = false) String encryptType,
                              @RequestParam(value = "msg_signature", required = false) String msgSignature) {
        try {
            //从XML中获取<Encrypt></Encrypt>标签内的密文文本
            if (postData.endsWith("\\n")) {
                postData = postData.substring(0, postData.length() -2);
            }
            postData = UnicodeUtil.toString(postData);
            Document document = XmlUtil.readXML(postData);
            NodeList nodeList = document.getElementsByTagName("Encrypt");
            String encrypt = nodeList.item(0).getTextContent();
            log.info("Encrypt:" + encrypt);
            //格式化密文文本,否则没有<ToUserName>标签,会解密失败,参考官方的加解密代码JAVA版本
            String format = "<xml><ToUserName><![CDATA[toUser]]></ToUserName><Encrypt><![CDATA[%1$s]]></Encrypt></xml>";
            String fromXML = String.format(format, encrypt);

            String msg;   //解密后的明文
            if(StrUtil.isEmpty(encrypt)) {
                msg = fromXML;
            } else {
                WXBizMsgCrypt wxBizMsgCrypt = new WXBizMsgCrypt(Token, EncodingAESKey, appId);
                // 解密消息
                msg = wxBizMsgCrypt.decryptMsg(msgSignature, timeStamp, nonce, fromXML);
            }
            log.info("解密后的明文:" + msg);
            //将XML格式字符串转为Map类型
            Document resultDocument = XmlUtil.readXML(msg);
            NodeList infoTypeNodeList = resultDocument.getElementsByTagName("InfoType");
            String infoType = infoTypeNodeList.item(0).getTextContent();
            switch (infoType) {
                case "component_verify_ticket":
                    NodeList ticketNodeList = resultDocument.getElementsByTagName("ComponentVerifyTicket");
                    String componentVerifyTicket = ticketNodeList.item(0).getTextContent();
                    Jedis jedis = null;
                    try {
                        jedis = RedisUtil.getWeChatJedis();
                        jedis.set(MiniProgramComponentVerifyTicket, componentVerifyTicket);
                        jedis.expire(MiniProgramComponentVerifyTicket, 60*60*12);
                    } finally {
                        jedis.close();
                    }
                    log.info("ComponentVerifyTicket成功更新:{}", componentVerifyTicket);
                    break;
                default:
                    break;
            }
        } catch (Exception e) {
            log.error(e.getMessage());
        }
        return "success";
    }

 2、消息与事件接收URL,此处只是简单的实现了接口,没有具体做处理

    @ApiOperation("消息与事件接收URL")
    @RequestMapping(value = "/appid/callback", method ={RequestMethod.POST, RequestMethod.GET})
    public Object callback(@RequestBody String xml,
                              @RequestParam(value = "signature", required = false) String signature,
                              @RequestParam(value = "timestamp", required = false) String timeStamp,
                              @RequestParam(value = "nonce", required = false) String nonce,
                              @RequestParam(value = "encrypt_type", required = false) String encryptType,
                              @RequestParam(value = "msg_signature", required = false) String msgSignature) throws Exception {
        return "success";
    }

3、其他接口的实现,要注意2点:

一、参数component_access_token是放在请求链接上的

二、请求体是json转换的字符串,不是json。

相关示例代码:

public String getComponentAccessToken() {
        String componentAccessToken = null;
        Jedis jedis = null;
        try {
            jedis = RedisUtil.getWeChatJedis();
            componentAccessToken = jedis.get(ComponentAccessToken);
            if (componentAccessToken != null) {
                return componentAccessToken;
            }
            Map<String, Object> param = new HashMap<>();
            param.put("component_appid", ComponentAppid);
            param.put("component_appsecret", ComponentAppsecret);
            String componentVerifyTicket = jedis.get(MiniProgramComponentVerifyTicket);
            param.put("component_verify_ticket", componentVerifyTicket);
            System.out.println(JSONUtil.toJsonStr(param));
            String post = HttpUtil.post("https://api.weixin.qq.com/cgi-bin/component/api_component_token", JSONUtil.toJsonStr(param));
            log.info("微信第三方平台接口:获取令牌,返回结果:{}", post);
            JSONObject jsonObject = JSONUtil.parseObj(post);
            Object token = jsonObject.get("component_access_token");
            if (token != null) {
                jedis.set(ComponentAccessToken, (String) token);
                jedis.expire(ComponentAccessToken, 7100);
                componentAccessToken = (String) token;
                log.info("重新获取component_access_token并放Redis中缓存成功:", token);
            }
        } catch (Exception e) {
            log.error("获取component_access_token失败:", e);
        } finally {
            jedis.close();
        }
        return componentAccessToken;
    }

    /**
     * 获取预授权码
     * https://developers.weixin.qq.com/doc/oplatform/Third-party_Platforms/2.0/api/ThirdParty/token/pre_auth_code.html
     * @return
     */
    public ResultDto getPreAuthCode() {
        String componentAccessToken = getComponentAccessToken();
        Map<String, Object> param = new HashMap<>();
        param.put("component_appid", ComponentAppid);
        String post = HttpUtil.post("https://api.weixin.qq.com/cgi-bin/component/api_create_preauthcode?component_access_token=" + componentAccessToken, JSONUtil.toJsonStr(param));
        log.info("微信第三方平台接口:获取预授权码,返回结果:{}", post);
        JSONObject jsonObject = JSONUtil.parseObj(post);
        if (jsonObject.get("pre_auth_code") != null) {
            String preAuthCode = (String) jsonObject.get("pre_auth_code");
            log.info("获取component_access_token成功:", preAuthCode);
            return new ResultDto(CodeEnum.SUCCESS, preAuthCode);
        } else {
            return new ResultDto(CodeEnum.ERROR_WE_CHAT, post);
        }
    }

    /**
     * 使用授权码获取授权信息
     * https://developers.weixin.qq.com/doc/oplatform/Third-party_Platforms/2.0/api/ThirdParty/token/authorization_info.html
     * @param req
     * @return
     */
    public ResultDto getAuthorizationInfo(GetAuthorizationInfoReq req) {
        String componentAccessToken = getComponentAccessToken();
        Map<String, Object> param = new HashMap<>();
        param.put("component_appid", ComponentAppid);
        param.put("authorization_code", req.getAuthorizationCode());
        String post = HttpUtil.post("https://api.weixin.qq.com/cgi-bin/component/api_query_auth?component_access_token=" + componentAccessToken, JSONUtil.toJsonStr(param));
        log.info("微信第三方平台接口:使用授权码获取授权信息,返回结果:{}", post);
        JSONObject jsonObject = JSONUtil.parseObj(post);
        return new ResultDto(CodeEnum.SUCCESS, jsonObject);
    }

    public ResultDto getOrRefreshToken(GetOrRefreshTokenReq req) {
        String componentAccessToken = getComponentAccessToken();
        Map<String, Object> param = new HashMap<>();
        param.put("component_appid", ComponentAppid);
        param.put("authorizer_appid", req.getAuthorizerAppid());
        param.put("authorizer_refresh_token", req.getAuthorizerRefreshToken());
        String post = HttpUtil.post("https://api.weixin.qq.com/cgi-bin/component/api_authorizer_token?component_access_token=" + componentAccessToken, JSONUtil.toJsonStr(param));
        log.info("微信第三方平台接口:获取/刷新接口调用令牌,返回结果:{}", post);
        JSONObject jsonObject = JSONUtil.parseObj(post);
        return new ResultDto(CodeEnum.SUCCESS, jsonObject);
    }

    /**
     * https://developers.weixin.qq.com/doc/oplatform/Third-party_Platforms/2.0/api/ThirdParty/token/api_get_authorizer_info.html
     * @param req
     * @return
     */
    public ResultDto getAuthorizerInfo(GetAuthorizerInfoReq req) {
        String componentAccessToken = getComponentAccessToken();
        Map<String, Object> param = new HashMap<>();
        param.put("component_appid", ComponentAppid);
        param.put("authorizer_appid", req.getAuthorizerAppid());
        String post = HttpUtil.post("https://api.weixin.qq.com/cgi-bin/component/api_get_authorizer_info?component_access_token=" + componentAccessToken, JSONUtil.toJsonStr(param));
        log.info("微信第三方平台接口:获取授权帐号信息,返回结果:{}", post);
        JSONObject jsonObject = JSONUtil.parseObj(post);
        return new ResultDto(CodeEnum.SUCCESS, jsonObject);
    }

    public ResultDto commitCode(CommitCodeReq req) {
        Map<String, Object> param = new HashMap<>();
        param.put("template_id", req.getTemplateId());
        param.put("ext_json", req.getExtJson());
        param.put("user_version", req.getUserVersion());
        param.put("user_desc", req.getUserDesc());
        String post = HttpUtil.post("https://api.weixin.qq.com/wxa/commit?access_token=" + req.getAccessToken(), JSONUtil.toJsonStr(param));
        log.info("微信第三方平台接口:上传代码,返回结果:{}", post);

        byte[] bytes = HttpUtil.downloadBytes("https://api.weixin.qq.com/wxa/get_qrcode?access_token=" + req.getAccessToken());

//        String get = HttpUtil.get("https://api.weixin.qq.com/wxa/get_qrcode?access_token=" + req.getAccessToken());
//        log.info("微信第三方平台接口:获取体验版二维码,返回结果:{}", get);
//        JSONObject jsonObject = JSONUtil.parseObj(get);

        return new ResultDto(CodeEnum.SUCCESS, bytes);
    }

    public ResultDto getQrcode(GetQrcodeReq req) {
        String get = HttpUtil.get("https://api.weixin.qq.com/wxa/get_qrcode?access_token=" + req.getAccessToken());
        log.info("微信第三方平台接口:获取体验版二维码,返回结果:{}", get);
//        JSONObject jsonObject = JSONUtil.parseObj(get);
        return new ResultDto(CodeEnum.SUCCESS, get);
    }

 相关参考:

微信开放平台_第三方平台授权流程_验证票据_小张写bug的博客-CSDN博客

微信开放平台---授权事件接收URL---Java_u011645644的博客-CSDN博客_授权事件接收url

java三方开放平台_微信开放平台---授权事件接收URL---Java_weixin_39978749的博客-CSDN博客

java三方开放平台_微信开放平台---授权事件接收URL---Java_weixin_39978749的博客-CSDN博客

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值