热门标签 | HotTags
当前位置:  开发笔记 > 编程语言 > 正文

微信开发之JSSDK+PHP实现录音、上传、语音识别,分享

先看效果图:先录音,录音成功之后,把录音追加到列表,点击列表可以播放;录音完成之后上传录音,上传成功再语音识别。 微信官方文档 https:developers.weixin.qq


先看效果图:先录音,录音成功之后,把录音追加到列表,点击列表可以播放;录音完成之后上传录音,上传成功再语音识别。

微信开发之JS-SDK + PHP实现录音、上传、语音识别,微信开发之JS-SDK + PHP实现录音、上传、语音识别,微信开发之JS-SDK + PHP实现录音、上传、语音识别,

 

%ignore_a_1%官方文档 https://developers.weixin.qq.com/doc/offiaccount/OA_Web_Apps/JS-SDK.html

实现流程:

一、 公众号配置

1.JS安全域名配置:登陆微信公众平台:公众号设置 -> 功能设置 -> JS安全域名,域名写到根域名就行,把下载的txt文件放到域名对应的根目录下

微信开发之JS-SDK + PHP实现录音、上传、语音识别,

 

 2.配置ip白名单

微信开发之JS-SDK + PHP实现录音、上传、语音识别,

 

 

 

 

二、代码展示

1.前端代码

用到了’startRecord’, ‘stopRecord’, ‘playVoice’, ‘uploadVoice’, ‘translateVoice’五个接口,先调用 startRecord 开始录音,再调用 stopRecord 停止录音,会返回一个音频的本地Id,把录音追加的Html录音列表中,方便播放录音,使用 playVoice 播放录音列表中的录音,再使用 uploadVoice 把录音上传到微信服务器上,会返回微信服务器上的serverId(感觉上传录音没有使用到),通过使用本地音频id去识别语音

