langfun 0.1.2.dev202510050804__py3-none-any.whl → 0.1.2.dev202510070805__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.

Potentially problematic release.


This version of langfun might be problematic. Click here for more details.

@@ -187,11 +187,23 @@ class Action(pg.Object):
187
187
  self._session = None
188
188
  self._invocation: ActionInvocation | None = None
189
189
 
190
+ # NOTE(daiyip): Users could use `self._state` to keep track of the state
191
+ # during the execution of the action.
192
+ # Strictly speaking action state should better fit into
193
+ # ActionInvocation, we make it a property of Action as it's usually
194
+ # initialized before `__call__` is called.
195
+ self._state: Any = None
196
+
190
197
  @property
191
198
  def session(self) -> Optional['Session']:
192
199
  """Returns the session started by this action."""
193
200
  return self._session
194
201
 
202
+ @property
203
+ def state(self) -> Any:
204
+ """Returns the state of the action."""
205
+ return self._state
206
+
195
207
  @property
196
208
  def result(self) -> Any:
197
209
  """Returns the result of the action."""
@@ -852,7 +864,11 @@ class ParallelExecutions(pg.Object, pg.views.html.HtmlTreeView.Extension):
852
864
 
853
865
  class ActionInvocation(pg.Object, pg.views.html.HtmlTreeView.Extension):
854
866
  """A class for capturing the invocation of an action."""
855
- action: Action
867
+
868
+ action: Annotated[
869
+ Action,
870
+ 'The action being invoked.'
871
+ ]
856
872
 
