langroid 0.2.2__py3-none-any.whl → 0.2.3__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- langroid/agent/task.py +30 -15
- {langroid-0.2.2.dist-info → langroid-0.2.3.dist-info}/METADATA +1 -1
- {langroid-0.2.2.dist-info → langroid-0.2.3.dist-info}/RECORD +6 -6
- pyproject.toml +1 -1
- {langroid-0.2.2.dist-info → langroid-0.2.3.dist-info}/LICENSE +0 -0
- {langroid-0.2.2.dist-info → langroid-0.2.3.dist-info}/WHEEL +0 -0
langroid/agent/task.py
CHANGED
@@ -184,8 +184,8 @@ class Task:
|
|
184
184
|
Note: erasing can reduce prompt sizes, but results in repetitive
|
185
185
|
sub-task delegation.
|
186
186
|
allow_null_result (bool):
|
187
|
-
If true,
|
188
|
-
|
187
|
+
If true, create dummy NO_ANSWER response when no valid response is found
|
188
|
+
in a step.
|
189
189
|
Optional, default is False.
|
190
190
|
*Note:* In non-interactive mode, when this is set to True,
|
191
191
|
you can have a situation where an LLM generates (non-tool) text,
|
@@ -193,7 +193,9 @@ class Task:
|
|
193
193
|
is inserted as a dummy response from the User entity, so the LLM
|
194
194
|
will now respond to this Null result, and this will continue
|
195
195
|
until the LLM emits a DONE signal (if instructed to do so),
|
196
|
-
otherwise
|
196
|
+
otherwise langroid detects a potential infinite loop after
|
197
|
+
a certain number of such steps (= `TaskConfig.inf_loop_wait_factor`)
|
198
|
+
and will raise an InfiniteLoopException.
|
197
199
|
max_stalled_steps (int): task considered done after this many consecutive
|
198
200
|
steps with no progress. Default is 3.
|
199
201
|
done_if_no_response (List[Responder]): consider task done if NULL
|
@@ -1047,15 +1049,10 @@ class Task:
|
|
1047
1049
|
self._show_pending_message_if_debug()
|
1048
1050
|
return self.pending_message
|
1049
1051
|
|
1050
|
-
def
|
1051
|
-
|
1052
|
-
|
1053
|
-
parent: ChatDocument | None,
|
1054
|
-
result: ChatDocument,
|
1055
|
-
) -> None:
|
1056
|
-
"""Processes valid result from a responder, during a step"""
|
1052
|
+
def _update_no_answer_vars(self, result: ChatDocument) -> None:
|
1053
|
+
"""Update variables related to NO_ANSWER responses, to aid
|
1054
|
+
in alternating NO_ANSWER infinite-loop detection."""
|
1057
1055
|
|
1058
|
-
# in case the valid response was a NO_ANSWER,
|
1059
1056
|
if NO_ANSWER in result.content:
|
1060
1057
|
if self._no_answer_step == self._step_idx - 2:
|
1061
1058
|
# N/A two steps ago
|
@@ -1067,6 +1064,16 @@ class Task:
|
|
1067
1064
|
# record the last step where the best explicit response was N/A
|
1068
1065
|
self._no_answer_step = self._step_idx
|
1069
1066
|
|
1067
|
+
def _process_valid_responder_result(
|
1068
|
+
self,
|
1069
|
+
r: Responder,
|
1070
|
+
parent: ChatDocument | None,
|
1071
|
+
result: ChatDocument,
|
1072
|
+
) -> None:
|
1073
|
+
"""Processes valid result from a responder, during a step"""
|
1074
|
+
|
1075
|
+
self._update_no_answer_vars(result)
|
1076
|
+
|
1070
1077
|
# pending_sender is of type Responder,
|
1071
1078
|
# i.e. it is either one of the agent's entities
|
1072
1079
|
# OR a sub-task, that has produced a valid response.
|
@@ -1131,6 +1138,7 @@ class Task:
|
|
1131
1138
|
metadata=ChatDocMetaData(sender=responder, parent_id=parent_id),
|
1132
1139
|
)
|
1133
1140
|
self.pending_sender = responder
|
1141
|
+
self._update_no_answer_vars(self.pending_message)
|
1134
1142
|
self.log_message(self.pending_sender, self.pending_message, mark=True)
|
1135
1143
|
|
1136
1144
|
def _show_pending_message_if_debug(self) -> None:
|
@@ -1346,13 +1354,20 @@ class Task:
|
|
1346
1354
|
def _maybe_infinite_loop(self) -> bool:
|
1347
1355
|
"""
|
1348
1356
|
Detect possible infinite loop based on message frequencies.
|
1349
|
-
NOTE: This
|
1350
|
-
|
1357
|
+
NOTE: This detects two types of loops:
|
1358
|
+
- Alternating NO_ANSWER loops, specifically of the form
|
1359
|
+
x1 NO_ANSWER x2 NO_ANSWER x3 NO_ANSWER...
|
1360
|
+
(e.g. an LLM repeatedly saying something different, and another responder
|
1361
|
+
or sub-task saying NO_ANSWER -- i.e. "DO-NOT-KNOW")
|
1362
|
+
|
1363
|
+
- "exact" loops, i.e. a cycle of messages that repeats exactly, e.g.
|
1351
1364
|
a r b i t r a t e r a t e r a t e r a t e ...
|
1352
1365
|
|
1353
|
-
[It does not detect "approximate" loops, where
|
1354
|
-
|
1366
|
+
[It does not detect more general "approximate" loops, where two entities are
|
1367
|
+
responding to each other potentially forever, with (slightly) different
|
1368
|
+
messages each time]
|
1355
1369
|
|
1370
|
+
Here is the logic for the exact-loop detection:
|
1356
1371
|
Intuition: when you look at a sufficiently long sequence with an m-message
|
1357
1372
|
loop, then the frequencies of these m messages will "dominate" those
|
1358
1373
|
of all other messages.
|
@@ -32,7 +32,7 @@ langroid/agent/special/sql/utils/populate_metadata.py,sha256=1J22UsyEPKzwK0XlJZt
|
|
32
32
|
langroid/agent/special/sql/utils/system_message.py,sha256=qKLHkvQWRQodTtPLPxr1GSLUYUFASZU8x-ybV67cB68,1885
|
33
33
|
langroid/agent/special/sql/utils/tools.py,sha256=vFYysk6Vi7HJjII8B4RitA3pt_z3gkSglDNdhNVMiFc,1332
|
34
34
|
langroid/agent/special/table_chat_agent.py,sha256=d9v2wsblaRx7oMnKhLV7uO_ujvk9gh59pSGvBXyeyNc,9659
|
35
|
-
langroid/agent/task.py,sha256=
|
35
|
+
langroid/agent/task.py,sha256=ALqGmqzqUNaZB3u8jReBcsC8rRti3WqsN82EMm4CFAo,72189
|
36
36
|
langroid/agent/tool_message.py,sha256=wIyZnUcZpxkiRPvM9O3MO3b5BBAdLEEan9kqPbvtApc,9743
|
37
37
|
langroid/agent/tools/__init__.py,sha256=e-63cfwQNk_ftRKQwgDAJQK16QLbRVWDBILeXIc7wLk,402
|
38
38
|
langroid/agent/tools/duckduckgo_search_tool.py,sha256=NhsCaGZkdv28nja7yveAhSK_w6l_Ftym8agbrdzqgfo,1935
|
@@ -128,8 +128,8 @@ langroid/vector_store/meilisearch.py,sha256=6frB7GFWeWmeKzRfLZIvzRjllniZ1cYj3Hmh
|
|
128
128
|
langroid/vector_store/momento.py,sha256=QaPzUnTwlswoawGB-paLtUPyLRvckFXLfLDfvbTzjNQ,10505
|
129
129
|
langroid/vector_store/qdrant_cloud.py,sha256=3im4Mip0QXLkR6wiqVsjV1QvhSElfxdFSuDKddBDQ-4,188
|
130
130
|
langroid/vector_store/qdrantdb.py,sha256=wYOuu5c2vIKn9ZgvTXcAiZXMpV8AOXEWFAzI8S8UP-0,16828
|
131
|
-
pyproject.toml,sha256=
|
132
|
-
langroid-0.2.
|
133
|
-
langroid-0.2.
|
134
|
-
langroid-0.2.
|
135
|
-
langroid-0.2.
|
131
|
+
pyproject.toml,sha256=MX6Rg0hLOiPlYpb9q4G0H0jLdqAjNWSI_tnKXB8mkuQ,6963
|
132
|
+
langroid-0.2.3.dist-info/LICENSE,sha256=EgVbvA6VSYgUlvC3RvPKehSg7MFaxWDsFuzLOsPPfJg,1065
|
133
|
+
langroid-0.2.3.dist-info/METADATA,sha256=1GD93aMG3wEtL7pE3NBXM1gxjyjEO0Og5XdtNGb3UGA,53146
|
134
|
+
langroid-0.2.3.dist-info/WHEEL,sha256=FMvqSimYX_P7y0a7UY-_Mc83r5zkBZsCYPm7Lr0Bsq4,88
|
135
|
+
langroid-0.2.3.dist-info/RECORD,,
|
pyproject.toml
CHANGED
File without changes
|
File without changes
|