DOCTYPE html> <html> <head>     <title>语音识别title> <meta http-equiv="X-UA-Compatible" content="IE=edge,chrome=1"> <meta name="viewport" content="> <script type="text/Javascript" src="/static/index/js/jquery.js">script> <script src="http://res2.wx.qq.com/open/js/jweixin-1.6.0.js">script> <link rel="stylesheet" type="text/css" href="/static/index/layui/css/layui.css">        <style>           button{               height: 40px;               width: 120px;               margin: 25px;           }           #ul{               margin-top: 15px;               height: 40px;               line-height: 40px;               text-align: center;               padding: 5px;           }           #ul li{               width: 80%;           }           #ullist button{             width:98%;             height:40px;             border-radius:5;             text-align: center;             margin: 5px;         }        style> head> <body>     <div class="container" style="width:100%">         <div class="row">             <ul class="list-unstyled" id="ullist">                              ul>         div>         <div id="btn" class="navbar-fixed-bottom" style="user-select:none:align-content:center">             <center>                 <button id="talk_btn" type="button" class="layui-btn">录 音button>                 <button id="uploadVoice" type="button" class="layui-btn layui-btn-normal">上传 录音button><br>                 <button id="translateVoice" type="button" class="layui-btn layui-btn-danger" style="width:90%;">语音 识别button><br>             center>         div>     div>      <script type="text/Javascript">      // 全局变量     var recordTimer = 300;     var voice={                   localId:'',                   serverId:''               }          wx.config({         debug: false,         appId: '{$signPackage.appId}',         timestamp: {$signPackage.timestamp},         nonceStr: '{$signPackage.nonceStr}',         signature: '{$signPackage.signature}',         jsApiList: [           // 所有要调用的 API 都要加到这个列表中           'startRecord', 'stopRecord', 'playVoice', 'uploadVoice', 'translateVoice'         ]       });              // 在这里调用 API     wx.ready(function () {         var START;         var END;                  // 开始录音         $("#talk_btn").on('touchstart',function (event) {             // console.log(event)             event.preventDefault();             START = new Date().getTime();              // 延迟后录音,避免误操作             recordTimer = setTimeout(function () {                  wx.startRecord({                     success:function () {                         // 授权录音                         localStorage.rainAllowRecord = 'true';                     },                     cancel:function () {                         console.log('用户拒绝了录音');                     }                 });             },300)         });                  //松手结束录音         $('#talk_btn').on('touchend', function(event){             event.preventDefault();             END = new Date().getTime();                          if((END - START) < 3000){                 END = 0;                 START = 0;                 alert('录音时间不能少于3秒');                 //小于300ms,不录音                 clearTimeout(recordTimer);             }else{                                  var mytime = new Date().toLocaleTimeString();  //获取当前时间                                  wx.stopRecord({                   success: function (res) {                                            voice.localId = res.localId;                     console.log(voice.localId)                     var str="
  • "; $("#ullist").append(str);//显示到列表 }, fail: function (res) { alert(JSON.stringify(res)); } }); } }); }); wx.error(function (res) { console.log(res) }); //list播放语音 $("ul").on("click", "li", function() { var audioid = $(this).attr("audioid"); wx.playVoice({ localId: audioid }); }) // 上传语音 $("#uploadVoice").click(function(){ //调用微信的上传录音接口把本地录音先上传到微信的服务器 wx.uploadVoice({ localId:voice.localId, // 需要上传的音频的本地ID,由stopRecord接口获得 isShowProgressTips: 1, // 默认为1,显示进度提示 success:function(res){ if(res.errMsg == 'uploadVoice:ok'){ voice.serverId = res.serverId alert('录音上传成功'); }else{ alert(res.errMsg) } } }) }) // 语音识别 $("#translateVoice").click(function(){ wx.translateVoice({ localId:voice.localId, // 需要识别的音频的本地Id,由录音相关接口获得 isShowProgressTips:1, // 默认为1,显示进度提示 success:function(res){ console.log(res) if(res.errMsg == "translateVoice:ok"){ alert(res.translateResult); // 语音识别的结果 }else{ alert(res.errMsg) } } }) }) script> body> html>

    后端代码(php

    Wechat.php 此类主要是获取accessToken和jsapiTicket

    php namespace appindexcontroller; use thinkController;  /**  * 微信类  */ class Wechat extends Controller {      protected  $APPID = 'XXXXXXXXXXXXX';     protected  $APPSECRET = 'xxxxxxxxxxxxxxxxxx';      /**     * 微信服务器配置时 验证token的url     */     public function checkToken()     {         header("Content-type: text/html; charset=utf-8");          //1.将timestamp,nonce,toke按字典顺序排序         $timestamp = $_GET['timestamp'];         $nonce = $_GET['nonce'];         $token = 'asd123456zxc';         $signature = $_GET['signature'];         $array = array($timestamp,$nonce,$token);         //2.将排序后的三个参数拼接之后用sha1加密         $tmpstr = implode('',$array);         $tmpstr = sha1($tmpstr);         //3.将加密后的字符串与signature进行对比,判断该请求是否来自微信         if($tmpstr == $signature){             echo $_GET['echostr'];             exit;         }     }      /**     * curl请求      */     public function http_curl($url, $type = 'get', $res = 'json', $arr = ''){       $cl = curl_init();       curl_setopt($cl, CURLOPT_URL, $url);       curl_setopt($cl, CURLOPT_RETURNTRANSFER, 1);       curl_setopt($cl, CURLOPT_SSL_VERIFYPEER, false);       curl_setopt($cl, CURLOPT_SSL_VERIFYHOST, false);       if($type == 'post'){         curl_setopt($cl, CURLOPT_POST, 1);         curl_setopt($cl, CURLOPT_POSTFIELDS, $arr);       }       $output = curl_exec($cl);       curl_close($cl);       return json_decode($output, true);       if($res == 'json'){         if( curl_error($cl)){           return curl_error($cl);         }else{           return json_decode($output, true);         }       }     }      /**      * 获取 AccessToken      */     public function getAccessToken()     {         $url = "https://api.weixin.qq.com/cgi-bin/token?grant_type=client_credential&appid=".$this->APPID."&secret=".$this->APPSECRET;          // 先判断 access_token 文件里的token是否过期,没过期继续使用,过期就更新         $data = json_decode($this->get_php_file(ROOT_PATH."public".DS."wxtxt".DS."access_token.txt"));         // 过期 更新         if ($data->expire_time <time()) {                          $res = $this->http_curl($url);             $access_token = $res['access_token'];             if ($access_token) {                 // 在当前时间戳的基础上加7000s (两小时)                 $data->expire_time = time() + 7000;                 $data->access_token = $res['access_token'];                 $this->set_php_file(ROOT_PATH."public".DS."wxtxt".DS."access_token.txt",json_encode($data));             }         }else{             // 未过期 直接使用             $access_token = $data->access_token;         }         return $access_token;     }            /**      * 获取 JsApiTicket      */       public function getJsApiTicket()       {           // 先判断 jsapi_ticket是否过期 没过期继续使用,过期就更新           $data = json_decode($this->get_php_file(ROOT_PATH."public".DS."wxtxt".DS."jsapi_ticket.txt"));            if ($data->expire_time <time()) {               // 过期 更新               $accessToken = $this->getAccessToken();               $url = "https://api.weixin.qq.com/cgi-bin/ticket/getticket?type=jsapi&access_token=$accessToken";               $res = $this->http_curl($url);               $ticket = $res['ticket'];               if ($ticket) {                   $data->expire_time = time() + 7000;                   $data->jsapi_ticket = $ticket;                   $this->set_php_file(ROOT_PATH."public".DS."wxtxt".DS."jsapi_ticket.txt",json_encode($data));               }           }else{               $ticket = $data->jsapi_ticket;           }           return $ticket;       }       // 获取存储文件中的token ticket     private function get_php_file($filename) {         return trim(file_get_contents($filename));       }       // 把token ticket 存储到文件中       private function set_php_file($filename, $content) {         $fp = fopen($filename, "w");         fwrite($fp,  $content);         fclose($fp);       }  }

    Wxmedia.php  此类是返回语音识别的配置信息

    php namespace appindexcontroller; use thinkController; use appindexcontrollerWechat;  /**  * 微信语音识别  */ class Wxmedia extends Wechat {      /**      * 语音识别      */     public function index()     {         $signPackage = json_decode($this->getSignPackage(),true);              $this->assign('signPackage',$signPackage);         return $this->fetch();     }      /**      * 生成签名      */     public function getSignPackage()      {          // 实例化微信操作类         $wx = new Wechat();          // 获取 ticket         $jsapiTicket = $wx->getJsApiTicket();          // 注意 URL 一定要动态获取,不能 hardcode.         $protocol = (!empty($_SERVER['HTTPS']) && $_SERVER['HTTPS'] !== 'off' || $_SERVER['SERVER_PORT'] == 443) ? "https://" : "http://";         // 当前页面的url         $url = "$protocol$_SERVER[HTTP_HOST]$_SERVER[REQUEST_URI]";          $timestamp = time();    //生成签名的时间戳         $nonceStr = $this->createNonceStr();    //生成前面的随机串          // 这里参数的顺序要按照 key 值 ASCII 码升序排序         $string = "jsapi_ticket=$jsapiTicket&nOncestr=$nonceStr×tamp=$timestamp&url=$url";         // 对string进行sha1加密         $signature = sha1($string);          $signPackage = array(           "appId"     => $wx->APPID,           "nonceStr"  => $nonceStr,           "timestamp" => $timestamp,           "url"       => $url,           "signature" => $signature,           "rawString" => $string         );         return json_encode($signPackage);      }      /**      * 生成签名的随机串      */     private function createNonceStr($length = 16) {         $chars = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789";         $str = "";         for ($i = 0; $i <$length; $i++) {           $str .= substr($chars, mt_rand(0, strlen($chars) - 1), 1);         }         return $str;     }      }

     

    www.dengb.comtruehttp://www.dengb.com/PHPjc/1401234.htmlTechArticle微信开发之JS-SDK + PHP实现录音、上传、语音识别, 先看效果图:先录音,录音成功之后,把录音追加到列表,点击列表可以播放;录音完成…

    —-想了解更多的php相关异常处理怎么解决关注<编程笔记>


    推荐阅读
    • CSS3选择器的使用方法详解,提高Web开发效率和精准度
      本文详细介绍了CSS3新增的选择器方法,包括属性选择器的使用。通过CSS3选择器,可以提高Web开发的效率和精准度,使得查找元素更加方便和快捷。同时,本文还对属性选择器的各种用法进行了详细解释,并给出了相应的代码示例。通过学习本文,读者可以更好地掌握CSS3选择器的使用方法,提升自己的Web开发能力。 ... [详细]
    • javascript  – 概述在Firefox上无法正常工作
      我试图提出一些自定义大纲,以达到一些Web可访问性建议.但我不能用Firefox制作.这就是它在Chrome上的外观:而那个图标实际上是一个锚点.在Firefox上,它只概述了整个 ... [详细]
    • 如何在服务器主机上实现文件共享的方法和工具
      本文介绍了在服务器主机上实现文件共享的方法和工具,包括Linux主机和Windows主机的文件传输方式,Web运维和FTP/SFTP客户端运维两种方式,以及使用WinSCP工具将文件上传至Linux云服务器的操作方法。此外,还介绍了在迁移过程中需要安装迁移Agent并输入目的端服务器所在华为云的AK/SK,以及主机迁移服务会收集的源端服务器信息。 ... [详细]
    • 本文介绍了前端人员必须知道的三个问题,即前端都做哪些事、前端都需要哪些技术,以及前端的发展阶段。初级阶段包括HTML、CSS、JavaScript和jQuery的基础知识。进阶阶段涵盖了面向对象编程、响应式设计、Ajax、HTML5等新兴技术。高级阶段包括架构基础、模块化开发、预编译和前沿规范等内容。此外,还介绍了一些后端服务,如Node.js。 ... [详细]
    • 本文介绍了Python高级网络编程及TCP/IP协议簇的OSI七层模型。首先简单介绍了七层模型的各层及其封装解封装过程。然后讨论了程序开发中涉及到的网络通信内容,主要包括TCP协议、UDP协议和IPV4协议。最后还介绍了socket编程、聊天socket实现、远程执行命令、上传文件、socketserver及其源码分析等相关内容。 ... [详细]
    • VScode格式化文档换行或不换行的设置方法
      本文介绍了在VScode中设置格式化文档换行或不换行的方法,包括使用插件和修改settings.json文件的内容。详细步骤为:找到settings.json文件,将其中的代码替换为指定的代码。 ... [详细]
    • 如何使用Java获取服务器硬件信息和磁盘负载率
      本文介绍了使用Java编程语言获取服务器硬件信息和磁盘负载率的方法。首先在远程服务器上搭建一个支持服务端语言的HTTP服务,并获取服务器的磁盘信息,并将结果输出。然后在本地使用JS编写一个AJAX脚本,远程请求服务端的程序,得到结果并展示给用户。其中还介绍了如何提取硬盘序列号的方法。 ... [详细]
    • 安卓select模态框样式改变_微软Office风格的多端(Web、安卓、iOS)组件库——Fabric UI...
      介绍FabricUI是微软开源的一套Office风格的多端组件库,共有三套针对性的组件,分别适用于web、android以及iOS,Fab ... [详细]
    • 本文介绍了在Vue项目中如何结合Element UI解决连续上传多张图片及图片编辑的问题。作者强调了在编码前要明确需求和所需要的结果,并详细描述了自己的代码实现过程。 ... [详细]
    • 本文讨论了在openwrt-17.01版本中,mt7628设备上初始化启动时eth0的mac地址总是随机生成的问题。每次随机生成的eth0的mac地址都会写到/sys/class/net/eth0/address目录下,而openwrt-17.01原版的SDK会根据随机生成的eth0的mac地址再生成eth0.1、eth0.2等,生成后的mac地址会保存在/etc/config/network下。 ... [详细]
    • 本文讨论了在手机移动端如何使用HTML5和JavaScript实现视频上传并压缩视频质量,或者降低手机摄像头拍摄质量的问题。作者指出HTML5和JavaScript无法直接压缩视频,只能通过将视频传送到服务器端由后端进行压缩。对于控制相机拍摄质量,只有使用JAVA编写Android客户端才能实现压缩。此外,作者还解释了在交作业时使用zip格式压缩包导致CSS文件和图片音乐丢失的原因,并提供了解决方法。最后,作者还介绍了一个用于处理图片的类,可以实现图片剪裁处理和生成缩略图的功能。 ... [详细]
    • 如何查询zone下的表的信息
      本文介绍了如何通过TcaplusDB知识库查询zone下的表的信息。包括请求地址、GET请求参数说明、返回参数说明等内容。通过curl方法发起请求,并提供了请求示例。 ... [详细]
    • 本文记录了在vue cli 3.x中移除console的一些采坑经验,通过使用uglifyjs-webpack-plugin插件,在vue.config.js中进行相关配置,包括设置minimizer、UglifyJsPlugin和compress等参数,最终成功移除了console。同时,还包括了一些可能出现的报错情况和解决方法。 ... [详细]
    • Java学习笔记之使用反射+泛型构建通用DAO
      本文介绍了使用反射和泛型构建通用DAO的方法,通过减少代码冗余度来提高开发效率。通过示例说明了如何使用反射和泛型来实现对不同表的相同操作,从而避免重复编写相似的代码。该方法可以在Java学习中起到较大的帮助作用。 ... [详细]
    • 小程序自动授权和手动接入的方式及操作步骤
      本文介绍了小程序支持的两种接入方式:自动授权和手动接入,并详细说明了它们的操作步骤。同时还介绍了如何在两种方式之间切换,以及手动接入后如何下载代码包和提交审核。 ... [详细]
    author-avatar
    只因为汰假_汰傻_615
    这个家伙很懒,什么也没留下!
    PHP1.CN | 中国最专业的PHP中文社区 | DevBox开发工具箱 | json解析格式化 |PHP资讯 | PHP教程 | 数据库技术 | 服务器技术 | 前端开发技术 | PHP框架 | 开发工具 | 在线工具
    Copyright © 1998 - 2020 PHP1.CN. All Rights Reserved | 京公网安备 11010802041100号 | 京ICP备19059560号-4 | PHP1.CN 第一PHP社区 版权所有