11个文件已修改
1 文件已重命名
1个文件已添加
| | |
| | | import json |
| | | import uuid |
| | | |
| | | from fastapi import Depends, APIRouter |
| | | from sqlalchemy.orm import Session |
| | | from starlette.responses import StreamingResponse |
| | | from app.api import get_current_user |
| | | from app.models import UserModel |
| | | from starlette.responses import StreamingResponse, Response |
| | | from app.config.const import dialog_chat, advanced_chat, base_chat, agent_chat, workflow_chat, basic_chat, \ |
| | | smart_message_error, http_400, http_500, http_200 |
| | | from app.models.base_model import get_db |
| | | from app.models.v2.session_model import ChatDialogData |
| | | from app.service.v2.chat import service_chat_dialog |
| | | from app.models.v2.session_model import ChatData |
| | | from app.service.v2.chat import service_chat_dialog, get_chat_info, service_chat_basic, \ |
| | | service_chat_workflow, service_chat_parameters, service_chat_sessions |
| | | |
| | | chat1_router = APIRouter() |
| | | chat_router_v2 = APIRouter() |
| | | |
| | | |
| | | @chat1_router.post("/chat_dialog") |
| | | async def api_chat_dialog(dialog: ChatDialogData, db: Session = Depends(get_db)): # current_user: UserModel = Depends(get_current_user) |
| | | return StreamingResponse(service_chat_dialog(db, dialog.chatId ,dialog.question, dialog.sessionId, 1), media_type="text/event-stream") |
| | | @chat_router_v2.post("/{chatId}/run") |
| | | async def api_chat_dialog(chatId:str, dialog: ChatData, db: Session = Depends(get_db)): # current_user: UserModel = Depends(get_current_user) |
| | | |
| | | chat_info = await get_chat_info(db, chatId) |
| | | if not chat_info: |
| | | error_msg = json.dumps({"message": smart_message_error, "error": "**ERROR**: parameter exception", "status": http_400}) |
| | | return StreamingResponse(f"data: {error_msg}\n\n", |
| | | media_type="text/event-stream") |
| | | session_id = dialog.sessionId |
| | | if chat_info.mode == dialog_chat: |
| | | if not dialog.query: |
| | | error_msg = json.dumps( |
| | | {"message": smart_message_error, "error": "**ERROR**: question cannot be empty.", "status": http_400}) |
| | | return StreamingResponse(f"data: {error_msg}\n\n", |
| | | media_type="text/event-stream") |
| | | if not session_id: |
| | | session = await service_chat_sessions(db, chatId, dialog.query) |
| | | if not session or session.get("code") != 0: |
| | | error_msg = json.dumps( |
| | | {"message": smart_message_error, "error": "**ERROR**: chat agent error", "status": http_500}) |
| | | return StreamingResponse(f"data: {error_msg}\n\n", |
| | | media_type="text/event-stream") |
| | | session_id = session.get("data", {}).get("id") |
| | | return StreamingResponse(service_chat_dialog(db, chatId ,dialog.query, session_id, 1, chat_info.mode), media_type="text/event-stream") |
| | | elif chat_info.mode == agent_chat or chat_info.mode == workflow_chat or chat_info.mode == advanced_chat or chat_info.mode == base_chat: |
| | | if not session_id: |
| | | session_id = str(uuid.uuid4()).replace("-", "") |
| | | return StreamingResponse(service_chat_workflow(db, chatId, dialog, session_id, 1, chat_info.mode), |
| | | media_type="text/event-stream") |
| | | elif chat_info.mode == basic_chat: |
| | | return StreamingResponse(service_chat_basic(db, chatId, dialog.question, dialog_chat.sessionId, 1), |
| | | media_type="text/event-stream") |
| | | else: |
| | | error_msg = json.dumps({"message": smart_message_error, "error": "**ERROR**: chat agent error", "status": http_500}) |
| | | return StreamingResponse(f"data: {error_msg}\n\n", |
| | | media_type="text/event-stream") |
| | | |
| | | |
| | | @chat_router_v2.get("/{chatId}/parameters") |
| | | async def api_chat_parameters(chatId:str, db: Session = Depends(get_db)): # current_user: UserModel = Depends(get_current_user) |
| | | status_code = http_200 |
| | | data = await service_chat_parameters(db, chatId, 1) |
| | | if not data: |
| | | status_code = http_400 |
| | | return Response(json.dumps(data), media_type="application/json", status_code=status_code) |
| | | |
| | | # @chat_router_v2.get("/{chatId}/parameters") |
| | | # async def api_chat_parameters(chatId:str, db: Session = Depends(get_db)): # current_user: UserModel = Depends(get_current_user) |
| | | # status_code = http_200 |
| | | # data = await service_chat_parameters(db, chatId, 1) |
| | | # if not data: |
| | | # status_code = http_400 |
| | | # return Response(json.dumps(data), media_type="application/json", status_code=status_code) |
| | |
| | | |
| | | ####------ |
| | | RG_CHAT_DIALOG= "/api/v1/chats/{}/completions" |
| | | RG_CHAT_SESSIONS= "/api/v1/chats/{}/sessions" |
| | | |
| | | ### ---------- |
| | | DF_CHAT_AGENT= "/v1/chat-messages" |
| | | DF_CHAT_WORKFLOW= "/v1/workflows/run" |
| | | DF_CHAT_PARAMETERS= "/v1/parameters" |
| | |
| | | DIFY = "dify_app" |
| | | |
| | | ### ---------------app type----------------- |
| | | BASIC_ID = 3 |
| | | RAGFLOW_ID = 1 |
| | | BISHENG_ID = 2 |
| | | DIFY_ID = 4 |
| | | BASIC_TYPE = "3" |
| | | RG_TYPE = "1" |
| | | BS_TYPE = "2" |
| | | DF_TYPE = "4" |
| | | |
| | | ### ------------------status-------------------- |
| | | USER_STATSU_DELETE = "2" |
| | |
| | | |
| | | ### |
| | | max_chunk_size =5000 |
| | | |
| | | |
| | | ### ---------chat mode-------------- |
| | | dialog_chat = "agent-dialog" |
| | | workflow_chat = "workflow" |
| | | advanced_chat = "advanced-chat" |
| | | agent_chat = "agent-chat" |
| | | base_chat = "chat" |
| | | basic_chat = "agent-basic" |
| | | |
| | | |
| | | ### ------------------------------ |
| | | rg_api_token = "6b8ee426c67511efb1510242ac1b0006" |
| | | |
| | | |
| | | ### ----------------evnet message value---------------------- |
| | | message_event = "message" |
| | | message_agent_thought = "agent_thought" |
| | | message_agent = "agent_message" |
| | | message_end = "message_end" |
| | | message_error = "error" |
| | | message_file = "message_file" |
| | | message_tts = "tts_message" |
| | | message_tts_end = "tts_message_end" |
| | | message_replace = "message_replace" |
| | | message_ping = "ping" |
| | | workflow_started = "workflow_started" |
| | | node_started = "node_started" |
| | | node_finished = "node_finished" |
| | | workflow_finished = "workflow_finished" |
| | | |
| | | |
| | | ### --------------------smart output event message---------------------------------- |
| | | smart_message_cover = "message" |
| | | smart_message_stream = "stream" |
| | | smart_message_file = "message_file" |
| | | smart_message_end = "message_end" |
| | | smart_message_error = "error" |
| | | smart_workflow_started = "workflow_started" |
| | | smart_node_started = "node_started" |
| | | smart_node_finished = "node_finished" |
| | | smart_workflow_finished = "workflow_finished" |
| | | |
| | | |
| | | ### ---------------------------http status-------------------------------------- |
| | | http_200 = 200 |
| | | http_400 = 400 |
| | | http_500 = 500 |
| | |
| | | from datetime import datetime |
| | | from typing import Type |
| | | |
| | | from sqlalchemy import Column, Integer, DateTime, Text |
| | | from sqlalchemy import Column, Integer, DateTime, Text, String |
| | | from sqlalchemy.orm import Session |
| | | |
| | | from app.config.const import RAGFLOW |
| | |
| | | |
| | | |
| | | |
| | | class ApiTokenModel(Base): |
| | | __tablename__ = "chat_api_tokens" |
| | | id = Column(String(32), primary_key=True) |
| | | app_id = Column(String(32), index=True) |
| | | type = Column(String(16)) |
| | | token = Column(String(255)) |
| | | created_at = Column(DateTime, default=datetime.now()) |
| | | last_used_at = Column(DateTime, default=datetime.now()) |
| | |
| | | from pydantic import BaseModel |
| | | from sqlalchemy import Column, String, Integer, DateTime, JSON, TEXT, Index |
| | | |
| | | from Log import logger |
| | | # from Log import logger |
| | | from app.models.agent_model import AgentType |
| | | from app.models.base_model import Base |
| | | |
| | |
| | | reference = Column(TEXT) |
| | | conversation_id = Column(String(36), index=True) |
| | | event_type = Column(String(16)) |
| | | session_type = Column(String(16)) |
| | | |
| | | # to_dict 方法 |
| | | def to_dict(self): |
| | | return { |
| | | 'id': self.id, |
| | | 'session_id': self.id, |
| | | 'name': self.name, |
| | | 'agent_type': self.agent_type, |
| | | 'agent_id': self.agent_id, |
| | | 'event_type': self.event_type, |
| | | 'session_type': self.session_type, |
| | | 'create_date': self.create_date.strftime("%Y-%m-%d %H:%M:%S"), |
| | | 'update_date': self.update_date.strftime("%Y-%m-%d %H:%M:%S"), |
| | | } |
| | |
| | | |
| | | |
| | | |
| | | class ChatDialogData(BaseModel): |
| | | class ChatData(BaseModel): |
| | | sessionId: Optional[str] = "" |
| | | question: str |
| | | chatId: str |
| | | |
| | | class Config: |
| | | extra = 'allow' # 允许其他动态字段 |
| | | |
| | | |
| | | |
| | | class ChatSessionDao: |
| | |
| | | session = self.db.query(ChatSessionModel).filter_by(id=session_id).first() |
| | | return session |
| | | |
| | | async def update_session_by_id(self, session_id: str, session, message: dict) -> ChatSessionModel | None: |
| | | async def update_session_by_id(self, session_id: str, session, message: dict, conversation_id=None) -> ChatSessionModel | None: |
| | | print(message) |
| | | if not session: |
| | | session = await self.get_session_by_id(session_id) |
| | | if session: |
| | | try: |
| | | if conversation_id: |
| | | session.conversation_id=conversation_id |
| | | session.add_message(message) |
| | | session.update_date = current_time() |
| | | self.db.commit() |
| | | self.db.refresh(session) |
| | | except Exception as e: |
| | | logger.error(e) |
| | | # logger.error(e) |
| | | self.db.rollback() |
| | | return session |
| | | |
| | |
| | | import json |
| | | |
| | | # from Log import logger |
| | | from app.models.v2.session_model import ChatData |
| | | from app.service.v2.app_driver.chat_base import ChatBase |
| | | |
| | | |
| | | class ChatAgent(ChatBase): |
| | | |
| | | async def chat_completions(self, url, data, headers): |
| | | complete_response = "" |
| | | async for line in self.http_stream(url, data, headers): |
| | | # logger.error(line) |
| | | if line.startswith("data:"): |
| | | complete_response = line.strip("data:").strip() |
| | | elif line.startswith("Error: "): |
| | | yield {"event": "error", "message": line} |
| | | else: |
| | | complete_response += line.strip() |
| | | try: |
| | | json_data = json.loads(complete_response) |
| | | # 处理 JSON 数据 |
| | | # print(json_data) |
| | | complete_response = "" |
| | | yield json_data |
| | | |
| | | except json.JSONDecodeError as e: |
| | | # logger.info("Invalid JSON data------------------") |
| | | print(e) |
| | | |
| | | @staticmethod |
| | | async def request_data(query: str, conversation_id: str, user:str, chat_data: ChatData) -> dict: |
| | | inputs = [] |
| | | files = [] |
| | | if hasattr(chat_data, "inputs"): |
| | | inputs = chat_data.inputs |
| | | if hasattr(chat_data, "files"): |
| | | files = chat_data.files |
| | | |
| | | return { |
| | | "inputs":inputs, |
| | | "query": query, |
| | | "response_mode": "streaming", |
| | | "conversation_id": conversation_id, |
| | | "user": user, |
| | | "files": files |
| | | } |
| | | |
| | | |
| | | if __name__ == "__main__": |
| | | async def aa(): |
| | | chat_id = "16954f6d-c1e6-4a0b-b371-363c28e8a48b" |
| | | token = "app-79ndndjNAFSV3qTuDAjDwuSO" |
| | | base_url = "http://192.168.20.116" |
| | | url = f"{base_url}/v1/chat-messages" |
| | | chat = ChatAgent() |
| | | data = { |
| | | "inputs":{}, |
| | | "query": "你好,你能做什么?", |
| | | "response_mode": "streaming", |
| | | "conversation_id": "", |
| | | "user": "1", |
| | | "files": [] |
| | | } |
| | | headers = { |
| | | 'Content-Type': 'application/json', |
| | | 'Authorization': f"Bearer {token}" |
| | | } |
| | | async for ans in chat.chat_completions(url, data, headers): |
| | | print(ans) |
| | | |
| | | |
| | | import asyncio |
| | | |
| | | asyncio.run(aa()) |
| | |
| | | @staticmethod |
| | | async def http_post(url, data, headers, timeout=300): |
| | | async with httpx.AsyncClient(timeout=timeout) as client: |
| | | response = client.post(url, json=data, headers=headers) |
| | | response = await client.post(url, json=data, headers=headers) |
| | | return response |
| | | |
| | | @staticmethod |
| | | async def http_get(url, params, headers, timeout=300): |
| | | async with httpx.AsyncClient(timeout=timeout) as client: |
| | | response = client.get(url, params=params, headers=headers) |
| | | response = await client.get(url, params=params, headers=headers) |
| | | return response |
| | | |
| | | @staticmethod |
| | | async def get_headers(token): |
| | | headers = { |
| | | # 'Content-Type': 'application/json', |
| | | return { |
| | | 'Content-Type': 'application/json', |
| | | 'Authorization': f'Bearer {token}' |
| | | } |
| | | |
New file |
| | |
| | | import json |
| | | |
| | | # from Log import logger |
| | | from app.service.v2.app_driver.chat_base import ChatBase |
| | | |
| | | |
| | | class ChatBaseApply(ChatBase): |
| | | |
| | | async def chat_parameters(self, url, params, headers): |
| | | |
| | | res = await self.http_get(url, params, headers) |
| | | if res.status_code == 200: |
| | | return res.json() |
| | | else: |
| | | return {} |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | |
| | | if __name__ == "__main__": |
| | | async def aa(): |
| | | chat_id = "bcb56e4b-8f21-41f1-b22a-80335fe58345" |
| | | token = "app-9sbGzhtFuGIducdepzQgX06v" |
| | | base_url = "http://192.168.20.116" |
| | | url = f"{base_url}/v1/parameters" |
| | | chat = ChatBaseApply() |
| | | data = { |
| | | "question": "电网技术总结300字", |
| | | "stream": True, |
| | | "session_id": "9969c152cce411ef8a140242ac1b0002" |
| | | } |
| | | params = { |
| | | "user": "1" |
| | | } |
| | | headers = { |
| | | 'Content-Type': 'application/json', |
| | | 'Authorization': f"Bearer {token}" |
| | | } |
| | | ans = await chat.chat_parameters(url, params, headers) |
| | | print(ans) |
| | | |
| | | |
| | | import asyncio |
| | | |
| | | asyncio.run(aa()) |
| | |
| | | |
| | | class ChatDialog(ChatBase): |
| | | |
| | | |
| | | def __init__(self, token): |
| | | self.token = token |
| | | |
| | | |
| | | async def get_headers(self): |
| | | return { |
| | | 'Content-Type': 'application/json', |
| | | 'Authorization': f'Bearer {self.token}' |
| | | } |
| | | |
| | | |
| | | async def chat_completions(self, url, data, headers): |
| | | complete_response = "" |
| | | async for line in self.http_stream(url, data, headers): |
| | | # logger.error(line) |
| | | print(line) |
| | | if line.startswith("data:"): |
| | | complete_response = line.strip("data:").strip() |
| | | else: |
| | |
| | | logger.info("Invalid JSON data------------------") |
| | | # print(e) |
| | | |
| | | async def chat_sessions(self, url, data, headers): |
| | | |
| | | res = await self.http_post(url, data, headers) |
| | | if res.status_code == 200: |
| | | return res.json() |
| | | else: |
| | | return {} |
| | | |
| | | |
| | | |
| | | @staticmethod |
| | | async def request_data(question, session_id=""): |
| | | return { |
| | | "question": question, |
| | | "stream": True, |
| | | "session_id": session_id |
| | | } |
| | | |
| | | |
| | | |
| | |
| | | import json |
| | | |
| | | # from Log import logger |
| | | from app.models.v2.session_model import ChatData |
| | | from app.service.v2.app_driver.chat_base import ChatBase |
| | | |
| | | |
| | | class ChatWorkflow(ChatBase): |
| | | |
| | | async def chat_completions(self, url, data, headers): |
| | | complete_response = "" |
| | | async for line in self.http_stream(url, data, headers): |
| | | if line.startswith("data:"): |
| | | complete_response = line.strip("data:").strip() |
| | | elif line.startswith("Error: "): |
| | | yield {"event": "error", "message": line} |
| | | else: |
| | | complete_response += line.strip() |
| | | try: |
| | | json_data = json.loads(complete_response) |
| | | # 处理 JSON 数据 |
| | | # print(json_data) |
| | | complete_response = "" |
| | | yield json_data |
| | | |
| | | except json.JSONDecodeError as e: |
| | | # logger.info("Invalid JSON data------------------") |
| | | print(e) |
| | | |
| | | @staticmethod |
| | | async def request_data(query: str, conversation_id: str, user:str, chat_data: ChatData) -> dict: |
| | | inputs = [] |
| | | files = [] |
| | | if hasattr(chat_data, "inputs"): |
| | | inputs = chat_data.inputs |
| | | if hasattr(chat_data, "files"): |
| | | files = chat_data.files |
| | | |
| | | return { |
| | | "inputs":inputs, |
| | | "query": query, |
| | | "response_mode": "streaming", |
| | | "conversation_id": conversation_id, |
| | | "user": user, |
| | | "files": files |
| | | } |
| | | |
| | | |
| | | if __name__ == "__main__": |
| | | async def aa(): |
| | | chat_id = "16954f6d-c1e6-4a0b-b371-363c28e8a48b" |
| | | token = "app-79ndndjNAFSV3qTuDAjDwuSO" |
| | | base_url = "http://192.168.20.116" |
| | | url = f"{base_url}/v1/chat-messages" |
| | | chat = ChatAgent() |
| | | data = { |
| | | "inputs":{}, |
| | | "query": "你好,你能做什么?", |
| | | "response_mode": "streaming", |
| | | "conversation_id": "", |
| | | "user": "1", |
| | | "files": [] |
| | | } |
| | | headers = { |
| | | 'Content-Type': 'application/json', |
| | | 'Authorization': f"Bearer {token}" |
| | | } |
| | | async for ans in chat.chat_completions(url, data, headers): |
| | | print(ans) |
| | | |
| | | |
| | | import asyncio |
| | | |
| | | asyncio.run(aa()) |
| | |
| | | import json |
| | | |
| | | from Log import logger |
| | | from app.config.agent_base_url import RG_CHAT_DIALOG |
| | | from app.config.agent_base_url import RG_CHAT_DIALOG, DF_CHAT_AGENT, DF_CHAT_PARAMETERS, RG_CHAT_SESSIONS, \ |
| | | DF_CHAT_WORKFLOW |
| | | from app.config.config import settings |
| | | from app.config.const import max_chunk_size |
| | | from app.models.v2.session_model import ChatSessionDao |
| | | from app.config.const import * |
| | | from app.models import DialogModel, ApiTokenModel |
| | | from app.models.v2.session_model import ChatSessionDao, ChatData |
| | | from app.service.v2.app_driver.chat_agent import ChatAgent |
| | | from app.service.v2.app_driver.chat_data import ChatBaseApply |
| | | from app.service.v2.app_driver.chat_dialog import ChatDialog |
| | | from app.service.v2.app_driver.chat_workflow import ChatWorkflow |
| | | |
| | | |
| | | async def service_chat_dialog(db, chat_id:str, question: str, session_id: str, user_id): |
| | | token = "ragflow-YzMzE1NDRjYzMyZjExZWY5ZjkxMDI0Mm" |
| | | url = settings.fwr_base_url+RG_CHAT_DIALOG.format(chat_id) |
| | | chat = ChatDialog(token) |
| | | request_data = { |
| | | "question": question, |
| | | "stream": True, |
| | | "session_id": session_id |
| | | } |
| | | headers = { |
| | | 'Content-Type': 'application/json', |
| | | 'Authorization': f"Bearer {token}" |
| | | } |
| | | async def update_session_log(db, session_id: str, message: dict, conversation_id: str): |
| | | await ChatSessionDao(db).update_session_by_id( |
| | | session_id=session_id, |
| | | session=None, |
| | | message=message, |
| | | conversation_id=conversation_id |
| | | ) |
| | | |
| | | |
| | | async def add_session_log(db, session_id: str, question: str, chat_id: str, user_id, event_type: str, |
| | | conversation_id: str): |
| | | try: |
| | | await ChatSessionDao(db).update_or_insert_by_id( |
| | | session = await ChatSessionDao(db).update_or_insert_by_id( |
| | | session_id=session_id, |
| | | name=question[:255], |
| | | agent_id=chat_id, |
| | | agent_type=1, |
| | | tenant_id=user_id, |
| | | message={"role": "user", "content": question}, |
| | | conversation_id=session_id, |
| | | event_type="message" |
| | | conversation_id=conversation_id, |
| | | event_type=event_type |
| | | ) |
| | | return session |
| | | except Exception as e: |
| | | logger.error(e) |
| | | try: |
| | | return None |
| | | |
| | | |
| | | async def get_chat_token(db, app_id): |
| | | app_token = db.query(ApiTokenModel).filter_by(app_id=app_id).first() |
| | | if app_token: |
| | | return app_token.token |
| | | return "" |
| | | |
| | | |
| | | async def get_chat_info(db, chat_id: str): |
| | | return db.query(DialogModel).filter_by(id=chat_id, status=Dialog_STATSU_ON).first() |
| | | |
| | | |
| | | async def get_chat_object(mode): |
| | | if mode == workflow_chat: |
| | | url = settings.dify_base_url + DF_CHAT_WORKFLOW |
| | | return ChatWorkflow(), url |
| | | else: |
| | | url = settings.dify_base_url + DF_CHAT_AGENT |
| | | return ChatAgent(), url |
| | | |
| | | |
| | | async def service_chat_dialog(db, chat_id: str, question: str, session_id: str, user_id, mode: str): |
| | | conversation_id = "" |
| | | token = await get_chat_token(db, rg_api_token) |
| | | url = settings.fwr_base_url + RG_CHAT_DIALOG.format(chat_id) |
| | | chat = ChatDialog() |
| | | session = await add_session_log(db, session_id, question, chat_id, user_id, mode, session_id) |
| | | if session: |
| | | conversation_id = session.conversation_id |
| | | message = {"role": "assistant","answer":"", "reference": {}} |
| | | async for ans in chat.chat_completions(url, request_data, headers): |
| | | try: |
| | | async for ans in chat.chat_completions(url, await chat.request_data(question, conversation_id), |
| | | await chat.get_headers(token)): |
| | | data = {} |
| | | error = "" |
| | | status = http_200 |
| | | if ans.get("code", None) == 102: |
| | | error = ans.get("message", "请输入你的问题!") |
| | | data = {"answer":error} |
| | | event = "message" |
| | | error = ans.get("message", "error!") |
| | | status = http_400 |
| | | event = smart_message_error |
| | | else: |
| | | if isinstance(ans.get("data"), bool) and ans.get("data") is True: |
| | | data = {} |
| | | event = "message_end" |
| | | event = smart_message_end |
| | | else: |
| | | data = ans.get("data", {}) |
| | | message = ans.get("data", {}) |
| | | event = "message" |
| | | message_str = "data: " + json.dumps({"event": event, "data": data}, ensure_ascii=False) + "\n\n" |
| | | # conversation_id = data.get("session_id", "") |
| | | if "session_id" in data: |
| | | del data["session_id"] |
| | | message = data |
| | | event = smart_message_cover |
| | | message_str = "data: " + json.dumps( |
| | | {"event": event, "data": data, "error": error, "status": status, "session_id": session_id}, |
| | | ensure_ascii=False) + "\n\n" |
| | | for i in range(0, len(message_str), max_chunk_size): |
| | | chunk = message_str[i:i + max_chunk_size] |
| | | # print(chunk) |
| | | yield chunk # 发送分块消息 |
| | | await ChatSessionDao(db).update_session_by_id( |
| | | session_id=session_id, |
| | | session=None, |
| | | message=message |
| | | ) |
| | | except Exception as e: |
| | | |
| | | logger.error(e) |
| | | yield "data: " + json.dumps({"message": "message", |
| | | "data": {"answer": "**ERROR**: " + str(e), "reference": []}}, |
| | | try: |
| | | yield "data: " + json.dumps({"message": smart_message_error, |
| | | "error": "**ERROR**: " + str(e), "status": http_500}, |
| | | ensure_ascii=False) + "\n\n" |
| | | except: |
| | | ... |
| | | finally: |
| | | await update_session_log(db, session_id, message, conversation_id) |
| | | |
| | | |
| | | async def service_chat_workflow(db, chat_id: str, chat_data: ChatData, session_id: str, user_id, mode: str): |
| | | conversation_id = "" |
| | | answer_event = "" |
| | | answer_agent = "" |
| | | message_id = "" |
| | | task_id = "" |
| | | error = "" |
| | | files = [] |
| | | node_list = [] |
| | | token = await get_chat_token(db, chat_id) |
| | | |
| | | chat, url = await get_chat_object(mode) |
| | | if hasattr(chat_data, "query"): |
| | | query = chat_data.query |
| | | else: |
| | | query = "start new workflow" |
| | | session = await add_session_log(db, session_id, query, chat_id, user_id, mode, conversation_id) |
| | | if session: |
| | | conversation_id = session.conversation_id |
| | | try: |
| | | async for ans in chat.chat_completions(url, |
| | | await chat.request_data(query, conversation_id, str(user_id), chat_data), |
| | | await chat.get_headers(token)): |
| | | data = {} |
| | | status = http_200 |
| | | conversation_id = ans.get("conversation_id") |
| | | task_id = ans.get("task_id") |
| | | if ans.get("event") == message_error: |
| | | error = ans.get("message", "参数异常!") |
| | | status = http_400 |
| | | event = smart_message_error |
| | | elif ans.get("event") == message_agent: |
| | | data = {"answer": ans.get("answer", ""), "id": ans.get("message_id", "")} |
| | | answer_agent += ans.get("answer", "") |
| | | message_id = ans.get("message_id", "") |
| | | event = smart_message_stream |
| | | elif ans.get("event") == message_event: |
| | | data = {"answer": ans.get("answer", ""), "id": ans.get("message_id", "")} |
| | | answer_event += ans.get("answer", "") |
| | | message_id = ans.get("message_id", "") |
| | | event = smart_message_stream |
| | | elif ans.get("event") == message_file: |
| | | data = {"url": ans.get("url", ""), "id": ans.get("id", ""), |
| | | "type": ans.get("type", "")} |
| | | files.append(data) |
| | | event = smart_message_file |
| | | elif ans.get("event") in [workflow_started, node_started, node_finished]: |
| | | data = ans.get("data", {}) |
| | | data["inputs"] = [] |
| | | data["outputs"] = [] |
| | | data["process_data"] = "" |
| | | node_list.append(ans) |
| | | event = [smart_workflow_started, smart_node_started, smart_node_finished][ |
| | | [workflow_started, node_started, node_finished].index(ans.get("event"))] |
| | | elif ans.get("event") == workflow_finished: |
| | | data = ans.get("data", {}) |
| | | event = smart_workflow_finished |
| | | node_list.append(ans) |
| | | elif ans.get("event") == message_end: |
| | | event = smart_message_end |
| | | else: |
| | | continue |
| | | |
| | | yield "data: " + json.dumps( |
| | | {"event": event, "data": data, "error": error, "status": status, "task_id": task_id, |
| | | "session_id": session_id}, |
| | | ensure_ascii=False) + "\n\n" |
| | | |
| | | yield "data: " + json.dumps({"message": "message_end", |
| | | "data": {}}, |
| | | except Exception as e: |
| | | logger.error(e) |
| | | try: |
| | | yield "data: " + json.dumps({"message": smart_message_error, |
| | | "error": "**ERROR**: " + str(e), "status": http_500}, |
| | | ensure_ascii=False) + "\n\n" |
| | | except: |
| | | ... |
| | | finally: |
| | | await update_session_log(db, session_id, {"role": "assistant", "answer": answer_event or answer_agent, |
| | | "node_list": node_list, "task_id": task_id, "id": message_id, |
| | | "error": error}, conversation_id) |
| | | |
| | | |
| | | async def service_chat_basic(db, chat_id: str, question: str, session_id: str, user_id): |
| | | ... |
| | | |
| | | |
| | | async def service_chat_parameters(db, chat_id, user_id): |
| | | chat_info = db.query(DialogModel).filter_by(id=chat_id).first() |
| | | if not chat_info: |
| | | return {} |
| | | if chat_info.dialog_type == RG_TYPE: |
| | | return {"retriever_resource": |
| | | { |
| | | "enabled": True |
| | | } |
| | | } |
| | | elif chat_info.dialog_type == BASIC_TYPE: |
| | | ... |
| | | elif chat_info.dialog_type == DF_TYPE: |
| | | token = await get_chat_token(db, chat_id) |
| | | if not token: |
| | | return {} |
| | | url = settings.dify_base_url + DF_CHAT_PARAMETERS |
| | | chat = ChatBaseApply() |
| | | return await chat.chat_parameters(url, {"user": str(user_id)}, await chat.get_headers(token)) |
| | | |
| | | |
| | | async def service_chat_sessions(db, chat_id, name): |
| | | token = await get_chat_token(db, rg_api_token) |
| | | if not token: |
| | | return {} |
| | | url = settings.fwr_base_url + RG_CHAT_SESSIONS.format(chat_id) |
| | | chat = ChatDialog() |
| | | return await chat.chat_sessions(url, {"name": name}, await chat.get_headers(token)) |
| | |
| | | from app.api.label import label_router |
| | | from app.api.llm import llm_router |
| | | from app.api.organization import dept_router |
| | | from app.api.v2.chat import chat1_router |
| | | from app.api.v2.chat import chat_router_v2 |
| | | from app.api.v2.public_api import public_api |
| | | from app.api.report import router as report_router |
| | | from app.api.resource import menu_router |
| | |
| | | app.include_router(canvas_router, prefix='/api/canvas', tags=["canvas"]) |
| | | app.include_router(label_router, prefix='/api/label', tags=["label"]) |
| | | app.include_router(public_api, prefix='/v1/api', tags=["public_api"]) |
| | | app.include_router(chat1_router, prefix='/v1/chat', tags=["chat1"]) |
| | | app.include_router(chat_router_v2, prefix='/v1/chat', tags=["chat1"]) |
| | | app.mount("/static", StaticFiles(directory="app/images"), name="static") |
| | | |
| | | if __name__ == "__main__": |