/// <summary> /// 释放Session /// </summary> /// <param name="sessionId">指定的sessionId</param> public static void SessionDispose(string sessionId) { //清空当前session语义槽 SemanticsSlot dd = null; _SemanticsDic.TryRemove(sessionId, out dd); }
/// <summary> /// 接收到请求过来的消息,再开始发送向所有nlp多线程发送消息 /// </summary> /// <param name="session">接收客户端session</param> /// <param name="body.questions">接收消息内容</param> public static void ProcessingRequest(SoundBodyRequest body) { try { log.Info($"--------------------------开始向各个NLP发送问题: {body.questions} --------------------------"); if (body.sourceId == null) { body.sourceId = ""; } //添加当前请求到语义槽 SemanticsSlot semanticsSlot = new SemanticsSlot() { SessionId = body.sessionId, DeviceId = body.deviceId, Questions = body.questions, SourceId = body.sourceId, NlpAnswers = new List <NlpAnswers>(), Answertimes = 0, State = 0 }; //创建语义槽 _SemanticsDic.TryAdd(body.sessionId, semanticsSlot); //超时检测标识 CancellationTokenSource cts = new CancellationTokenSource(); //多线程集合 List <Task> taskList = new List <Task>(); TaskFactory taskFactory = new TaskFactory(); var type = typeof(INlp); var types = AppDomain.CurrentDomain.GetAssemblies() .SelectMany(a => a.GetTypes().Where(t => t.GetInterfaces().Contains(typeof(INlp)))) .ToArray(); INlps = types.Count();//语义槽应该放入个数 foreach (var v in types) { if (v.IsClass) { taskList.Add(taskFactory.StartNew(() => { try { //开始发送消息,并接收返回的语义 NlpAnswers _NlpAnswers = (Activator.CreateInstance(v) as INlp).SendMsg(body); //如果线程没有被取消,放入语义槽 if (!cts.IsCancellationRequested) { //过滤异步 if (_NlpAnswers != null) { _SemanticsDic[body.sessionId].Answertimes += 1; lock (_lock) { //过滤"" if (_NlpAnswers.Answers != "") { _SemanticsDic[body.sessionId].NlpAnswers.Add(_NlpAnswers); log.Info($"{body.questions} {_SemanticsDic[body.sessionId].Answertimes} {v.Name} 入槽内容: { _NlpAnswers.Answers.Replace("\r\n","")}"); } else { log.Info($"{body.questions} {_SemanticsDic[body.sessionId].Answertimes} {v.Name} 返回内容为空"); } } } } else { log.Info($"{body.questions} {v.Name} 超时线程取消未入槽!"); } } catch (Exception ex) { log.Info($"开始向{v.Name}发送消息异常:{ex.Message}"); } }, cts.Token)); } } //到了1.5秒还没有全部执行的,取消线程并返回 taskList.Add(Task.Delay(1500).ContinueWith(t => { //如果语义槽为空不再执行 if (_SemanticsDic.ContainsKey(body.sessionId)) { //如果当前语义槽标识位为State=0,则表示可以继续执行 if (_SemanticsDic[body.sessionId].State == 0) { //把当前session状态设置false _SemanticsDic[body.sessionId].State = -1; lock (_lock) { cts.Cancel(); } //如果语义槽不为null再继续执行 if (_SemanticsDic[body.sessionId] != null) { //返回语义结果 AIControler.GetAIAnswers(_SemanticsDic[body.sessionId], "超时"); } } } })); } catch (Exception ex) { log.Info($"发送消息异常:{ex.Message}"); } }
/// <summary> ///调用第三方语义排序API,对于语义进行排序 /// </summary> /// <param name="_SemanticsDictionary">传递语义槽</param> /// <returns>排序结果</returns> public static void GetAIAnswers(SemanticsSlot _SemanticsSlot, string type) { try { string sessionId = _SemanticsSlot.SessionId; string deviceId = _SemanticsSlot.DeviceId; string questions = _SemanticsSlot.Questions; string sourceid = _SemanticsSlot.SourceId; log.Info($"{questions} 执行方式:{type} 返回次数:{_SemanticsSlot.Answertimes} 语义槽数量:{_SemanticsSlot.NlpAnswers.Count} "); //过滤掉所有空 var Answers = _SemanticsSlot.NlpAnswers.OrderBy(t => t.Level);//.Where(t => !string.IsNullOrEmpty(t.Answers)) if (Answers.Count() > 0) { foreach (var item in Answers) { string code = item.Code; string answers = item.Answers; //优先返回基础nlp if (code == "BaseNlp") { NlpControler.BackAnswers(sessionId, deviceId, questions, "2011", answers, BaiduSDK.Tts(answers));// 2011播放url内容,播放完自动唤醒 break; } //返回智能家居nlp,不带的设备无法识别@ else if (code == "SmartHomeNlp" && !answers.Contains("2014@")) { if (answers.Split('@').Length == 2) { string action = answers.Split('@')[0]; string req = answers.Split('@')[1]; NlpControler.BackAnswers(sessionId, deviceId, questions, action, answers, "");//根据@中的action返回 break; } else { NlpControler.BackAnswers(sessionId, deviceId, questions, "2020", answers, "");//2020播放响应效果音可持续交流 break; } } else { //设备无法识别的时候,优先返回音响自带的结果(不为空的情况下) var item2 = _SemanticsSlot.NlpAnswers.Where(t => t.Code == "SoundNlp").FirstOrDefault(); if (sourceid != "mengdou") { ///执行百度自己请求 NlpControler.BackAnswers(sessionId, deviceId, questions, "2010", "无法识别您说的意思", ""); break; } else if (item2 != null) { if (answers.Contains("service\":\"musicX") || answers.Contains("service\":\"news") || answers.Contains("service\":\"story") || answers.Contains("service\":\"joke")) { NlpControler.BackAnswers(sessionId, deviceId, questions, "2025", item2.Answers, "");//2025主机不返回,超时,播放错误音,其实主机已经在播放音乐 break; } else { NlpControler.BackAnswers(sessionId, deviceId, questions, "2011", item2.Answers, BaiduSDK.Tts(item2.Answers));// 2011播放url内容,播放完自动唤醒 break; } } else { NlpControler.BackAnswers(sessionId, deviceId, questions, "2014", "无法识别您说的意思", ""); //NlpControler.BackAnswers(sessionId, deviceId, questions, "2014", "无法识别您说的意思", BaiduSDK.mp3Fail); break; } } } } else { if (sourceid != "mengdou") { ///执行百度自己请求 NlpControler.BackAnswers(sessionId, deviceId, questions, "2010", "无法识别您说的意思", ""); } else { NlpControler.BackAnswers(sessionId, deviceId, questions, "2014", "无法识别您说的意思", ""); } //NlpControler.BackAnswers(sessionId, deviceId, questions, "2014", "无法识别您说的意思", BaiduSDK.mp3Fail); } } catch (Exception ex) { log.Info($"{_SemanticsSlot.Questions} AI处理异常: {ex.Message}"); } }