857
873
  result: Annotated[
858
874
  Any,
@@ -931,6 +947,11 @@ class ActionInvocation(pg.Object, pg.views.html.HtmlTreeView.Extension):
931
947
  """Returns True if the action invocation has an error."""
932
948
  return self.error is not None
933
949
 
950
+ @property
951
+ def state(self) -> Any:
952
+ """Returns the state of the action."""
953
+ return self.action.state
954
+
934
955
  @property
935
956
  def logs(self) -> list[lf.logging.LogEntry]:
936
957
  """Returns immediate child logs from execution sequence."""
@@ -66,12 +66,18 @@ class Foo(action_lib.Action):
66
66
  time.sleep(self.simulate_execution_time[2])
67
67
  return lf_structured.query(f'subtask_{i}', lm=lm)
68
68
 
69
+ self._state = []
69
70
  for i, output, error in session.concurrent_map(
70
- _sub_task, range(3), max_workers=2, silence_on_errors=None,
71
+ _sub_task,
72
+ range(3),
73
+ max_workers=2,
74
+ ordered=True,
75
+ silence_on_errors=None,
71
76
  ):
72
77
  assert isinstance(i, int), i
73
78
  assert isinstance(output, str), output
74
79
  assert error is None, error
80
+ self._state.append(i)
75
81
  return self.x + Bar(
76
82
  simulate_action_error=self.simulate_action_error,
77
83
  simulate_execution_time=self.simulate_execution_time[3]
@@ -118,6 +124,7 @@ class SessionTest(unittest.TestCase):
118
124
  foo = Foo(1)
119
125
  self.assertIsNone(foo.session)
120
126
  self.assertIsNone(foo.invocation)
127
+ self.assertIsNone(foo.state)
121
128
  self.assertIsNone(foo.result)
122
129
  self.assertIsNone(foo.metadata)
123
130
 
@@ -136,6 +143,8 @@ class SessionTest(unittest.TestCase):
136
143
  self.assertTrue(session.has_stopped)
137
144
  self.assertEqual(result, 3)
138
145
  self.assertIsNone(foo.session)
146
+ self.assertEqual(foo.state, [0, 1, 2])
147
+ self.assertIs(foo.invocation.state, foo.state)
139
148
  self.assertEqual(foo.result, 3)
140
149
  self.assertEqual(
141
150
  foo.metadata, dict(note='foo', subtask_0=0, subtask_1=1, subtask_2=2)
@@ -1159,21 +1159,35 @@ class LanguageModel(component.Component):
1159
1159
  ) -> message_lib.Message:
1160
1160
  """Returns the first candidate."""
1161
1161
  prompt = message_lib.UserMessage.from_value(prompt)
1162
- with component.context(override_attrs=True, **kwargs):
1163
- sampling_options = self.sampling_options
1164
- if sampling_options.n != 1:
1165
- sampling_options = sampling_options.clone(override=dict(n=1))
1166
-
1167
- call_counter = self._call_counter
1168
- self._call_counter += 1
1169
- request_start = time.time()
1170
- result = self.sample(
1171
- [prompt], sampling_options=sampling_options, cache_seed=cache_seed
1172
- )[0]
1173
- elapse = time.time() - request_start
1174
- response = result.samples[0].response
1175
- self._debug(prompt, response, call_counter, result.usage, elapse)
1176
- return response
1162
+ start_time = time.time()
1163
+ error_tag = ''
1164
+ try:
1165
+ with component.context(override_attrs=True, **kwargs):
1166
+ sampling_options = self.sampling_options
1167
+ if sampling_options.n != 1:
1168
+ sampling_options = sampling_options.clone(override=dict(n=1))
1169
+
1170
+ call_counter = self._call_counter
1171
+ self._call_counter += 1
1172
+ request_start = time.time()
1173
+ result = self.sample(
1174
+ [prompt], sampling_options=sampling_options, cache_seed=cache_seed
1175
+ )[0]
1176
+ elapse = time.time() - request_start
1177
+ response = result.samples[0].response
1178
+ self._debug(prompt, response, call_counter, result.usage, elapse)
1179
+ return response
1180
+ except BaseException as e:
1181
+ error_tag = pg.ErrorInfo.from_exception(e).tag
1182
+ raise e
1183
+ finally:
1184
+ _METRICS.language_model_calls.increment(
1185
+ model=self.model_id, error=error_tag
1186
+ )
1187
+ _METRICS.language_model_call_duration_ms.record(
1188
+ int((time.time() - start_time) * 1000),
1189
+ model=self.model_id, error=error_tag,
1190
+ )
1177
1191
 
1178
1192
  def _debug(
1179
1193
  self,
@@ -1438,6 +1452,25 @@ class LanguageModel(component.Component):
1438
1452
  return None
1439
1453
 
1440
1454
 
1455
+ class _Metrics:
1456
+ """Metrics for Langfun."""
1457
+
1458
+ def __init__(self):
1459
+ self._metrics = pg.monitoring.metric_collection('/third_party/langfun')
1460
+ self.language_model_calls = self._metrics.get_counter(
1461
+ 'language_model_calls',
1462
+ 'Number of calls to the language model.',
1463
+ parameters={'model': str, 'error': str},
1464
+ )
1465
+ self.language_model_call_duration_ms = self._metrics.get_scalar(
1466
+ 'language_model_call_duration_ms',
1467
+ 'Duration of calls to the language model in milliseconds.',
1468
+ parameters={'model': str, 'error': str},
1469
+ )
1470
+
1471
+ _METRICS = _Metrics()
1472
+
1473
+
1441
1474
  class _ConcurrencyControl:
1442
1475
  """Controls the max concurrent LLM calls for a given model."""
1443
1476
 
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: langfun
3
- Version: 0.1.2.dev202510050804
3
+ Version: 0.1.2.dev202510070805
4
4
  Summary: Langfun: Language as Functions.
5
5
  Home-page: https://github.com/google/langfun
6
6
  Author: Langfun Authors
@@ -17,7 +17,7 @@ langfun/core/console.py,sha256=cLQEf84aDxItA9fStJV22xJch0TqFLNf9hLqwJ0RHmU,2652
17
17
  langfun/core/console_test.py,sha256=pBOcuNMJdVELywvroptfcRtJMsegMm3wSlHAL2TdxVk,1679
18
18
  langfun/core/langfunc.py,sha256=G50YgoVZ0y1GFw2ev41MlOqr6qa8YakbvNC0h_E0PiA,11140
19
19
  langfun/core/langfunc_test.py,sha256=CDn-gJCa5EnjN7cotAVCfSCbuzddq2o-HzEt7kV8HbY,8882
20
- langfun/core/language_model.py,sha256=T3Gyb0-S4uRunO9EotTN5-86Dc3Bw6tE4Db43qDMqOc,51042
20
+ langfun/core/language_model.py,sha256=Fs7sKLji8SZFn2V1pMpSyZREaobvlWQygCbZnJBVgcY,52101
21
21
  langfun/core/language_model_test.py,sha256=aJWn3UJm_S6U7VhU7EVXdJHPe1xza5glngPkRGtx280,38426
22
22
  langfun/core/logging.py,sha256=7IGAhp7mGokZxxqtL-XZvFLKaZ5k3F5_Xp2NUtR4GwE,9136
23
23
  langfun/core/logging_test.py,sha256=vbVGOQxwMmVSiFfbt2897gUt-8nqDpV64jCAeUG_q5U,6924
@@ -35,10 +35,10 @@ langfun/core/subscription_test.py,sha256=Y4ZdbZEwm83YNZBxHff0QR4QUa4rdaNXA3_jfIc
35
35
  langfun/core/template.py,sha256=GSOZ3OcmRtw-q05GdHrE-Y4-2MGDYsTRKmWGvVPbdhE,24962
36
36
  langfun/core/template_test.py,sha256=AQv_m9qE93WxhEhSlm1xaBgB4hu0UVtA53dljngkUW0,17090
37
37
  langfun/core/agentic/__init__.py,sha256=s9zRiAOtiTvp_sWeyGcykjlo6rez8asvLK7tiOELWEU,1336
38
- langfun/core/agentic/action.py,sha256=n3WD2J4Hw1YuldNGAzgu0pynil0DyBx1ia-_e-S9AgI,52958
38
+ langfun/core/agentic/action.py,sha256=E4B9M2Tp9LLPYSsZ4mPK4kR0dYMTR6qvRBgxyGdkIWE,53558
39
39
  langfun/core/agentic/action_eval.py,sha256=YTilyUEkJl_8FVMgdfO17PurWWaEJ6oA15CuefJJRLk,4887
40
40
  langfun/core/agentic/action_eval_test.py,sha256=7AkOwNbUX-ZgR1R0a7bvUZ5abNTUV7blf_8Mnrwb-II,2811
41
- langfun/core/agentic/action_test.py,sha256=rorIo58S1o27CZrtw05b49mLZOaiitl_xGanGZa5HXo,18028
41
+ langfun/core/agentic/action_test.py,sha256=y7cZbZGn4q8RATYibRPNea_AAvI4b4tGODo5PVTGJpA,18250
42
42
  langfun/core/coding/__init__.py,sha256=5utju_fwEsImaiftx4oXKl9FAM8p281k8-Esdh_-m1w,835
43
43
  langfun/core/coding/python/__init__.py,sha256=yTXm92oLpQb4A-fZ2qy-bzfhPYND7B-oidtbv1PNaX0,1678
44
44
  langfun/core/coding/python/correction.py,sha256=4PD76Xfv36Xrm8Ji3-GgGDNImtcDqWfMw3z6ircJMlM,7285
@@ -181,8 +181,8 @@ langfun/env/event_handlers/event_logger.py,sha256=3dbPjBe53dBgntYHlyLlj_77hVecPS
181
181
  langfun/env/event_handlers/event_logger_test.py,sha256=PGof3rPllNnyzs3Yp8kaOHLeTkVrzUgCJwlODTrVRKI,9111
182
182
  langfun/env/event_handlers/metric_writer.py,sha256=cnJe0BeWntUZ56NlwB8lkv2udcldds9GNyMg71Zz-II,16994
183
183
  langfun/env/event_handlers/metric_writer_test.py,sha256=4tI7s3o1Gw1bawXewaEZ65EPPOcr8A4m1bLK7uUcJY4,4735
184
- langfun-0.1.2.dev202510050804.dist-info/licenses/LICENSE,sha256=WNHhf_5RCaeuKWyq_K39vmp9F28LxKsB4SpomwSZ2L0,11357
185
- langfun-0.1.2.dev202510050804.dist-info/METADATA,sha256=C6wkMR5mltFYjLtWjaljJlvVvP1ZCkPWAnPgfTSawDA,7380
186
- langfun-0.1.2.dev202510050804.dist-info/WHEEL,sha256=_zCd3N1l69ArxyTb8rzEoP9TpbYXkqRFSNOD5OuxnTs,91
187
- langfun-0.1.2.dev202510050804.dist-info/top_level.txt,sha256=RhlEkHxs1qtzmmtWSwYoLVJAc1YrbPtxQ52uh8Z9VvY,8
188
- langfun-0.1.2.dev202510050804.dist-info/RECORD,,
184
+ langfun-0.1.2.dev202510070805.dist-info/licenses/LICENSE,sha256=WNHhf_5RCaeuKWyq_K39vmp9F28LxKsB4SpomwSZ2L0,11357
185
+ langfun-0.1.2.dev202510070805.dist-info/METADATA,sha256=yAexTugtlh0I2DtDp-ziy5TGQi0e45C9DhmiJOhVq-w,7380
186
+ langfun-0.1.2.dev202510070805.dist-info/WHEEL,sha256=_zCd3N1l69ArxyTb8rzEoP9TpbYXkqRFSNOD5OuxnTs,91
187
+ langfun-0.1.2.dev202510070805.dist-info/top_level.txt,sha256=RhlEkHxs1qtzmmtWSwYoLVJAc1YrbPtxQ52uh8Z9VvY,8
188
+ langfun-0.1.2.dev202510070805.dist-info/RECORD,,