|
@@ -0,0 +1,743 @@
|
|
|
+# This files contains your custom actions which can be used to run
|
|
|
+# custom Python code.
|
|
|
+#
|
|
|
+# See this guide on how to implement these action:
|
|
|
+# https://rasa.com/docs/rasa/custom-actions
|
|
|
+
|
|
|
+
|
|
|
+# This is a simple example for a custom action which utters "Hello World!"
|
|
|
+
|
|
|
+# from typing import Any, Text, Dict, List
|
|
|
+#
|
|
|
+# from rasa_sdk import Action, Tracker
|
|
|
+# from rasa_sdk.executor import CollectingDispatcher
|
|
|
+
|
|
|
+
|
|
|
+import logging
|
|
|
+import json
|
|
|
+from datetime import datetime
|
|
|
+from typing import Any, Dict, List, Text, Optional
|
|
|
+import requests
|
|
|
+from neo4j import GraphDatabase
|
|
|
+from rasa_sdk import Action, Tracker
|
|
|
+from rasa_sdk.types import DomainDict
|
|
|
+from rasa_sdk.forms import FormValidationAction
|
|
|
+from rasa_sdk.executor import CollectingDispatcher
|
|
|
+from datetime import datetime, date, timedelta
|
|
|
+import jieba
|
|
|
+import jellyfish
|
|
|
+from .api import question_parser
|
|
|
+from .api import answer_search
|
|
|
+from .api import app
|
|
|
+import subprocess
|
|
|
+import datetime
|
|
|
+
|
|
|
+from rasa_sdk.events import (
|
|
|
+ SlotSet,
|
|
|
+ UserUtteranceReverted,
|
|
|
+ ConversationPaused,
|
|
|
+ EventType,
|
|
|
+)
|
|
|
+
|
|
|
+USER_INTENT_OUT_OF_SCOPE = "out_of_scope"
|
|
|
+
|
|
|
+logger = logging.getLogger(__name__)
|
|
|
+
|
|
|
+class FindTheCorrespondingFault_des(Action):
|
|
|
+ def name(self) -> Text:
|
|
|
+ return "FindTheCorrespondingFault_des"
|
|
|
+
|
|
|
+ def run(
|
|
|
+ self,
|
|
|
+ dispatcher: CollectingDispatcher,
|
|
|
+ tracker: Tracker,
|
|
|
+ domain: Dict[Text, Any]
|
|
|
+ ) -> List[Dict[Text, Any]]:
|
|
|
+ user_message = tracker.latest_message.get('text')
|
|
|
+ print("text", user_message)
|
|
|
+
|
|
|
+ # 获取故障实体
|
|
|
+ fault_des = tracker.get_slot('fault_des')
|
|
|
+ # 获取意图
|
|
|
+ intentions = tracker.get_intent_of_latest_message()
|
|
|
+ print(f"fault_des: {fault_des}")
|
|
|
+ print(f"Intentions: {intentions}")
|
|
|
+
|
|
|
+
|
|
|
+ # 连接到 Neo4j 数据库
|
|
|
+ try:
|
|
|
+ driver = GraphDatabase.driver("bolt://localhost:7687", auth=("neo4j", "fdx3081475970"))
|
|
|
+ except Exception as e:
|
|
|
+ dispatcher.utter_message(text=f"无法连接到 Neo4j 数据库: {e}")
|
|
|
+ return []
|
|
|
+
|
|
|
+ # 定义查询
|
|
|
+ query = """
|
|
|
+ MATCH (n: 故障描述)
|
|
|
+ RETURN n.name AS name
|
|
|
+ """
|
|
|
+
|
|
|
+ # 执行查询
|
|
|
+ names = []
|
|
|
+ try:
|
|
|
+ with driver.session() as session:
|
|
|
+ result = session.run(query)
|
|
|
+ names = [record["name"] for record in result]
|
|
|
+ except Exception as e:
|
|
|
+ dispatcher.utter_message(text=f"查询 Neo4j 数据库时出错: {e}")
|
|
|
+ driver.close()
|
|
|
+ return []
|
|
|
+
|
|
|
+ # 设置相似度阈值
|
|
|
+ threshold = 0.5
|
|
|
+
|
|
|
+ # 存储相似度和名称
|
|
|
+ similarity_scores = [(name, jellyfish.jaro_winkler_similarity(name, user_message)) for name in names]
|
|
|
+
|
|
|
+ # 过滤出相似度大于阈值的名称
|
|
|
+ filtered_similarities = [(name, score) for name, score in similarity_scores if score > threshold]
|
|
|
+
|
|
|
+ # 找出相似度最高的名称
|
|
|
+ highest_similarity_name = None
|
|
|
+ if filtered_similarities:
|
|
|
+ highest_similarity_name, highest_similarity_score = max(filtered_similarities, key=lambda x: x[1])
|
|
|
+ print(f"最高相似度的名称: {highest_similarity_name}")
|
|
|
+
|
|
|
+ # 如果找到了相似度高的名称,则用它替换原始的 fault_name
|
|
|
+ if highest_similarity_name is not None:
|
|
|
+ fault_des = highest_similarity_name
|
|
|
+
|
|
|
+ # 关闭 Neo4j 驱动连接
|
|
|
+ driver.close()
|
|
|
+
|
|
|
+ # 准备数据结构
|
|
|
+ if type(fault_des) != list:
|
|
|
+ data = {'args': {fault_des: ['fault_des']}, 'question_types': [intentions]}
|
|
|
+ else:
|
|
|
+ data = {'args': {fault_des[0]: ['fault_des']}, 'question_types': [intentions]}
|
|
|
+
|
|
|
+ parser = question_parser.QuestionParser()
|
|
|
+ searcher = answer_search.AnswerSearcher()
|
|
|
+ print(f"Data: {data}")
|
|
|
+ sqls = parser.parser_main(data) # 生成相关的查询语句
|
|
|
+ print(f"SQLs: {sqls}")
|
|
|
+ final_answer = searcher.search_main(sqls) # 查询相关内容
|
|
|
+ entity_lists = searcher.get_entity(sqls)
|
|
|
+ entity_str = json.dumps(entity_lists)
|
|
|
+ print(f"Entity Lists: {entity_str}")
|
|
|
+ print(f"Final Answer: {final_answer}")
|
|
|
+
|
|
|
+ # 进行判断 输出结果
|
|
|
+ if not final_answer:
|
|
|
+ dispatcher.utter_message(template='utter_out')
|
|
|
+ else:
|
|
|
+ if highest_similarity_name is not None and highest_similarity_score is not None:
|
|
|
+ match_info = (
|
|
|
+ f"当前实体的匹配数值为:{highest_similarity_score:.2f}\n"
|
|
|
+ f"根据当前的实体匹配结果的输出为:\n"
|
|
|
+ )
|
|
|
+ answer = match_info + '\n'.join(final_answer)
|
|
|
+ else:
|
|
|
+ answer = '\n'.join(final_answer)
|
|
|
+
|
|
|
+ # 发送最终答案和实体信息
|
|
|
+ dispatcher.utter_message(text=answer)
|
|
|
+ dispatcher.utter_message(text=f'{entity_lists}')
|
|
|
+
|
|
|
+ return [SlotSet('fault_des', entity_str)]
|
|
|
+
|
|
|
+class FindTheCorrespondingFault_hmc(Action):
|
|
|
+ def name(self) -> Text:
|
|
|
+ return "FindTheCorrespondingFault_hmc"
|
|
|
+
|
|
|
+ def run(
|
|
|
+ self,
|
|
|
+ dispatcher: CollectingDispatcher,
|
|
|
+ tracker: Tracker,
|
|
|
+ domain: Dict[Text, Any]
|
|
|
+ ) -> List[Dict[Text, Any]]:
|
|
|
+ user_message = tracker.latest_message.get('text')
|
|
|
+ print("text", user_message)
|
|
|
+
|
|
|
+ # 获取故障实体
|
|
|
+ fault_hmc = tracker.get_slot('fault_hmc')
|
|
|
+ # 获取意图
|
|
|
+ intentions = tracker.get_intent_of_latest_message()
|
|
|
+ print(f"Fault HMC: {fault_hmc}")
|
|
|
+ print(f"Intentions: {intentions}")
|
|
|
+
|
|
|
+
|
|
|
+ # 连接到 Neo4j 数据库
|
|
|
+ try:
|
|
|
+ driver = GraphDatabase.driver("bolt://localhost:7687", auth=("neo4j", "fdx3081475970"))
|
|
|
+ except Exception as e:
|
|
|
+ dispatcher.utter_message(text=f"无法连接到 Neo4j 数据库: {e}")
|
|
|
+ return []
|
|
|
+
|
|
|
+ # 定义查询
|
|
|
+ query = """
|
|
|
+ MATCH (n: HMC)
|
|
|
+ RETURN n.name AS name
|
|
|
+ """
|
|
|
+
|
|
|
+ # 执行查询
|
|
|
+ names = []
|
|
|
+ try:
|
|
|
+ with driver.session() as session:
|
|
|
+ result = session.run(query)
|
|
|
+ names = [str(record["name"]) for record in result]
|
|
|
+ except Exception as e:
|
|
|
+ dispatcher.utter_message(text=f"查询 Neo4j 数据库时出错: {e}")
|
|
|
+ driver.close()
|
|
|
+ return []
|
|
|
+
|
|
|
+ # 设置相似度阈值
|
|
|
+ threshold = 0.5
|
|
|
+
|
|
|
+ # 存储相似度和名称
|
|
|
+ similarity_scores = [(name, jellyfish.jaro_winkler_similarity(str(name), user_message)) for name in names]
|
|
|
+
|
|
|
+ # 过滤出相似度大于阈值的名称
|
|
|
+ filtered_similarities = [(name, score) for name, score in similarity_scores if score > threshold]
|
|
|
+
|
|
|
+ # 找出相似度最高的名称
|
|
|
+ highest_similarity_name = None
|
|
|
+ if filtered_similarities:
|
|
|
+ highest_similarity_name, highest_similarity_score = max(filtered_similarities, key=lambda x: x[1])
|
|
|
+ print(f"最高相似度的名称: {highest_similarity_name}")
|
|
|
+
|
|
|
+ # 如果找到了相似度高的名称,则用它替换原始的 fault_name
|
|
|
+ if highest_similarity_name is not None:
|
|
|
+ fault_hmc = highest_similarity_name
|
|
|
+
|
|
|
+ # 关闭 Neo4j 驱动连接
|
|
|
+ driver.close()
|
|
|
+
|
|
|
+ # 准备数据结构
|
|
|
+ if type(fault_hmc) != list:
|
|
|
+ data = {'args': {fault_hmc: ['fault_hmc']}, 'question_types': [intentions]}
|
|
|
+ else:
|
|
|
+ data = {'args': {fault_hmc[0]: ['fault_hmc']}, 'question_types': [intentions]}
|
|
|
+
|
|
|
+ parser = question_parser.QuestionParser()
|
|
|
+ searcher = answer_search.AnswerSearcher()
|
|
|
+ print(f"Data: {data}")
|
|
|
+ sqls = parser.parser_main(data) # 生成相关的查询语句
|
|
|
+ print(f"SQLs: {sqls}")
|
|
|
+ final_answer = searcher.search_main(sqls) # 查询相关内容
|
|
|
+ entity_lists = searcher.get_entity(sqls)
|
|
|
+ entity_str = json.dumps(entity_lists)
|
|
|
+ print(f"Entity Lists: {entity_str}")
|
|
|
+ print(f"Final Answer: {final_answer}")
|
|
|
+
|
|
|
+ # 进行判断 输出结果
|
|
|
+ if not final_answer:
|
|
|
+ dispatcher.utter_message(template='utter_out')
|
|
|
+ else:
|
|
|
+ if highest_similarity_name is not None and highest_similarity_score is not None:
|
|
|
+ match_info = (
|
|
|
+ f"当前实体的匹配数值为:{highest_similarity_score:.2f}\n"
|
|
|
+ f"根据当前的实体匹配结果的输出为:\n"
|
|
|
+ )
|
|
|
+ answer = match_info + '\n'.join(final_answer)
|
|
|
+ else:
|
|
|
+ answer = '\n'.join(final_answer)
|
|
|
+
|
|
|
+ # 发送最终答案和实体信息
|
|
|
+ dispatcher.utter_message(text=answer)
|
|
|
+ dispatcher.utter_message(text=f'{entity_lists}')
|
|
|
+
|
|
|
+ return [SlotSet('fault_hmc', entity_str)]
|
|
|
+
|
|
|
+class FindTheCorrespondingFault_obj(Action):
|
|
|
+ def name(self) -> Text:
|
|
|
+ return "FindTheCorrespondingFault_obj"
|
|
|
+
|
|
|
+ def run(
|
|
|
+ self,
|
|
|
+ dispatcher: CollectingDispatcher,
|
|
|
+ tracker: Tracker,
|
|
|
+ domain: Dict[Text, Any]
|
|
|
+ ) -> List[Dict[Text, Any]]:
|
|
|
+ user_message = tracker.latest_message.get('text')
|
|
|
+ print("text", user_message)
|
|
|
+
|
|
|
+ # 获取故障实体
|
|
|
+ fault_obj = tracker.get_slot('fault_obj')
|
|
|
+ # 获取意图
|
|
|
+ intentions = tracker.get_intent_of_latest_message()
|
|
|
+ print(f"fault_obj: {fault_obj}")
|
|
|
+ print(f"Intentions: {intentions}")
|
|
|
+
|
|
|
+
|
|
|
+ # 连接到 Neo4j 数据库
|
|
|
+ try:
|
|
|
+ driver = GraphDatabase.driver("bolt://localhost:7687", auth=("neo4j", "fdx3081475970"))
|
|
|
+ except Exception as e:
|
|
|
+ dispatcher.utter_message(text=f"无法连接到 Neo4j 数据库: {e}")
|
|
|
+ return []
|
|
|
+
|
|
|
+ # 定义查询
|
|
|
+ query = """
|
|
|
+ MATCH (n: 成品)
|
|
|
+ RETURN n.name AS name
|
|
|
+ """
|
|
|
+
|
|
|
+ # 执行查询
|
|
|
+ names = []
|
|
|
+ try:
|
|
|
+ with driver.session() as session:
|
|
|
+ result = session.run(query)
|
|
|
+ names = [record["name"] for record in result]
|
|
|
+ except Exception as e:
|
|
|
+ dispatcher.utter_message(text=f"查询 Neo4j 数据库时出错: {e}")
|
|
|
+ driver.close()
|
|
|
+ return []
|
|
|
+
|
|
|
+ # 设置相似度阈值
|
|
|
+ threshold = 0.5
|
|
|
+
|
|
|
+ # 存储相似度和名称
|
|
|
+ similarity_scores = [(name, jellyfish.jaro_winkler_similarity(name, user_message)) for name in names]
|
|
|
+
|
|
|
+ # 过滤出相似度大于阈值的名称
|
|
|
+ filtered_similarities = [(name, score) for name, score in similarity_scores if score > threshold]
|
|
|
+
|
|
|
+ # 找出相似度最高的名称
|
|
|
+ highest_similarity_name = None
|
|
|
+ if filtered_similarities:
|
|
|
+ highest_similarity_name, highest_similarity_score = max(filtered_similarities, key=lambda x: x[1])
|
|
|
+ print(f"最高相似度的名称: {highest_similarity_name}")
|
|
|
+
|
|
|
+ # 如果找到了相似度高的名称,则用它替换原始的 fault_name
|
|
|
+ if highest_similarity_name is not None:
|
|
|
+ fault_obj = highest_similarity_name
|
|
|
+
|
|
|
+ # 关闭 Neo4j 驱动连接
|
|
|
+ driver.close()
|
|
|
+
|
|
|
+ # 准备数据结构
|
|
|
+ if type(fault_obj) != list:
|
|
|
+ data = {'args': {fault_obj: ['fault_obj']}, 'question_types': [intentions]}
|
|
|
+ else:
|
|
|
+ data = {'args': {fault_obj[0]: ['fault_obj']}, 'question_types': [intentions]}
|
|
|
+
|
|
|
+ parser = question_parser.QuestionParser()
|
|
|
+ searcher = answer_search.AnswerSearcher()
|
|
|
+ print(f"Data: {data}")
|
|
|
+ sqls = parser.parser_main(data) # 生成相关的查询语句
|
|
|
+ print(f"SQLs: {sqls}")
|
|
|
+ final_answer = searcher.search_main(sqls) # 查询相关内容
|
|
|
+ entity_lists = searcher.get_entity(sqls)
|
|
|
+ entity_str = json.dumps(entity_lists)
|
|
|
+ print(f"Entity Lists: {entity_str}")
|
|
|
+ print(f"Final Answer: {final_answer}")
|
|
|
+
|
|
|
+ # 进行判断 输出结果
|
|
|
+ if not final_answer:
|
|
|
+ dispatcher.utter_message(template='utter_out')
|
|
|
+ else:
|
|
|
+ if highest_similarity_name is not None and highest_similarity_score is not None:
|
|
|
+ match_info = (
|
|
|
+ f"当前实体的匹配数值为:{highest_similarity_score:.2f}\n"
|
|
|
+ f"根据当前的实体匹配结果的输出为:\n"
|
|
|
+ )
|
|
|
+ answer = match_info + '\n'.join(final_answer)
|
|
|
+ else:
|
|
|
+ answer = '\n'.join(final_answer)
|
|
|
+
|
|
|
+ # 发送最终答案和实体信息
|
|
|
+ dispatcher.utter_message(text=answer)
|
|
|
+ dispatcher.utter_message(text=f'{entity_lists}')
|
|
|
+
|
|
|
+ return [SlotSet('fault_obj', entity_str)]
|
|
|
+
|
|
|
+class FindTheCorrespondingFault_x_obj(Action):
|
|
|
+ def name(self) -> Text:
|
|
|
+ return "FindTheCorrespondingFault_x_obj"
|
|
|
+
|
|
|
+ def run(
|
|
|
+ self,
|
|
|
+ dispatcher: CollectingDispatcher,
|
|
|
+ tracker: Tracker,
|
|
|
+ domain: Dict[Text, Any]
|
|
|
+ ) -> List[Dict[Text, Any]]:
|
|
|
+ user_message = tracker.latest_message.get('text')
|
|
|
+ print("text", user_message)
|
|
|
+
|
|
|
+ # 获取故障实体
|
|
|
+ fault_x_obj = tracker.get_slot('fault_x_obj')
|
|
|
+ # 获取意图
|
|
|
+ intentions = tracker.get_intent_of_latest_message()
|
|
|
+ print(f"Fault x obj: {fault_x_obj}")
|
|
|
+ print(f"Intentions: {intentions}")
|
|
|
+
|
|
|
+
|
|
|
+ # 连接到 Neo4j 数据库
|
|
|
+ try:
|
|
|
+ driver = GraphDatabase.driver("bolt://localhost:7687", auth=("neo4j", "fdx3081475970"))
|
|
|
+ except Exception as e:
|
|
|
+ dispatcher.utter_message(text=f"无法连接到 Neo4j 数据库: {e}")
|
|
|
+ return []
|
|
|
+
|
|
|
+ # 定义查询
|
|
|
+ query = """
|
|
|
+ MATCH (n: 型号)
|
|
|
+ RETURN n.name AS name
|
|
|
+ """
|
|
|
+
|
|
|
+ # 执行查询
|
|
|
+ names = []
|
|
|
+ try:
|
|
|
+ with driver.session() as session:
|
|
|
+ result = session.run(query)
|
|
|
+ names = [record["name"] for record in result]
|
|
|
+ except Exception as e:
|
|
|
+ dispatcher.utter_message(text=f"查询 Neo4j 数据库时出错: {e}")
|
|
|
+ driver.close()
|
|
|
+ return []
|
|
|
+
|
|
|
+ # 设置相似度阈值
|
|
|
+ threshold = 0.5
|
|
|
+
|
|
|
+ # 存储相似度和名称
|
|
|
+ similarity_scores = [(name, jellyfish.jaro_winkler_similarity(name, user_message)) for name in names]
|
|
|
+
|
|
|
+ # 过滤出相似度大于阈值的名称
|
|
|
+ filtered_similarities = [(name, score) for name, score in similarity_scores if score > threshold]
|
|
|
+
|
|
|
+ # 找出相似度最高的名称
|
|
|
+ highest_similarity_name = None
|
|
|
+ if filtered_similarities:
|
|
|
+ highest_similarity_name, highest_similarity_score = max(filtered_similarities, key=lambda x: x[1])
|
|
|
+ print(f"最高相似度的名称: {highest_similarity_name}")
|
|
|
+
|
|
|
+ # 如果找到了相似度高的名称,则用它替换原始的 fault_name
|
|
|
+ if highest_similarity_name is not None:
|
|
|
+ fault_x_obj = highest_similarity_name
|
|
|
+
|
|
|
+ # 关闭 Neo4j 驱动连接
|
|
|
+ driver.close()
|
|
|
+
|
|
|
+ # 准备数据结构
|
|
|
+ if type(fault_x_obj) != list:
|
|
|
+ data = {'args': {fault_x_obj: ['fault_x_obj']}, 'question_types': [intentions]}
|
|
|
+ else:
|
|
|
+ data = {'args': {fault_x_obj[0]: ['fault_x_obj']}, 'question_types': [intentions]}
|
|
|
+
|
|
|
+ parser = question_parser.QuestionParser()
|
|
|
+ searcher = answer_search.AnswerSearcher()
|
|
|
+ print(f"Data: {data}")
|
|
|
+ sqls = parser.parser_main(data) # 生成相关的查询语句
|
|
|
+ print(f"SQLs: {sqls}")
|
|
|
+ final_answer = searcher.search_main(sqls) # 查询相关内容
|
|
|
+ entity_lists = searcher.get_entity(sqls)
|
|
|
+ entity_str = json.dumps(entity_lists)
|
|
|
+ print(f"Entity Lists: {entity_str}")
|
|
|
+ print(f"Final Answer: {final_answer}")
|
|
|
+
|
|
|
+ # 进行判断 输出结果
|
|
|
+ if not final_answer:
|
|
|
+ dispatcher.utter_message(template='utter_out')
|
|
|
+ else:
|
|
|
+ if highest_similarity_name is not None and highest_similarity_score is not None:
|
|
|
+ match_info = (
|
|
|
+ f"当前实体的匹配数值为:{highest_similarity_score:.2f}\n"
|
|
|
+ f"根据当前的实体匹配结果的输出为:\n"
|
|
|
+ )
|
|
|
+ answer = match_info + '\n'.join(final_answer)
|
|
|
+ else:
|
|
|
+ answer = '\n'.join(final_answer)
|
|
|
+
|
|
|
+ # 发送最终答案和实体信息
|
|
|
+ dispatcher.utter_message(text=answer)
|
|
|
+ dispatcher.utter_message(text=f'{entity_lists}')
|
|
|
+
|
|
|
+ return [SlotSet('fault_x_obj', entity_str)]
|
|
|
+
|
|
|
+class FindTheCorrespondingFault_s_sys(Action):
|
|
|
+ def name(self) -> Text:
|
|
|
+ return "FindTheCorrespondingFault_s_sys"
|
|
|
+
|
|
|
+ def run(
|
|
|
+ self,
|
|
|
+ dispatcher: CollectingDispatcher,
|
|
|
+ tracker: Tracker,
|
|
|
+ domain: Dict[Text, Any]
|
|
|
+ ) -> List[Dict[Text, Any]]:
|
|
|
+ user_message = tracker.latest_message.get('text')
|
|
|
+ print("text", user_message)
|
|
|
+
|
|
|
+ # 获取故障实体
|
|
|
+ s_sys = tracker.get_slot('s_sys')
|
|
|
+ # 获取意图
|
|
|
+ intentions = tracker.get_intent_of_latest_message()
|
|
|
+ print(f"s_sys: {s_sys}")
|
|
|
+ print(f"Intentions: {intentions}")
|
|
|
+
|
|
|
+ # 连接到 Neo4j 数据库
|
|
|
+ try:
|
|
|
+ driver = GraphDatabase.driver("bolt://localhost:7687", auth=("neo4j", "fdx3081475970"))
|
|
|
+ except Exception as e:
|
|
|
+ dispatcher.utter_message(text=f"无法连接到 Neo4j 数据库: {e}")
|
|
|
+ return []
|
|
|
+
|
|
|
+ # 定义查询
|
|
|
+ query = """
|
|
|
+ MATCH (n: 子系统)
|
|
|
+ RETURN n.name AS name
|
|
|
+ """
|
|
|
+
|
|
|
+ # 执行查询
|
|
|
+ names = []
|
|
|
+ try:
|
|
|
+ with driver.session() as session:
|
|
|
+ result = session.run(query)
|
|
|
+ names = [record["name"] for record in result]
|
|
|
+ except Exception as e:
|
|
|
+ dispatcher.utter_message(text=f"查询 Neo4j 数据库时出错: {e}")
|
|
|
+ driver.close()
|
|
|
+ return []
|
|
|
+
|
|
|
+ # 设置相似度阈值
|
|
|
+ threshold = 0.5
|
|
|
+
|
|
|
+ # 存储相似度和名称
|
|
|
+ similarity_scores = [(name, jellyfish.jaro_winkler_similarity(name, user_message)) for name in names]
|
|
|
+
|
|
|
+ # 过滤出相似度大于阈值的名称
|
|
|
+ filtered_similarities = [(name, score) for name, score in similarity_scores if score > threshold]
|
|
|
+
|
|
|
+ # 找出相似度最高的名称
|
|
|
+ highest_similarity_name = None
|
|
|
+ if filtered_similarities:
|
|
|
+ highest_similarity_name, highest_similarity_score = max(filtered_similarities, key=lambda x: x[1])
|
|
|
+ print(f"最高相似度的名称: {highest_similarity_name}")
|
|
|
+
|
|
|
+ # 如果找到了相似度高的名称,则用它替换原始的 fault_name
|
|
|
+ if highest_similarity_name is not None:
|
|
|
+ s_sys = highest_similarity_name
|
|
|
+
|
|
|
+ # 关闭 Neo4j 驱动连接
|
|
|
+ driver.close()
|
|
|
+
|
|
|
+ # 准备数据结构
|
|
|
+ if type(s_sys) != list:
|
|
|
+ data = {'args': {s_sys: ['s_sys']}, 'question_types': [intentions]}
|
|
|
+ else:
|
|
|
+ data = {'args': {s_sys[0]: ['s_sys']}, 'question_types': [intentions]}
|
|
|
+
|
|
|
+ parser = question_parser.QuestionParser()
|
|
|
+ searcher = answer_search.AnswerSearcher()
|
|
|
+ print(f"Data: {data}")
|
|
|
+ sqls = parser.parser_main(data) # 生成相关的查询语句
|
|
|
+ print(f"SQLs: {sqls}")
|
|
|
+ final_answer = searcher.search_main(sqls) # 查询相关内容
|
|
|
+ entity_lists = searcher.get_entity(sqls)
|
|
|
+ entity_str = json.dumps(entity_lists)
|
|
|
+ print(f"Entity Lists: {entity_str}")
|
|
|
+ print(f"Final Answer: {final_answer}")
|
|
|
+
|
|
|
+ # 进行判断 输出结果
|
|
|
+ if not final_answer:
|
|
|
+ dispatcher.utter_message(template='utter_out')
|
|
|
+ else:
|
|
|
+ if highest_similarity_name is not None and highest_similarity_score is not None:
|
|
|
+ match_info = (
|
|
|
+ f"当前实体的匹配数值为:{highest_similarity_score:.2f}\n"
|
|
|
+ f"根据当前的实体匹配结果的输出为:\n"
|
|
|
+ )
|
|
|
+ answer = match_info + '\n'.join(final_answer)
|
|
|
+ else:
|
|
|
+ answer = '\n'.join(final_answer)
|
|
|
+
|
|
|
+ # 发送最终答案和实体信息
|
|
|
+ dispatcher.utter_message(text=answer)
|
|
|
+ dispatcher.utter_message(text=f'{entity_lists}')
|
|
|
+
|
|
|
+ return [SlotSet('s_sys', entity_str)]
|
|
|
+
|
|
|
+class FindTheCorrespondingFault_system(Action):
|
|
|
+ def name(self) -> Text:
|
|
|
+ return "FindTheCorrespondingFault_system"
|
|
|
+
|
|
|
+ def run(
|
|
|
+ self,
|
|
|
+ dispatcher: CollectingDispatcher,
|
|
|
+ tracker: Tracker,
|
|
|
+ domain: Dict[Text, Any]
|
|
|
+ ) -> List[Dict[Text, Any]]:
|
|
|
+ user_message = tracker.latest_message.get('text')
|
|
|
+ print("text", user_message)
|
|
|
+
|
|
|
+ # 获取故障实体
|
|
|
+ system = tracker.get_slot('system')
|
|
|
+ # 获取意图
|
|
|
+ intentions = tracker.get_intent_of_latest_message()
|
|
|
+ print(f"system: {system}")
|
|
|
+ print(f"Intentions: {intentions}")
|
|
|
+
|
|
|
+ # 连接到 Neo4j 数据库
|
|
|
+ try:
|
|
|
+ driver = GraphDatabase.driver("bolt://localhost:7687", auth=("neo4j", "fdx3081475970"))
|
|
|
+ except Exception as e:
|
|
|
+ dispatcher.utter_message(text=f"无法连接到 Neo4j 数据库: {e}")
|
|
|
+ return []
|
|
|
+
|
|
|
+ # 定义查询
|
|
|
+ query = """
|
|
|
+ MATCH (n: 系统)
|
|
|
+ RETURN n.name AS name
|
|
|
+ """
|
|
|
+
|
|
|
+ # 执行查询
|
|
|
+ names = []
|
|
|
+ try:
|
|
|
+ with driver.session() as session:
|
|
|
+ result = session.run(query)
|
|
|
+ names = [record["name"] for record in result]
|
|
|
+ except Exception as e:
|
|
|
+ dispatcher.utter_message(text=f"查询 Neo4j 数据库时出错: {e}")
|
|
|
+ driver.close()
|
|
|
+ return []
|
|
|
+
|
|
|
+ # 设置相似度阈值
|
|
|
+ threshold = 0.5
|
|
|
+
|
|
|
+ # 存储相似度和名称
|
|
|
+ similarity_scores = [(name, jellyfish.jaro_winkler_similarity(name, user_message)) for name in names]
|
|
|
+
|
|
|
+ # 过滤出相似度大于阈值的名称
|
|
|
+ filtered_similarities = [(name, score) for name, score in similarity_scores if score > threshold]
|
|
|
+
|
|
|
+ # 找出相似度最高的名称
|
|
|
+ highest_similarity_name = None
|
|
|
+ if filtered_similarities:
|
|
|
+ highest_similarity_name, highest_similarity_score = max(filtered_similarities, key=lambda x: x[1])
|
|
|
+ print(f"最高相似度的名称: {highest_similarity_name}")
|
|
|
+
|
|
|
+ # 如果找到了相似度高的名称,则用它替换原始的 fault_name
|
|
|
+ if highest_similarity_name is not None:
|
|
|
+ system = highest_similarity_name
|
|
|
+
|
|
|
+ # 关闭 Neo4j 驱动连接
|
|
|
+ driver.close()
|
|
|
+
|
|
|
+ # 准备数据结构
|
|
|
+ if type(system) != list:
|
|
|
+ data = {'args': {system: ['system']}, 'question_types': [intentions]}
|
|
|
+ else:
|
|
|
+ data = {'args': {system[0]: ['system']}, 'question_types': [intentions]}
|
|
|
+
|
|
|
+ parser = question_parser.QuestionParser()
|
|
|
+ searcher = answer_search.AnswerSearcher()
|
|
|
+ print(f"Data: {data}")
|
|
|
+ sqls = parser.parser_main(data) # 生成相关的查询语句
|
|
|
+ print(f"SQLs: {sqls}")
|
|
|
+ final_answer = searcher.search_main(sqls) # 查询相关内容
|
|
|
+ # entity_lists = searcher.get_entity(sqls)
|
|
|
+ try:
|
|
|
+ entity_lists = searcher.get_entity(sqls)
|
|
|
+ except Exception as e:
|
|
|
+ dispatcher.utter_message(text=f"获取实体信息时出错: {e}")
|
|
|
+ return []
|
|
|
+ entity_str = json.dumps(entity_lists)
|
|
|
+ print(f"Entity Lists: {entity_str}")
|
|
|
+ print(f"Final Answer: {final_answer}")
|
|
|
+
|
|
|
+ # 进行判断 输出结果
|
|
|
+ if not final_answer:
|
|
|
+ dispatcher.utter_message(template='utter_out')
|
|
|
+ else:
|
|
|
+ if highest_similarity_name is not None and highest_similarity_score is not None:
|
|
|
+ match_info = (
|
|
|
+ f"当前实体的匹配数值为:{highest_similarity_score:.2f}\n"
|
|
|
+ f"根据当前的实体匹配结果的输出为:\n"
|
|
|
+ )
|
|
|
+ answer = match_info + '\n'.join(final_answer)
|
|
|
+ else:
|
|
|
+ answer = '\n'.join(final_answer)
|
|
|
+
|
|
|
+ # 发送最终答案和实体信息
|
|
|
+ dispatcher.utter_message(text=answer)
|
|
|
+ dispatcher.utter_message(text=f'{entity_lists}')
|
|
|
+
|
|
|
+ return [SlotSet('system', entity_str)]
|
|
|
+
|
|
|
+# class FindTheCorrespondingsmallTalk(Action):
|
|
|
+# def name(self) -> Text:
|
|
|
+# return "action_default_fallback"
|
|
|
+#
|
|
|
+# def run(
|
|
|
+# self,
|
|
|
+# dispatcher: CollectingDispatcher,
|
|
|
+# tracker: Tracker,
|
|
|
+# domain: Dict[Text, Any],
|
|
|
+# ) -> List[EventType]:
|
|
|
+#
|
|
|
+# try:
|
|
|
+# # 获取用户的最新消息
|
|
|
+# user_message = tracker.latest_message
|
|
|
+#
|
|
|
+# # 调用 app.talk() 处理用户输入
|
|
|
+# answer = app.talk(user_message['text'])
|
|
|
+#
|
|
|
+# # 如果 answer 是一个列表,逐条发送每一条消息
|
|
|
+# if isinstance(answer, list):
|
|
|
+# for message in answer:
|
|
|
+# dispatcher.utter_message(text=message)
|
|
|
+# else:
|
|
|
+# # 否则直接发送单条消息
|
|
|
+# dispatcher.utter_message(text=answer)
|
|
|
+# except Exception as e:
|
|
|
+# print(e)
|
|
|
+# dispatcher.utter_message(template='utter_exception')
|
|
|
+#
|
|
|
+# return []
|
|
|
+
|
|
|
+
|
|
|
+class FindTheCorrespondingsmallTalk(Action):
|
|
|
+ def name(self) -> Text:
|
|
|
+ return "action_default_fallback"
|
|
|
+
|
|
|
+ def run(
|
|
|
+ self,
|
|
|
+ dispatcher: CollectingDispatcher,
|
|
|
+ tracker: Tracker,
|
|
|
+ domain: Dict[Text, Any],
|
|
|
+ ) -> List[EventType]:
|
|
|
+
|
|
|
+ try:
|
|
|
+ # food = tracker.latest_message
|
|
|
+ # answer = app.talk(food['text'])
|
|
|
+ dispatcher.utter_message(template="utter_exception")
|
|
|
+ except Exception as e:
|
|
|
+ print(e)
|
|
|
+ dispatcher.utter_message(template="utter_exception")
|
|
|
+ return []
|
|
|
+
|
|
|
+ # try:
|
|
|
+ # # 获取用户的最新消息
|
|
|
+ # user_message = tracker.latest_message
|
|
|
+ #
|
|
|
+ # # 调用 app.talk() 处理用户输入
|
|
|
+ # answer = app.talk(user_message['text'])
|
|
|
+ #
|
|
|
+ # # 如果 answer 是一个列表,则逐条发送每一条消息
|
|
|
+ # if isinstance(answer, list):
|
|
|
+ # for message in answer:
|
|
|
+ # if isinstance(message, dict) and 'text' in message:
|
|
|
+ # dispatcher.utter_message(text=message['text'])
|
|
|
+ # else:
|
|
|
+ # dispatcher.utter_message(text=str(message)) # 确保其他类型也能被处理
|
|
|
+ # elif isinstance(answer, dict) and 'text' in answer:
|
|
|
+ # # 如果是单个字典,直接发送
|
|
|
+ # dispatcher.utter_message(text=answer['text'])
|
|
|
+ # else:
|
|
|
+ # # 否则直接发送单条消息(假设 answer 是字符串)
|
|
|
+ # dispatcher.utter_message(text=str(answer))
|
|
|
+ # except Exception as e:
|
|
|
+ # print(e)
|
|
|
+ # dispatcher.utter_message(template='utter_exception')
|
|
|
+ #
|
|
|
+ # return []
|