langfun 0.1.2.dev202411150804__py3-none-any.whl → 0.1.2.dev202411170804__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.
- langfun/core/eval/v2/runners.py +25 -1
- langfun/core/eval/v2/runners_test.py +24 -2
- langfun/core/language_model.py +21 -8
- langfun/core/language_model_test.py +7 -0
- {langfun-0.1.2.dev202411150804.dist-info → langfun-0.1.2.dev202411170804.dist-info}/METADATA +1 -1
- {langfun-0.1.2.dev202411150804.dist-info → langfun-0.1.2.dev202411170804.dist-info}/RECORD +9 -9
- {langfun-0.1.2.dev202411150804.dist-info → langfun-0.1.2.dev202411170804.dist-info}/LICENSE +0 -0
- {langfun-0.1.2.dev202411150804.dist-info → langfun-0.1.2.dev202411170804.dist-info}/WHEEL +0 -0
- {langfun-0.1.2.dev202411150804.dist-info → langfun-0.1.2.dev202411170804.dist-info}/top_level.txt +0 -0
langfun/core/eval/v2/runners.py
CHANGED
@@ -15,6 +15,9 @@
|
|
15
15
|
import abc
|
16
16
|
import collections
|
17
17
|
import concurrent.futures
|
18
|
+
import random
|
19
|
+
import threading
|
20
|
+
import time
|
18
21
|
from typing import Any, Annotated, Callable, Iterator
|
19
22
|
|
20
23
|
from langfun import core as lf
|
@@ -373,6 +376,15 @@ class ParallelRunner(RunnerBase):
|
|
373
376
|
'Timeout for each evaluation example.'
|
374
377
|
] = None
|
375
378
|
|
379
|
+
concurrent_startup_delay: Annotated[
|
380
|
+
tuple[int, int] | None,
|
381
|
+
(
|
382
|
+
'A range of seconds to delay the initial evaluation of each thread '
|
383
|
+
'in the thread pool, helping to prevent a burst in LLM QPS at '
|
384
|
+
'startup. If set to None, no delay will be applied.'
|
385
|
+
)
|
386
|
+
] = None
|
387
|
+
|
376
388
|
def _run(self, evaluations: list[Evaluation]) -> None:
|
377
389
|
"""Runs the evaluations in parallel."""
|
378
390
|
def _run_group(evaluation_group: list[Evaluation]):
|
@@ -405,8 +417,20 @@ class ParallelRunner(RunnerBase):
|
|
405
417
|
self, evaluation: Evaluation, items: Iterator[Example]
|
406
418
|
) -> None:
|
407
419
|
"""Override run items to run in parallel."""
|
420
|
+
if self.concurrent_startup_delay is not None:
|
421
|
+
thread_delayed = {}
|
422
|
+
def _evaluate_item(item: Example):
|
423
|
+
thread_id = threading.current_thread().ident
|
424
|
+
if thread_id not in thread_delayed:
|
425
|
+
thread_delayed[thread_id] = True
|
426
|
+
time.sleep(random.randint(*self.concurrent_startup_delay))
|
427
|
+
return self.evaluate_item(evaluation, item)
|
428
|
+
else:
|
429
|
+
def _evaluate_item(item: Example):
|
430
|
+
return self.evaluate_item(evaluation, item)
|
431
|
+
|
408
432
|
for _, _, _ in lf.concurrent_map(
|
409
|
-
|
433
|
+
_evaluate_item,
|
410
434
|
items,
|
411
435
|
max_workers=evaluation.max_workers,
|
412
436
|
timeout=self.timeout,
|
@@ -198,7 +198,9 @@ class RunnerTest(unittest.TestCase):
|
|
198
198
|
)
|
199
199
|
# Global cache.
|
200
200
|
root_dir = os.path.join(tempfile.gettempdir(), 'global_cache')
|
201
|
-
run = exp.run(
|
201
|
+
run = exp.run(
|
202
|
+
root_dir, 'new', runner='sequential', use_cache='global', plugins=[]
|
203
|
+
)
|
202
204
|
self.assertTrue(pg.io.path_exists(run.output_path_for(exp, 'cache.json')))
|
203
205
|
self.assertEqual(exp.usage_summary.cached.total.num_requests, 4)
|
204
206
|
self.assertEqual(exp.usage_summary.uncached.total.num_requests, 2)
|
@@ -206,7 +208,8 @@ class RunnerTest(unittest.TestCase):
|
|
206
208
|
# Per-dataset cache.
|
207
209
|
root_dir = os.path.join(tempfile.gettempdir(), 'per_dataset')
|
208
210
|
run = exp.run(
|
209
|
-
root_dir,
|
211
|
+
root_dir, 'new', runner='sequential',
|
212
|
+
use_cache='per_dataset', plugins=[]
|
210
213
|
)
|
211
214
|
for leaf in exp.leaf_nodes:
|
212
215
|
self.assertTrue(
|
@@ -226,6 +229,9 @@ class RunnerTest(unittest.TestCase):
|
|
226
229
|
self.assertEqual(exp.usage_summary.cached.total.num_requests, 0)
|
227
230
|
self.assertEqual(exp.usage_summary.uncached.total.num_requests, 6)
|
228
231
|
|
232
|
+
|
233
|
+
class ParallelRunnerTest(RunnerTest):
|
234
|
+
|
229
235
|
def test_parallel_runner(self):
|
230
236
|
plugin = TestPlugin()
|
231
237
|
exp = test_helper.test_experiment()
|
@@ -266,6 +272,22 @@ class RunnerTest(unittest.TestCase):
|
|
266
272
|
self.assertEqual(node.progress.num_failed, 0)
|
267
273
|
self.assertEqual(node.progress.num_processed, node.progress.num_total)
|
268
274
|
|
275
|
+
def test_concurrent_startup_delay(self):
|
276
|
+
plugin = TestPlugin()
|
277
|
+
exp = test_helper.test_experiment()
|
278
|
+
root_dir = os.path.join(
|
279
|
+
tempfile.gettempdir(), 'test_concurrent_startup_delay'
|
280
|
+
)
|
281
|
+
_ = exp.run(
|
282
|
+
root_dir,
|
283
|
+
runner='parallel',
|
284
|
+
plugins=[plugin],
|
285
|
+
concurrent_startup_delay=(0, 5),
|
286
|
+
)
|
287
|
+
|
288
|
+
|
289
|
+
class DebugRunnerTest(RunnerTest):
|
290
|
+
|
269
291
|
def test_debug_runner(self):
|
270
292
|
plugin = TestPlugin()
|
271
293
|
exp = test_helper.test_experiment()
|
langfun/core/language_model.py
CHANGED
@@ -124,17 +124,18 @@ class LMSamplingUsage(pg.Object):
|
|
124
124
|
def __add__(self, other: Optional['LMSamplingUsage']) -> 'LMSamplingUsage':
|
125
125
|
if other is None:
|
126
126
|
return self
|
127
|
+
if self.estimated_cost is None:
|
128
|
+
estimated_cost = other.estimated_cost
|
129
|
+
elif other.estimated_cost is None:
|
130
|
+
estimated_cost = self.estimated_cost
|
131
|
+
else:
|
132
|
+
estimated_cost = self.estimated_cost + other.estimated_cost
|
127
133
|
return LMSamplingUsage(
|
128
134
|
prompt_tokens=self.prompt_tokens + other.prompt_tokens,
|
129
135
|
completion_tokens=self.completion_tokens + other.completion_tokens,
|
130
136
|
total_tokens=self.total_tokens + other.total_tokens,
|
131
137
|
num_requests=self.num_requests + other.num_requests,
|
132
|
-
estimated_cost=
|
133
|
-
self.estimated_cost + other.estimated_cost # pylint: disable=g-long-ternary
|
134
|
-
if (self.estimated_cost is not None
|
135
|
-
and other.estimated_cost is not None)
|
136
|
-
else None
|
137
|
-
)
|
138
|
+
estimated_cost=estimated_cost,
|
138
139
|
)
|
139
140
|
|
140
141
|
def __radd__(self, other: Optional['LMSamplingUsage']) -> 'LMSamplingUsage':
|
@@ -956,7 +957,9 @@ class UsageSummary(pg.Object, pg.views.HtmlTreeView.Extension):
|
|
956
957
|
if self._usage_badge is not None:
|
957
958
|
self._usage_badge.update(
|
958
959
|
self._badge_text(),
|
959
|
-
tooltip=pg.format(
|
960
|
+
tooltip=pg.format(
|
961
|
+
self, verbose=False, custom_format=self._tooltip_format
|
962
|
+
),
|
960
963
|
styles=dict(color=self._badge_color()),
|
961
964
|
)
|
962
965
|
|
@@ -978,6 +981,14 @@ class UsageSummary(pg.Object, pg.views.HtmlTreeView.Extension):
|
|
978
981
|
green = int(255 * (1 - normalized_value))
|
979
982
|
return f'rgb({red}, {green}, 0)'
|
980
983
|
|
984
|
+
def _tooltip_format(self, v, root_indent):
|
985
|
+
del root_indent
|
986
|
+
if isinstance(v, int):
|
987
|
+
return f'{v:,}'
|
988
|
+
if isinstance(v, float):
|
989
|
+
return f'{v:,.3f}'
|
990
|
+
return None
|
991
|
+
|
981
992
|
def _html_tree_view(
|
982
993
|
self,
|
983
994
|
*,
|
@@ -993,7 +1004,9 @@ class UsageSummary(pg.Object, pg.views.HtmlTreeView.Extension):
|
|
993
1004
|
if usage_badge is None:
|
994
1005
|
usage_badge = pg.views.html.controls.Badge(
|
995
1006
|
self._badge_text(),
|
996
|
-
tooltip=pg.format(
|
1007
|
+
tooltip=pg.format(
|
1008
|
+
self, custom_format=self._tooltip_format, verbose=False
|
1009
|
+
),
|
997
1010
|
css_classes=['usage-summary'],
|
998
1011
|
styles=dict(color=self._badge_color()),
|
999
1012
|
interactive=True,
|
@@ -744,6 +744,13 @@ class LMSamplingUsageTest(unittest.TestCase):
|
|
744
744
|
self.assertEqual(usage1 + usage2, usage1 + usage2)
|
745
745
|
self.assertIs(usage1 + None, usage1)
|
746
746
|
self.assertIs(None + usage1, usage1)
|
747
|
+
usage3 = lm_lib.LMSamplingUsage(100, 200, 300, 4, None)
|
748
|
+
self.assertEqual(
|
749
|
+
usage1 + usage3, lm_lib.LMSamplingUsage(200, 400, 600, 8, 5.0)
|
750
|
+
)
|
751
|
+
self.assertEqual(
|
752
|
+
usage3 + usage1, lm_lib.LMSamplingUsage(200, 400, 600, 8, 5.0)
|
753
|
+
)
|
747
754
|
|
748
755
|
def test_usage_not_available(self):
|
749
756
|
usage_not_available = lm_lib.UsageNotAvailable()
|
@@ -8,8 +8,8 @@ langfun/core/console.py,sha256=Fra2_MSWZbFh6rY8HZoYgpGLsrNvhaGuL03znOwQbhM,2529
|
|
8
8
|
langfun/core/console_test.py,sha256=pBOcuNMJdVELywvroptfcRtJMsegMm3wSlHAL2TdxVk,1679
|
9
9
|
langfun/core/langfunc.py,sha256=G50YgoVZ0y1GFw2ev41MlOqr6qa8YakbvNC0h_E0PiA,11140
|
10
10
|
langfun/core/langfunc_test.py,sha256=fKIAqcSNI_7M6nwoZW77HEam8Oa6vcWhsCNgVJanzb4,8822
|
11
|
-
langfun/core/language_model.py,sha256=
|
12
|
-
langfun/core/language_model_test.py,sha256=
|
11
|
+
langfun/core/language_model.py,sha256=b15MZ_qbydnz5vQ09t7sf9tc3C7qWvMSxUrGfT0p99I,33827
|
12
|
+
langfun/core/language_model_test.py,sha256=hnYhtw7GM_TbhgsJzHNYTaoDewUlPHpOVlI7xEkCFuI,31783
|
13
13
|
langfun/core/logging.py,sha256=uslllP0RTGN223oro1m4nZZ0bFppcL07OwbFKm2iG6k,7519
|
14
14
|
langfun/core/logging_test.py,sha256=b5bPTSUoYeICATaO6I8dOVumodwRbxSp1Oz96Sf3KcE,6104
|
15
15
|
langfun/core/memory.py,sha256=f-asN1F7Vehgdn_fK84v73GrEUOxRtaW934keutTKjk,2416
|
@@ -76,8 +76,8 @@ langfun/core/eval/v2/progress_tracking.py,sha256=1imwSbllxHWG3zYrzo2NvytBZsVtjqu
|
|
76
76
|
langfun/core/eval/v2/progress_tracking_test.py,sha256=eY2HvZeEXDA5Zyfi2m5NDWO_9kSfQsaAOEcIhkSbWCY,1874
|
77
77
|
langfun/core/eval/v2/reporting.py,sha256=TGkli1IDwqfqsCJ_WslOMGk_24JDg7oRRTGXlAJlWpc,4361
|
78
78
|
langfun/core/eval/v2/reporting_test.py,sha256=JxffbUPWInUyLjo-AQVFrllga884Mdfm05R86FtxSss,1482
|
79
|
-
langfun/core/eval/v2/runners.py,sha256=
|
80
|
-
langfun/core/eval/v2/runners_test.py,sha256=
|
79
|
+
langfun/core/eval/v2/runners.py,sha256=zJmu-amUiYv1g0Ek4c3mXkBgp-AFvSF7WpXVZCCf7Y4,14245
|
80
|
+
langfun/core/eval/v2/runners_test.py,sha256=UeiUNygux_U6iGVG18rhp68ZE4hoWeoT6XsXvSjxNQg,11620
|
81
81
|
langfun/core/eval/v2/test_helper.py,sha256=pDpZTBnWRR5xjJv3Uy3NWEzArqlL8FTMOgeR4C53F5M,2348
|
82
82
|
langfun/core/llms/__init__.py,sha256=uR2vLghsnZqY6OjZKAs9Lo-YFNxZNunf3A0q6-1GYlc,6346
|
83
83
|
langfun/core/llms/anthropic.py,sha256=uJXVgaFONL8okOSVQ4VGMGht_VZ30m1hoLzmDbIjmks,13990
|
@@ -148,8 +148,8 @@ langfun/core/templates/demonstration.py,sha256=vCrgYubdZM5Umqcgp8NUVGXgr4P_c-fik
|
|
148
148
|
langfun/core/templates/demonstration_test.py,sha256=SafcDQ0WgI7pw05EmPI2S4v1t3ABKzup8jReCljHeK4,2162
|
149
149
|
langfun/core/templates/selfplay.py,sha256=yhgrJbiYwq47TgzThmHrDQTF4nDrTI09CWGhuQPNv-s,2273
|
150
150
|
langfun/core/templates/selfplay_test.py,sha256=Ot__1P1M8oJfoTp-M9-PQ6HUXqZKyMwvZ5f7yQ3yfyM,2326
|
151
|
-
langfun-0.1.2.
|
152
|
-
langfun-0.1.2.
|
153
|
-
langfun-0.1.2.
|
154
|
-
langfun-0.1.2.
|
155
|
-
langfun-0.1.2.
|
151
|
+
langfun-0.1.2.dev202411170804.dist-info/LICENSE,sha256=WNHhf_5RCaeuKWyq_K39vmp9F28LxKsB4SpomwSZ2L0,11357
|
152
|
+
langfun-0.1.2.dev202411170804.dist-info/METADATA,sha256=Sr1olxW-wSjImKrZFtjVkrCe-_-uqVWkPa20-axQGPQ,8890
|
153
|
+
langfun-0.1.2.dev202411170804.dist-info/WHEEL,sha256=R06PA3UVYHThwHvxuRWMqaGcr-PuniXahwjmQRFMEkY,91
|
154
|
+
langfun-0.1.2.dev202411170804.dist-info/top_level.txt,sha256=RhlEkHxs1qtzmmtWSwYoLVJAc1YrbPtxQ52uh8Z9VvY,8
|
155
|
+
langfun-0.1.2.dev202411170804.dist-info/RECORD,,
|
File without changes
|
File without changes
|
{langfun-0.1.2.dev202411150804.dist-info → langfun-0.1.2.dev202411170804.dist-info}/top_level.txt
RENAMED
File without changes
|