美文网首页
微信h5页面分享之多个页面一个公众号

微信h5页面分享之多个页面一个公众号

作者: 洗耳恭听_kai | 来源:发表于2022-05-18 15:43 被阅读0次

    我想先放个图,因为这句话让我陷入了深深的沉思……


    image.png

    我只想说刚刚开始读还读的通,再读几遍就有点迷茫了。。

    一、功能项目环境

    • 直播h5页面的分享功能
    • 多个直播
    • 一个公众号

    二、实现步骤

    基本步骤在官方文档中,还算是人能读通的,我就直接复制过来了

    步骤一:绑定域名

    先登录微信公众平台进入“公众号设置”的“功能设置”里填写“JS接口安全域名”。

    备注:登录后可在“开发者中心”查看对应的接口权限。

    步骤二:引入JS文件

    在需要调用JS接口的页面引入如下JS文件,(支持https):http://res.wx.qq.com/open/js/jweixin-1.6.0.js

    如需进一步提升服务稳定性,当上述资源不可访问时,可改访问:http://res2.wx.qq.com/open/js/jweixin-1.6.0.js (支持https)。

    备注:支持使用 AMD/CMD 标准模块加载方法加载

    步骤三:通过config接口注入权限验证配置

    所有需要使用JS-SDK的页面必须先注入配置信息,否则将无法调用(同一个url仅需调用一次,对于变化url的SPA的web app可在每次url变化时进行调用,目前Android微信客户端不支持pushState的H5新特性,所以使用pushState来实现web app的页面会导致签名失败,此问题会在Android6.2中修复)。

    wx.config({
      debug: true, // 开启调试模式,调用的所有api的返回值会在客户端alert出来,若要查看传入的参数,可以在pc端打开,参数信息会通过log打出,仅在pc端时才会打印。
      appId: '', // 必填,公众号的唯一标识
      timestamp: , // 必填,生成签名的时间戳
      nonceStr: '', // 必填,生成签名的随机串
      signature: '',// 必填,签名
      jsApiList: [] // 必填,需要使用的JS接口列表
    });
    

    三、代码

    前端

    let url = location.href.split('#')[0];
    let link = encodeURIComponent(url);
    $.ajax({
        type: "GET",
        url: 'https://h5-saic.matrixpr.net/know/token/get-sign-str1',
        dataType: "jsonp",
        jsonp: 'callback',
        data: {
            url: link,
            type: '02'
        },
        success: function(res) {
            wx.config({
                debug: false,
                appId: res.data.appId,
                timestamp: res.data.timestamp,
                nonceStr: res.data.noncestr,
                signature: res.data.signature,
                jsApiList:['updateTimelineShareData','updateAppMessageShareData']
        });
    wx.ready(() => {
        //wx.hideOptionMenu();
        wx.updateTimelineShareData({
            title: tent.sharetitle, // 分享标题
            desc: tent.sharetitle2, // 分享描述
            link: url, // 分享链接,该链接域名或路径必须与当前页面对应的公众号JS安全域名一致
            imgUrl: tent.sharesrc, // 分享图标
            success: function () {
                // 设置成功
                console.log('成功')
                resolve();
            },
            fail:function(e){
                    const msg = e.errMsg || "未知错误";
                    cAlert(msg);
                reject(new Error(msg));
            }
        })
        wx.updateAppMessageShareData({ 
          title: tent.sharetitle, // 分享标题
          desc: tent.sharetitle2, // 分享描述
          link: url, // 分享链接,该链接域名或路径必须与当前页面对应的公众号JS安全域名一致
          imgUrl: tent.sharesrc, // 分享图标
          success: function () {
                // 设置成功  
                resolve();
          },
          fail:function(e){
            const msg = e.errMsg || "未知错误";
            cAlert(msg);
            reject(new Error(msg));
         }
      })
    })
    },
    error: function(xhr, status, error) {
        console.log("获取微信参数失败==" + error);
    }
    });
    

    PHP

    public function actionGetSignStr(){
            header("Access-Control-Allow-Origin: *");
            $url  = (\Yii::$app->request->get('url'));
            $type  = (\Yii::$app->request->get('type'));
            if (empty($url)) {
                OutTools::outJsonP(OutTools::error(Constants::PARAM_LOSE, '缺少必要参数!'));
            }
            $url = urldecode($url);
            $redis = Yii::$app->redis;
            $key = 'matrix_main_kyle'.$type;
            if ( $redis->get($key) ) {
                $ticket = $redis->get($key);
            } else {
                $access_token = $this->getTokenCuigsnqaphep11( 'matrix_main',$type );
                //var_dump($access_token);die;
                //$curlUrl = 'https://qyapi.weixin.qq.com/cgi-bin/ticket/get?access_token='.$access_token.'&type=agent_config';
                //$curlUrl = 'https://qyapi.weixin.qq.com/cgi-bin/get_jsapi_ticket?access_token='.$access_token;
                $curlUrl = 'https://api.weixin.qq.com/cgi-bin/ticket/getticket?access_token='.$access_token.'&type=jsapi';
                $res = HttpTools::http_get($curlUrl);
                $r = json_decode($res,true);
    
                if($r['errcode'] == 0){
                    $ticket = $r['ticket'];
                    $expires_in = $r['expires_in'];
                    $redis->set($key, $ticket);
                    $redis->expire($key, $expires_in);
                }else{
                    OutTools::outJsonP(OutTools::error(Constants::PARAM_LOSE, '获取失败!'));
                }
            }
            $noncestr = $this->generateNonce();
            $timestamp = time();
            //$url = 'https://h5-saic.matrixpr.net/sgm_zhihu_store/html9999';
            //$url = 'http://192.168.89.110:8080/';
            $jsapi_ticket='jsapi_ticket='.$ticket.'&noncestr='.$noncestr.'&timestamp='.$timestamp.'&url='.$url;
            // 转换成key=val&串
    //        $params = [
    //            'ticket' => $ticket,
    //            'noncestr' => $noncestr,
    //            'timestamp' => $timestamp,
    //            'url' => $url,
    //        ];
            //$jsapi_ticket = self::createLinkString ( $params, true, false );
            $signature = sha1($jsapi_ticket);
    
            $str = [
                'ticket' => $ticket,
                'noncestr' => $noncestr,
                'timestamp' => $timestamp,
                'signature' => $signature,
                'jsapi_ticket' => $jsapi_ticket,
                'url' => $url,
                'appId' => 'wxcca46bafxxxxxx'
            ];
            $res = OutTools::success( $str ,  '请求成功!');
            OutTools::outJsonP($res);
        }
    

    四、问题及总结

    经过上述步骤可以知道,首先需要接收前端传来的url,这个url最好在前端进行encodeURIComponent(url),然后在后端再进行解码urldecode($url)。接着根据appid和appsecret获取access_token,再用access_token来获取ticket,接着用ticket和其他一些参数生成签名signature,最后将这些参数一并传回给前端。

    那么问题来了,我们再看文章刚开始我放的那个图,如果是同一个公众号,也就是只有一个appid和密钥的话,这里生成的一些参数还可以配置成功吗?
    那个图中文档上说如果url变化的话需要在每次变化的时候调用。什么叫每次变化的时候调用,我不同直播h5页面路径本来就是不同啊。网上说的是在前端vue的路由中进行配置注入。


    image.png

    vue我不太懂,如果是不同项目下的呢?那我就用个蠢蠢的方法,直接在前端调用接口,这个接口,我在后端复制完全一样的来,命名为2,3,4....,这样是不是也可以说在url变化的时候调用?我调用不同接口。。。靠,一开始我也不知道能不能行,神奇的是居然还真可以。。
    我之前还试了一下不同access_token调用ticket,由于这两个参数都有有效期,结果获取到的ticket居然一样,然后配置失败。
    接着我重新获取一个ticket,配置还是失败。
    所以我就直接复制不同的接口,前端不同项目调用不同接口就行了。


    image.png image.png

    相关文章

      网友评论

          本文标题:微信h5页面分享之多个页面一个公众号

          本文链接:https://www.haomeiwen.com/subject/ccjaurtx.html