微信小程序实现图林机器人聊天和百度AI语音识别的简单人工客服

用微信小程序实现简单的人工客服

最近在做软件工程的课程设计,选择性的做了微信小程序的简单的人工客服。在这里对该课程设计的原理和实现进行一个讲解,也算做一个总结和笔记,方便自己以后查看、复习和帮助大家的学习。


  • 工具:微信开发者工具、Eclipse、Tomcat、图林机器人V2版、百度AI语音识别
  • 实现原理与过程
    (1)微信小程序获取用户输入的文字、图片或语音消息,发送给Tomcat服务器;
    (2)Tomcat服务器接收到消息后交给对应的servel进行处理。因为微信小程序发送文字消息可以使用GET方式,发送文件必须使用POST方式,所以只用一个Sevlet就可以进行处理。
    (3)Servlet获取GET方式的请求,则调用doGet方法,获取请求携带的用户消息,发送给图林机器人,得到图林机器人的随机回复消息后,返回给微信小程序,显示给用户;
    (4)Servlet获取POST方式的请求,则调用doPost方法,获取微信小程序上传的文件消息,先保存在本地的临时文件夹中,在判断是图片消息还是语音消息。如果是图片消息,仅保存在本地,不做任何处理,只返回给微信小程序一个文字回复,如:“图片我看不懂,你自己看”;如果是语音消息,则发送给百度AI进行语音识别,识别成功,在将结果发送给图林机器人,取得图林机器人的回复后,返回给微信小程序,显示给用户;识别失败,则返回给微信小程序一个文字回复,如:“太吵了,听不清楚。。”;

  • 实现过程

(1)服务器实现:
- 项目结构:
chat
- 导入jar包到lib文件夹下:
lib

- 新建web项目,创建一个Servelt(图中的MyServlet):

servlet部分

import java.io.File;
import java.io.IOException;
import java.io.PrintWriter;
import java.util.List;
import java.util.UUID;import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;import org.apache.commons.fileupload.FileItem;
import org.apache.commons.fileupload.FileUploadException;
import org.apache.commons.fileupload.disk.DiskFileItemFactory;
import org.apache.commons.fileupload.servlet.ServletFileUpload;@WebServlet("/MyServlet")
public class MyServlet extends HttpServlet{private static final long serialVersionUID = 1L;private static final String URL = "http://openapi.tuling123.com/openapi/api/v2";private Tuling tuling = new Tuling();//进行文本聊天protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {request.setCharacterEncoding("utf-8");response.setContentType("text/html;charset=utf-8");String reqMes = request.getParameter("reqMes").toString().trim();//		System.out.println(reqMes);//将用户发送过来的消息转换成JSON格式String reqJson = tuling.getReqJson(reqMes);//发送消息到图林机器人,获取图林机器人的回复String sendPost = tuling.sendPost(URL, reqJson);//获取图林机器人回复的JSON消息中的主要回复内容String string = tuling.getResultMeg("[" + sendPost +"]");System.out.println("get提问: "+reqMes);System.out.println("回复: "+string);//返回值给小程序//将图林回复的消息string返回给小程序PrintWriter out = response.getWriter();out.write(string);out.flush();out.close();//		response.sendRedirect("index.jsp");}//文件上传protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {System.out.println("上传文件");request.setCharacterEncoding("utf-8");response.setContentType("text/html;charset=utf-8");response.setCharacterEncoding("utf-8");//调用下面的保存文件的方法uploadFile(request, response);//   在uploadFile方法中实现了上述的   实现过程与原理  中的第四步		//语音   小程序API录音后Silk格式转码PCM}//获取微信小程序发送的文件消息,并进行处理private void uploadFile(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException{//得到服务器的真是磁盘路径String realPath = this.getServletContext().getRealPath("/");File file = new File(realPath+"upload");System.out.println(realPath);//要返回给微信小程序的结果String string = "";//磁盘文件工厂DiskFileItemFactory factory  = new DiskFileItemFactory();factory.setRepository(file);//设置临时文件存放的位置factory.setSizeThreshold(1024*1024*10);//上传文件的大小5M//servlet文件上传对象ServletFileUpload upload = new ServletFileUpload(factory);try {//将普通的request请求转成FileItem的列表集合List<FileItem> list = upload.parseRequest(request);FileItem uploadFile = null;//增强型for循环for(FileItem item : list) {if(item.isFormField()) {//是普通表单元素}else {//否则说明是文件上传uploadFile = item;}}//获取文件后缀String name = uploadFile.getName();String suffix = name.substring(name.lastIndexOf("."));//做真正的上传,将临时文件 存储到 指定磁盘位置//图片或语音要保存的绝对路径String skil = "";if(".silk".equals(suffix)) {skil = "该语音文件要保存的绝对路径"+suffix;}else {// 图片文件要保存的绝对路径skil = (file+"\\"+UUID.randomUUID()+"."+suffix);}System.out.println(skil);// 按保存的文路径创建文件File saveFile = new File(skil);//数据写入保存的文件try {uploadFile.write(saveFile);} catch (Exception e) {e.printStackTrace();}// 分别对图片或语音消息进行处理if(".silk".equals(suffix)) {//处理语音消息System.out.println("这是一个语音");Sample sample = new Sample();string = sample.checkMeg();System.out.println(string);}else {System.out.println("这是一个图片");string = "图片自己看,我看不懂";}} catch (FileUploadException e) {e.printStackTrace();} finally {//  对语音或图片进行不同的回复处理,返回给微信小程序if(!"太吵了,听不清楚..".equals(string) && !"图片自己看,我看不懂".equals(string)) {System.out.println("将调用图林机器人");System.out.println("get提问: "+string);String reqJson = tuling.getReqJson(string);String sendPost = tuling.sendPost(URL, reqJson);string = tuling.getResultMeg("[" + sendPost +"]");System.out.println("回复: "+string);}//返回值给小程序PrintWriter out = response.getWriter();out.write(string);out.flush();out.close();}}
}

