| 189 | return text_messages |
| 190 | |
| 191 | def _detect_tool(self, text: str) -> Tuple[bool, str, str, str]: |
| 192 | special_func_token = '\nAction:' |
| 193 | special_args_token = '\nAction Input:' |
| 194 | special_obs_token = '\nObservation:' |
| 195 | func_name, func_args = None, None |
| 196 | i = text.rfind(special_func_token) |
| 197 | j = text.rfind(special_args_token) |
| 198 | k = text.rfind(special_obs_token) |
| 199 | if 0 <= i < j: # If the text has `Action` and `Action input`, |
| 200 | if k < j: # but does not contain `Observation`, |
| 201 | # then it is likely that `Observation` is ommited by the LLM, |
| 202 | # because the output text may have discarded the stop word. |
| 203 | text = text.rstrip() + special_obs_token # Add it back. |
| 204 | k = text.rfind(special_obs_token) |
| 205 | func_name = text[i + len(special_func_token):j].strip() |
| 206 | func_args = text[j + len(special_args_token):k].strip() |
| 207 | text = text[:i] # Return the response before tool call, i.e., `Thought` |
| 208 | return (func_name is not None), func_name, func_args, text |