diff --git a/Agently/plugins/agent_component/EventListener.py b/Agently/plugins/agent_component/EventListener.py index 6503c31a..40f7bc7e 100644 --- a/Agently/plugins/agent_component/EventListener.py +++ b/Agently/plugins/agent_component/EventListener.py @@ -34,6 +34,10 @@ def on_done(self, listener: callable, *, is_await:bool=False, is_agent_event:boo def on_finally(self, listener: callable, *, is_await:bool=False, is_agent_event:bool=False): self.add("response:finally", listener, is_await=is_await, is_agent_event=is_agent_event) return self.agent + + def on_realtime(self, listener: callable, *, is_await:bool=False, is_agent_event:bool=False): + self.add("response:realtime", listener, is_await=is_await, is_agent_event=is_agent_event) + return self.agent async def call_event_listeners(self, event: str, data: any): listeners = self.listeners.get_trace_back() or {} @@ -65,6 +69,7 @@ def export(self): "on_delta": { "func": self.on_delta }, "on_done": { "func": self.on_done }, "on_finally": { "func": self.on_finally }, + "on_realtime": { "func": self.on_realtime }, "call_event_listeners": { "func": self.call_event_listeners }, }, } diff --git a/Agently/plugins/agent_component/Realtime.py b/Agently/plugins/agent_component/Realtime.py index cfbd59f8..191442dd 100644 --- a/Agently/plugins/agent_component/Realtime.py +++ b/Agently/plugins/agent_component/Realtime.py @@ -15,6 +15,7 @@ def __init__(self, agent: object): self._streamed_keys = [] self._ongoing_key = None self._ongoing_value = None + self._last_value = None def use_realtime(self): self._is_enable = True @@ -39,6 +40,21 @@ async def __scan_realtime_value(self, realtime_value:dict, prefix:str="", output else: if self._ongoing_key == (prefix + key): self._ongoing_value = value + if self._last_value and isinstance(self._ongoing_value, str): + delta = self._ongoing_value.replace(self._last_value, "") + else: + delta = value + if delta != "": + await self.agent.call_event_listeners( + "response:realtime", + { + "key": self._ongoing_key, + "value": self._ongoing_value, + "delta": delta, + "complete_value": realtime_value, + }, + ) + self._last_value = value if self._ongoing_key != prefix + key: if (prefix + key) not in self._streamed_keys and value not in (None, ""): if self._ongoing_key != None: @@ -47,6 +63,21 @@ async def __scan_realtime_value(self, realtime_value:dict, prefix:str="", output await self.agent.call_event_listeners(f"key_start:{ self._ongoing_key }", None) self._streamed_keys.append(prefix + key) self._ongoing_value = value + if self._last_value and isinstance(self._ongoing_value, str): + delta = self._ongoing_value.replace(self._last_value, "") + else: + delta = value + if delta != "": + await self.agent.call_event_listeners( + "response:realtime", + { + "key": self._ongoing_key, + "value": self._ongoing_value, + "delta": delta, + "complete_value": realtime_value, + }, + ) + self._last_value = value if (prefix + key) in self._streamed_keys or value in (None, ""): continue @@ -67,26 +98,24 @@ async def _suffix(self, event:str, data:any): lexer.append_string(realtime_json_str) realtime_value = json5.loads(lexer.complete_json()) if self._output_data_frame == None: - await self.agent.call_event_listeners( - "response:realtime", - { - "key": None, - "value": realtime_value, - "complete_value": realtime_value, - }, - ) + if self._last_value and isinstance(realtime_value, str): + delta = realtime_value.replace(self._last_value, "") + else: + delta = realtime_value + if delta != "": + await self.agent.call_event_listeners( + "response:realtime", + { + "key": None, + "value": realtime_value, + "delta": delta, + "complete_value": realtime_value, + }, + ) + self._last_value = realtime_value else: if isinstance(realtime_value, dict): await self.__scan_realtime_value(realtime_value, "", self._output_data_frame) - if self._ongoing_key != None: - await self.agent.call_event_listeners( - "response:realtime", - { - "key": self._ongoing_key, - "value": self._ongoing_value, - "complete_value": realtime_value, - }, - ) def export(self): return { diff --git a/Agently/plugins/request/ERNIE.py b/Agently/plugins/request/ERNIE.py index a576a829..ea64866a 100644 --- a/Agently/plugins/request/ERNIE.py +++ b/Agently/plugins/request/ERNIE.py @@ -1,4 +1,4 @@ -from .utils import RequestABC, to_prompt_structure, to_instruction, to_json_desc +from .utils import RequestABC, to_prompt_structure, to_instruction, to_json_desc, format_request_messages from Agently.utils import RuntimeCtxNamespace import erniebot @@ -11,6 +11,12 @@ def __init__(self, request): self.request_type = "chat" self.model_name = "ERNIE" self.model_settings = RuntimeCtxNamespace(f"model.{self.model_name}", self.request.settings) + if not self.model_settings.get_trace_back("message_rules.no_multi_system_messages"): + self.model_settings.set("message_rules.no_multi_system_messages", True) + if not self.model_settings.get_trace_back("message_rules.strict_orders"): + self.model_settings.set("message_rules.strict_orders", True) + if not self.model_settings.get_trace_back("message_rules.no_multi_type_messages"): + self.model_settings.set("message_rules.no_multi_type_messages", True) def _create_client(self): if self.request_type == "chat": @@ -101,19 +107,21 @@ def generate_request_data(self): erniebot.access_token = access_token[api_type] messages = self.construct_request_messages() request_messages = [] - system_prompt = "" + #system_prompt = "" for message in messages: if message["role"] == "system": - system_prompt += f"{ message['content'] }\n" + #system_prompt += f"{ message['content'] }\n" + message["role"] = "user" + request_messages.append(message) else: request_messages.append(message) request_data = { - "messages": request_messages, + "messages": format_request_messages(request_messages, self.model_settings), "stream": True, **options, } - if system_prompt != "" and self.request.settings.get_trace_back("retry_count", 0) > 0: - request_data.update({ "system": system_prompt }) + #if system_prompt != "" and self.request.settings.get_trace_back("retry_count", 0) > 0: + # request_data.update({ "system": system_prompt }) # request type: embedding elif self.request_type == "embedding": if "model" not in options: diff --git a/Agently/plugins/request/QianFan.py b/Agently/plugins/request/QianFan.py index 65e76c6e..1900ed5e 100644 --- a/Agently/plugins/request/QianFan.py +++ b/Agently/plugins/request/QianFan.py @@ -170,19 +170,21 @@ def generate_request_data(self): options["model"] = "ERNIE-Speed-8K" messages = format_request_messages(self.construct_request_messages(), self.model_settings) request_messages = [] - system_prompt = "" + #system_prompt = "" for message in messages: if message["role"] == "system": - system_prompt += f"{ message['content'] }\n" + message["role"] = "user" + request_messages.append(message) + #system_prompt += f"{ message['content'] }\n" else: request_messages.append(message) request_data = { - "messages": request_messages, + "messages": format_request_messages(request_messages, self.model_settings), "stream": True, **options, } - if system_prompt != "" and self.request.settings.get_trace_back("retry_count", 0) > 0: - request_data.update({ "system": system_prompt }) + #if system_prompt != "" and self.request.settings.get_trace_back("retry_count", 0) > 0: + # request_data.update({ "system": system_prompt }) elif self.request_type in ["completion", "completions"]: if "model" not in options: options["model"] = "Yi-34B-Chat"