图灵机器人部分:

详细解析,查看此文章

import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.io.PrintWriter;
import java.net.HttpURLConnection;
import java.net.URL;
import java.net.URLConnection;import net.sf.json.JSONArray;
import net.sf.json.JSONObject;public class Tuling {private static final String apikey ="图林机器人apikey";private static final String uid = "用户id";/*** 将输入的信息转换为json对象* @param reqMes* @return*/public String getReqJson(String reqMes) {//请求jsonJSONObject reqJson = new JSONObject();//输入类型int reqType = 0;//输入信息json,如文本,图片JSONObject perception = new JSONObject();//输入的信息JSONObject inputText = new JSONObject();inputText.put("text", reqMes);perception.put("inputText",inputText);//用户信息JSONObject userInfo = new JSONObject();userInfo.put("apiKey", apikey);userInfo.put("userId", uid);reqJson.put("reqType", reqType);reqJson.put("perception", perception);reqJson.put("userInfo", userInfo);return reqJson.toString();}/*** 发送请求* @param url* @param reqJson* @return*/public String sendPost(String url, String reqJson) {String status = "";String responseStr = "";PrintWriter out = null;BufferedReader in = null;try {URL realUrl = new URL(url);//打开url连接URLConnection urlCon = realUrl.openConnection();HttpURLConnection httpUrlConnection = (HttpURLConnection) urlCon;//设置请求属性httpUrlConnection.setRequestProperty("Content-Type", "application/json");httpUrlConnection.setRequestProperty("x-adviewrtb-version", "2.1");//发送post请求必须设置一下两行httpUrlConnection.setDoOutput(true);httpUrlConnection.setDoInput(true);//获取URLConnection对象对应的输出流out = new PrintWriter(httpUrlConnection.getOutputStream());//发送请求参数out.write(reqJson);//flush输出流的缓冲out.flush();httpUrlConnection.connect();//定义BufferedReader输入流来读取URL的响应in = new BufferedReader(new InputStreamReader(httpUrlConnection.getInputStream()));String line = "";while((line = in.readLine())!=null) {responseStr += line;}status = new Integer(httpUrlConnection.getResponseCode()).toString();httpUrlConnection.disconnect();} catch (IOException e) {System.out.println("发送post请求出现异常");e.printStackTrace();} finally {try {if(out != null) {out.close();}if(in != null) {in.close();}} catch (IOException e) {e.printStackTrace();}}return responseStr;}/*** JSONObject将字符串转换为json,取到消息信息* @param tulingStr* @return*/public String getResultMeg(String tulingStr) {JSONObject object = null;String strResult = "";JSONArray jsonArray = new JSONArray(tulingStr);for(int i = 0; i < jsonArray.length(); i++) {//System.out.println("jsonArray: " + jsonArray.getJSONObject(i));object = jsonArray.getJSONObject(i);strResult = object.getString("results");//System.out.println("results: "+string);}JSONArray jsonArray1 = new JSONArray(strResult);for(int i = 0; i < jsonArray1.length(); i++) {//System.out.println("jsonArray1: " + jsonArray1.getJSONObject(i));object = jsonArray1.getJSONObject(i);strResult = object.getString("values");//System.out.println("values: "+string);}JSONArray jsonArray2 = new JSONArray("["+strResult+"]");for(int i = 0; i < jsonArray2.length(); i++) {//System.out.println("jsonArray2: " + jsonArray2.getJSONObject(i));object = jsonArray2.getJSONObject(i);strResult = object.getString("text");//System.out.println("text: "+string);}return strResult;}}

百度AI语音识别部分:

DeCoder类,用来进行语音格式的转换详细信息,查看此文章

import java.io.IOException;import org.nutz.lang.Encoding;
import org.nutz.lang.Lang;public class DeCoder {/*** 解码为pcm格式* @param silk * @param pcm * @return*/public static boolean getPcm(String silk,String pcm){boolean flag = true;String cmd="cmd.exe /c C:\\silk_v3_decoder.exe "+silk+" "+pcm+" -quiet";System.out.println("转码到pcm...");try{StringBuilder msg = Lang.execOutput(cmd, Encoding.CHARSET_GBK);System.out.println(msg);}catch (IOException e){e.printStackTrace();flag = false;}return flag;}/*** 转码为MP3格式* @param pcm * @param mp3 * @return*/public static boolean getMp3(String pcm,String mp3){boolean flag = true;String command = "cmd.exe /c C:\\ffmpeg.exe -y -f s16le -ar 24000 -ac 1 -i "+pcm+" "+mp3+" ";System.out.println("转码到mp3...");try {StringBuilder sb = Lang.execOutput(command, Encoding.CHARSET_GBK);System.out.println(sb);} catch (IOException e) {e.printStackTrace();flag = false;}return flag;}
}

Sample类,发送消息给百度AI,进行语音识别详细信息,查看此官方文档

import org.json.JSONObject;import com.baidu.aip.speech.AipSpeech;import net.sf.json.JSONArray;
import net.sf.json.JSONException;public class Sample {//设置APPID/AK/SK   都填写自己的public static final String APP_ID = "app_id";public static final String API_KEY = "app_key";public static final String SECRET_KEY = "secret_key";//进行语音格式转换和发送给百度AI进行语音识别public static String checkMeg() {//此路径详见DeCoder类String silk = "D:\\test.silk";String pcm = "D:\\test.pcm";String mp3 = "D:\\test.mp3";DeCoder deCoder = new DeCoder();boolean b = deCoder.getPcm(silk, pcm);System.out.println(b);if(b)deCoder.getMp3(pcm, mp3);String filePath = "D:\\test.pcm";String sendPost = sendPost(filePath);//post返回剪切好的字符串return sendPost;}//发送给百度AI进行语音识别,详见官方文档private static String sendPost(String filePath) {// 初始化一个AipSpeechAipSpeech client = new AipSpeech(APP_ID, API_KEY, SECRET_KEY);// 可选:设置网络连接参数client.setConnectionTimeoutInMillis(2000);client.setSocketTimeoutInMillis(60000);// 可选:设置代理服务器地址, http和socket二选一,或者均不设置
//        client.setHttpProxy("proxy_host", proxy_port);  // 设置http代理
//        client.setSocketProxy("proxy_host", proxy_port);  // 设置socket代理// 可选:设置log4j日志输出格式,若不设置,则使用默认配置// 也可以直接通过jvm启动参数设置此环境变量
//        System.setProperty("aip.log4j.conf", "path/to/your/log4j.properties");// 调用接口JSONObject res = client.asr(filePath, "pcm", 16000, null);String string = res.toString(2);System.out.println("返回JSON: "+string);//获取结果String resultMeg = getResultMeg("["+string+"]");
//        System.out.println(resultMeg);//剪切字符串int last = resultMeg.indexOf("\"]");String lastResult = resultMeg.substring(2, last);
//  		System.out.println(lastResult);//将剪切好的字符串返回return lastResult;}//对百度AI返回的结果进行解析,获取回复字段消息public static String getResultMeg(String tulingStr) {net.sf.json.JSONObject object = null;String strResult = "";JSONArray jsonArray = new JSONArray(tulingStr);for(int i = 0; i < jsonArray.length(); i++) {object = (net.sf.json.JSONObject) jsonArray.getJSONObject(i);try {strResult = object.getString("result");} catch (JSONException e) {
//				e.printStackTrace();strResult = "[\""+"太吵了,听不清楚.."+"\"]";}}return strResult;}
}

(2)微信小程序实现:
这部分我是直接使用的github的项目,只是做了功能部分的修改,直接下载导入微信开发者工具,修改servlet访问路径即可。下载地址:微信小程序实现,提取码:gnzo。导入时需要填入自己的测试码,不然不可以使用。切记哦!!


以上就是整个小项目的实现过程,难点在于图林机器人的跨域问题,还有语音格式的转换,需要注意一下。好啦,以上就是我对这个小项目的一个小的总结,希望可以帮助到你们。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.rhkb.cn/news/43531.html

如若内容造成侵权/违法违规/事实不符,请联系长河编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

Python实现语音识别(基于百度语音识别)

我是一名2016级电子信息工程的学生&#xff0c;这是第一次发博客&#xff0c;因为经常在这里查资料 &#xff0c;自己也应该贡献一点经验吧&#xff0c;也可以当是记录自己学习的过程吧。 最近在自学python&#xff0c;然后18年9月份正好python加入计算机二级&#xff0c;再然…

玩转百度语音识别,就是这么简单

http://www.cnblogs.com/bigdataZJ/p/SpeechRecognition.html 明后两天就是公司一年一度的Fedex Day了。我的理解就是技术界的头脑风暴&#xff0c;idea喷如泉涌的盛大节日。 对于这次活动每个人或者两三个人一组需要有个idea&#xff0c;针对当前的产品现状&#xff0c;提出自…

语音-小度自定义技能

文章目录 前言一、学习简介二、代码快速开发三、官网配置3.1 百度云CFC配置3.2 小度官网配置 四、测试4.1连接技能4.2 意图测试4.3 断开技能 前言 主要是为了记录下学习小度自定义技能的过程 一、学习简介 参考官网解释 自定义技能简介 二、代码快速开发 快速开发java 我…

人人都是绘画大师!微软必应接入DALL·E模型,文字生成图像!

机器之心编辑部 微软必应完善文字生成图像能力&#xff0c;Adobe 今日也发布 Firefly&#xff0c;杀入生成式 AI 这场游戏。 今晚实在是有些热闹。 一边英伟达 GTC 正在进行中&#xff0c;一边谷歌正式开放了 Bard 的测试&#xff0c;这里微软必应也不甘寂寞。 今日&#xff0c…

对比编程语言的四种错误处理方法,哪种才是最优方案?

△点击上方“Python猫”关注 &#xff0c;回复“1”领取电子书 作者&#xff1a;Andrea Bergia 译者&#xff1a;豌豆花下猫Python猫 英文&#xff1a;Error handling patterns 转载请保留作者及译者信息&#xff01; 错误处理是编程的一个基本要素。除非你写的是“hello world…

巴比特 | 元宇宙每日必读:不再盲目迷信硬件掘金,大厂XR集体后撤,业内人士建议多条腿走路,生态和内容才有更广阔市场...

摘要&#xff1a;据极点商业报道&#xff0c;元宇宙凉热之间&#xff0c;大厂集体收缩XR业务。是舆论定调的风口已过&#xff0c;还是如业内人士所言&#xff0c;进入理智探索时代&#xff1f;为何短短半年时间内&#xff0c;大厂们态度就发生了截然不同的变化&#xff1f;“与…

学会这些思维模型,窥见查理·芒格的致胜秘笈(二)

目录 导语 模型五&#xff1a;SCQA模型 模型六&#xff1a;问题树模型 模型七&#xff1a;MECE原则 模型八&#xff1a;SWOT分析 模型九&#xff1a;波特五力模型 模型十&#xff1a;波斯顿矩阵 导语 读者朋友们好&#xff0c;在我上一篇文章介绍了几个最核心和底层的模…

产品读书《穷查理宝典:查理.芒格智慧箴言录》

要通过提升自己&#xff0c;来强化对世界的感知&#xff0c;内在的能力才能增长&#xff0c;和世界的大趋势才能互相匹配。这种匹配度提高了&#xff0c;无论你是用来投资、创业&#xff0c;还是做其他事情&#xff0c;都会无往而不利。 查理芒格在书中反复强调的4点内容有&a…

芒格最新演讲:中国的水有些聪明人已经蹚进去了,时候到了更多人会进场

图文来源&#xff1a;雪球 译者&#xff1a;RanRan 我们在说某个人有常识的时候&#xff0c;我们其实是说&#xff0c;他具备平常人没有的常识。人们都以为具备常识很简单&#xff0c;其实很难。 2月14日&#xff0c;95岁的芒格参加了Daily Journal 公司年会&#xff0c;发表了…

站在大模型新风口的云知声:十一年创业之路引领智能语音技术变革

AGI的目标是实现人类般的通用智能&#xff0c;这意味着AI可以像人类一样理解任意通用任务&#xff0c;并以人类的智力水平执行完成。基本上&#xff0c;除了自我意识的生成&#xff0c;AGI就是人类对人工智能的终极梦想了。在AGI曙光照进现实之际&#xff0c;云知声化身为那位站…

在MT4上使用KDJ指标

KDJ指标就是随机指标&#xff0c;由K线、D线和J线这三条曲线共同构成&#xff0c;通过分析图表&#xff0c;我们可以得出&#xff0c;K、D、J分别用不同的颜色线条来表示&#xff0c;所谓的K线是指快速确认线&#xff0c;D线就是指慢速主干线&#xff0c;而J线则为方向明暗线。…

同花顺资金监测精鹰指标公式源码 通过资金监测强弱

使用方法&#xff1a; 指标不含未来,是通过资金监测强弱,资金是不会骗人 当红柱有粉色帽子或红柱上方金色线均表示资金流入 源代码&#xff1a; VAR1:VOL/((HIGH-LOW)*2-ABS(CLOSE-OPEN)); 主动买盘:IF(CLOSE>OPEN,VAR1*(HIGH-LOW),IF(CLOSE<OPEN,VAR1*((HIGH-OPEN)(…

django中使用auth.authenticate在用户名和密码都正确的情况下返回值依然为None的可能原因

毕业设计做了一个系统&#xff0c;其中涉及到用户修改密码&#xff0c;然后发现密码改完之后即使输入了也登不上去&#xff0c;最终定位到问题出在auth.authenticate上&#xff0c;它返回的是None&#xff0c;在csdn上找了好久&#xff0c;全都是说在创建的时候使用django自带的…

美国公司裁员潮可视化;GitHub + Kaggle + InfoQ:3份报告回顾中国开发者的2022 | ShowMeAI每周通讯 #005-01.07

这是ShowMeAI每周通讯的第5期。通讯聚焦AI领域本周热点&#xff0c;及其在各圈层泛起的涟漪&#xff1b;关注AI技术进步&#xff0c;并提供我们的商业洞察。欢迎关注与订阅&#xff01; 导读&#xff1a;2023年第1周&#xff0c;美国科技大厂的裁员信息&#xff0c;终于还是来了…

如何转换图片格式?教你三招一键轻松转换图片格式

之前有朋友跟我吐槽说&#xff0c;有时候保存到电脑上的图片原来是正常的&#xff0c;结果保存下来以后就打不开了&#xff0c;搞的他非常苦恼。其实这个问题也很好解决&#xff0c;一般这种问题都是由于图片格式导致的&#xff0c;只需要将图片格式转换成jpg、png等常见格式就…

手把手教你免费、批量转换HEIC图片到JPG

iPhone手机更新IOS11系统后&#xff0c;相机拍摄的文件格式为HEIC格式&#xff0c;很多软件都无法打开。找了半天也是各种收费&#xff0c;就比如某款软件居然收费&#xff0c;还有年费88块&#xff01;你们怎么好意思收费的&#xff1f; 要么就是在线的转换&#xff0c;一张张…

PS把变成人物照片插画效果

算不算插画不是很懂&#xff0c;又有点类似&#xff0c;效果就是下图的这样&#xff0c;使用陌鱼社区动作&#xff1a;简单时尚手绘人物插画效果PS动作&#xff0c;下面是一些效果图&#xff0c;喜欢的可以试一下 01、双击图案&#xff08;.pat&#xff09;&#xff0c;Adobe P…

通过python我实现了照片转化为动漫模式,媳妇儿再也不用愁没有好看的头像了~

​ 最近某音上的动漫特效特别火&#xff0c;很多人都玩着动漫肖像&#xff0c;我媳妇儿也不例外。看着她这么喜欢这个特效&#xff0c;我决定做一个图片处理工具&#xff0c;这样媳妇儿的动漫头像就有着落了。 编码 为了快速实现我们的目标&#xff0c;我们就不自己写图片处理程…

将照片转换成漫画风格的API推荐

这段时间休息的时候发现了一个很有意思的API——将照片转换成漫画风格API&#xff0c;是在 APISpace 这个接口服务平台发现的。它里面的很多接口都非常的好用&#xff0c;使用起来也很方便&#xff0c;所有的接口都可以提供免费的试用&#xff0c;有需要的同学可以去看看~ 效果…

APISpace 将照片转化成漫画风格API

APISpace 的 将照片转化成漫画风格API&#xff0c;会自动为你将照片转换成漫画风格&#xff0c;无须使用Photoshop 等图片编辑软件、无须任何技术基础。输入图片的url&#xff0c;即可得到漫画风格的图片。 APISpace 上面还多各种各样的API&#xff0c;包括常见的短信、物流、…