langfun 0.1.2.dev202509250804__py3-none-any.whl → 0.1.2.dev202509260805__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.
- langfun/env/__init__.py +4 -5
- langfun/env/base_environment.py +41 -34
- langfun/env/base_feature.py +10 -1
- langfun/env/base_sandbox.py +27 -26
- langfun/env/base_test.py +106 -33
- langfun/env/event_handlers/__init__.py +12 -0
- langfun/env/event_handlers/base.py +271 -0
- langfun/env/event_handlers/event_logger.py +415 -0
- langfun/env/event_handlers/event_logger_test.py +289 -0
- langfun/env/interface.py +103 -380
- langfun/env/interface_test.py +3 -3
- langfun/env/load_balancers_test.py +3 -15
- langfun/env/test_utils.py +12 -26
- {langfun-0.1.2.dev202509250804.dist-info → langfun-0.1.2.dev202509260805.dist-info}/METADATA +1 -1
- {langfun-0.1.2.dev202509250804.dist-info → langfun-0.1.2.dev202509260805.dist-info}/RECORD +18 -14
- {langfun-0.1.2.dev202509250804.dist-info → langfun-0.1.2.dev202509260805.dist-info}/WHEEL +0 -0
- {langfun-0.1.2.dev202509250804.dist-info → langfun-0.1.2.dev202509260805.dist-info}/licenses/LICENSE +0 -0
- {langfun-0.1.2.dev202509250804.dist-info → langfun-0.1.2.dev202509260805.dist-info}/top_level.txt +0 -0
langfun/env/interface.py
CHANGED
|
@@ -22,60 +22,6 @@ from typing import Annotated, Any, ContextManager, ClassVar, Iterator, Optional
|
|
|
22
22
|
|
|
23
23
|
import pyglove as pg
|
|
24
24
|
|
|
25
|
-
#
|
|
26
|
-
# Environemnt identifiers.
|
|
27
|
-
#
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
@dataclasses.dataclass(frozen=True)
|
|
31
|
-
class EnvironmentId:
|
|
32
|
-
"""Identifier for an environment."""
|
|
33
|
-
environment_id: str
|
|
34
|
-
|
|
35
|
-
def __str__(self) -> str:
|
|
36
|
-
return self.environment_id
|
|
37
|
-
|
|
38
|
-
def working_dir(self, root_dir: str | None) -> str | None:
|
|
39
|
-
"""Returns the download directory for the service."""
|
|
40
|
-
if root_dir is None:
|
|
41
|
-
return None
|
|
42
|
-
return os.path.join(root_dir, _make_path_compatible(self.environment_id))
|
|
43
|
-
|
|
44
|
-
# Enable automatic conversion from str to EnvironmentId.
|
|
45
|
-
pg.typing.register_converter(str, EnvironmentId, EnvironmentId)
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
@dataclasses.dataclass(frozen=True)
|
|
49
|
-
class SandboxId:
|
|
50
|
-
"""Identifier for a sandbox."""
|
|
51
|
-
environment_id: EnvironmentId
|
|
52
|
-
sandbox_id: str
|
|
53
|
-
|
|
54
|
-
def __str__(self) -> str:
|
|
55
|
-
return f'{self.environment_id}/{self.sandbox_id}'
|
|
56
|
-
|
|
57
|
-
def working_dir(self, root_dir: str | None) -> str | None:
|
|
58
|
-
"""Returns the download directory for the sandbox."""
|
|
59
|
-
if root_dir is None:
|
|
60
|
-
return None
|
|
61
|
-
return os.path.join(
|
|
62
|
-
self.environment_id.working_dir(root_dir),
|
|
63
|
-
_make_path_compatible(self.sandbox_id)
|
|
64
|
-
)
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
def _make_path_compatible(id_str: str) -> str:
|
|
68
|
-
"""Makes a path compatible with CNS."""
|
|
69
|
-
return id_str.translate(
|
|
70
|
-
str.maketrans({
|
|
71
|
-
'@': '_',
|
|
72
|
-
':': '_',
|
|
73
|
-
'#': '_',
|
|
74
|
-
' ': '',
|
|
75
|
-
})
|
|
76
|
-
)
|
|
77
|
-
|
|
78
|
-
|
|
79
25
|
#
|
|
80
26
|
# Environment errors.
|
|
81
27
|
#
|
|
@@ -216,262 +162,6 @@ class SessionTeardownError(SandboxError):
|
|
|
216
162
|
not isinstance(e, SandboxStateError) for e in self.errors.values()
|
|
217
163
|
)
|
|
218
164
|
|
|
219
|
-
|
|
220
|
-
#
|
|
221
|
-
# Event handler.
|
|
222
|
-
#
|
|
223
|
-
|
|
224
|
-
|
|
225
|
-
class SessionEventHandler:
|
|
226
|
-
"""Base class for session event handlers."""
|
|
227
|
-
|
|
228
|
-
def on_session_start(
|
|
229
|
-
self,
|
|
230
|
-
environment: 'Environment',
|
|
231
|
-
sandbox: 'Sandbox',
|
|
232
|
-
session_id: str,
|
|
233
|
-
duration: float,
|
|
234
|
-
error: BaseException | None
|
|
235
|
-
) -> None:
|
|
236
|
-
"""Called when a sandbox session starts.
|
|
237
|
-
|
|
238
|
-
Args:
|
|
239
|
-
environment: The environment.
|
|
240
|
-
sandbox: The sandbox.
|
|
241
|
-
session_id: The session ID.
|
|
242
|
-
duration: The time spent on starting the session.
|
|
243
|
-
error: The error that caused the session to start. If None, the session
|
|
244
|
-
started normally.
|
|
245
|
-
"""
|
|
246
|
-
|
|
247
|
-
def on_session_end(
|
|
248
|
-
self,
|
|
249
|
-
environment: 'Environment',
|
|
250
|
-
sandbox: 'Sandbox',
|
|
251
|
-
session_id: str,
|
|
252
|
-
lifetime: float,
|
|
253
|
-
error: BaseException | None
|
|
254
|
-
) -> None:
|
|
255
|
-
"""Called when a sandbox session ends.
|
|
256
|
-
|
|
257
|
-
Args:
|
|
258
|
-
environment: The environment.
|
|
259
|
-
sandbox: The sandbox.
|
|
260
|
-
session_id: The session ID.
|
|
261
|
-
lifetime: The session lifetime in seconds.
|
|
262
|
-
error: The error that caused the session to end. If None, the session
|
|
263
|
-
ended normally.
|
|
264
|
-
"""
|
|
265
|
-
|
|
266
|
-
|
|
267
|
-
class FeatureEventHandler:
|
|
268
|
-
"""Base class for feature event handlers."""
|
|
269
|
-
|
|
270
|
-
def on_feature_setup(
|
|
271
|
-
self,
|
|
272
|
-
environment: 'Environment',
|
|
273
|
-
sandbox: 'Sandbox',
|
|
274
|
-
feature: 'Feature',
|
|
275
|
-
duration: float,
|
|
276
|
-
error: BaseException | None
|
|
277
|
-
) -> None:
|
|
278
|
-
"""Called when a sandbox feature is setup."""
|
|
279
|
-
|
|
280
|
-
def on_feature_teardown(
|
|
281
|
-
self,
|
|
282
|
-
environment: 'Environment',
|
|
283
|
-
sandbox: 'Sandbox',
|
|
284
|
-
feature: 'Feature',
|
|
285
|
-
duration: float,
|
|
286
|
-
error: BaseException | None
|
|
287
|
-
) -> None:
|
|
288
|
-
"""Called when a sandbox feature is teardown."""
|
|
289
|
-
|
|
290
|
-
def on_feature_teardown_session(
|
|
291
|
-
self,
|
|
292
|
-
environment: 'Environment',
|
|
293
|
-
sandbox: 'Sandbox',
|
|
294
|
-
feature: 'Feature',
|
|
295
|
-
session_id: str,
|
|
296
|
-
duration: float,
|
|
297
|
-
error: BaseException | None
|
|
298
|
-
) -> None:
|
|
299
|
-
"""Called when a feature is teardown with a session."""
|
|
300
|
-
|
|
301
|
-
def on_feature_setup_session(
|
|
302
|
-
self,
|
|
303
|
-
environment: 'Environment',
|
|
304
|
-
sandbox: 'Sandbox',
|
|
305
|
-
feature: 'Feature',
|
|
306
|
-
session_id: str | None,
|
|
307
|
-
duration: float,
|
|
308
|
-
error: BaseException | None
|
|
309
|
-
) -> None:
|
|
310
|
-
"""Called when a feature is setup with a session."""
|
|
311
|
-
|
|
312
|
-
def on_feature_housekeep(
|
|
313
|
-
self,
|
|
314
|
-
environment: 'Environment',
|
|
315
|
-
sandbox: 'Sandbox',
|
|
316
|
-
feature: 'Feature',
|
|
317
|
-
counter: int,
|
|
318
|
-
duration: float,
|
|
319
|
-
error: BaseException | None
|
|
320
|
-
) -> None:
|
|
321
|
-
"""Called when a sandbox feature is housekeeping."""
|
|
322
|
-
|
|
323
|
-
|
|
324
|
-
class SandboxEventHandler(FeatureEventHandler, SessionEventHandler):
|
|
325
|
-
"""Base class for sandbox event handlers."""
|
|
326
|
-
|
|
327
|
-
def on_sandbox_start(
|
|
328
|
-
self,
|
|
329
|
-
environment: 'Environment',
|
|
330
|
-
sandbox: 'Sandbox',
|
|
331
|
-
duration: float,
|
|
332
|
-
error: BaseException | None
|
|
333
|
-
) -> None:
|
|
334
|
-
"""Called when a sandbox is started.
|
|
335
|
-
|
|
336
|
-
Args:
|
|
337
|
-
environment: The environment.
|
|
338
|
-
sandbox: The sandbox.
|
|
339
|
-
duration: The time spent on starting the sandbox.
|
|
340
|
-
error: The error that caused the sandbox to start. If None, the sandbox
|
|
341
|
-
started normally.
|
|
342
|
-
"""
|
|
343
|
-
|
|
344
|
-
def on_sandbox_status_change(
|
|
345
|
-
self,
|
|
346
|
-
environment: 'Environment',
|
|
347
|
-
sandbox: 'Sandbox',
|
|
348
|
-
old_status: 'Sandbox.Status',
|
|
349
|
-
new_status: 'Sandbox.Status',
|
|
350
|
-
span: float,
|
|
351
|
-
) -> None:
|
|
352
|
-
"""Called when a sandbox status changes.
|
|
353
|
-
|
|
354
|
-
Args:
|
|
355
|
-
environment: The environment.
|
|
356
|
-
sandbox: The sandbox.
|
|
357
|
-
old_status: The old sandbox status.
|
|
358
|
-
new_status: The new sandbox status.
|
|
359
|
-
span: Time spent on the old status in seconds.
|
|
360
|
-
"""
|
|
361
|
-
|
|
362
|
-
def on_sandbox_shutdown(
|
|
363
|
-
self,
|
|
364
|
-
environment: 'Environment',
|
|
365
|
-
sandbox: 'Sandbox',
|
|
366
|
-
lifetime: float,
|
|
367
|
-
error: BaseException | None
|
|
368
|
-
) -> None:
|
|
369
|
-
"""Called when a sandbox is shutdown.
|
|
370
|
-
|
|
371
|
-
Args:
|
|
372
|
-
environment: The environment.
|
|
373
|
-
sandbox: The sandbox.
|
|
374
|
-
lifetime: The sandbox lifetime in seconds.
|
|
375
|
-
error: The error that caused the sandbox to shutdown. If None, the
|
|
376
|
-
sandbox shutdown normally.
|
|
377
|
-
"""
|
|
378
|
-
|
|
379
|
-
def on_sandbox_activity(
|
|
380
|
-
self,
|
|
381
|
-
name: str,
|
|
382
|
-
environment: 'Environment',
|
|
383
|
-
sandbox: 'Sandbox',
|
|
384
|
-
feature: Optional['Feature'],
|
|
385
|
-
session_id: str | None,
|
|
386
|
-
duration: float,
|
|
387
|
-
error: BaseException | None,
|
|
388
|
-
**kwargs
|
|
389
|
-
) -> None:
|
|
390
|
-
"""Called when a sandbox activity is performed.
|
|
391
|
-
|
|
392
|
-
Args:
|
|
393
|
-
name: The name of the sandbox activity.
|
|
394
|
-
environment: The environment.
|
|
395
|
-
sandbox: The sandbox.
|
|
396
|
-
feature: The feature that is associated with the sandbox activity.
|
|
397
|
-
session_id: The session ID.
|
|
398
|
-
duration: The sandbox activity duration in seconds.
|
|
399
|
-
error: The error that caused the sandbox activity to perform. If None,
|
|
400
|
-
the sandbox activity performed normally.
|
|
401
|
-
**kwargs: The keyword arguments of the sandbox activity.
|
|
402
|
-
"""
|
|
403
|
-
|
|
404
|
-
def on_sandbox_housekeep(
|
|
405
|
-
self,
|
|
406
|
-
environment: 'Environment',
|
|
407
|
-
sandbox: 'Sandbox',
|
|
408
|
-
counter: int,
|
|
409
|
-
duration: float,
|
|
410
|
-
error: BaseException | None
|
|
411
|
-
) -> None:
|
|
412
|
-
"""Called when a sandbox finishes a round of housekeeping.
|
|
413
|
-
|
|
414
|
-
Args:
|
|
415
|
-
environment: The environment.
|
|
416
|
-
sandbox: The sandbox.
|
|
417
|
-
counter: Zero-based counter of the housekeeping round.
|
|
418
|
-
duration: The sandbox housekeeping duration in seconds.
|
|
419
|
-
error: The error that caused the sandbox to housekeeping. If None, the
|
|
420
|
-
sandbox housekeeping normally.
|
|
421
|
-
"""
|
|
422
|
-
|
|
423
|
-
|
|
424
|
-
class EnvironmentEventHandler(SandboxEventHandler):
|
|
425
|
-
"""Base class for environment event handlers."""
|
|
426
|
-
|
|
427
|
-
def on_environment_start(
|
|
428
|
-
self,
|
|
429
|
-
environment: 'Environment',
|
|
430
|
-
duration: float,
|
|
431
|
-
error: BaseException | None
|
|
432
|
-
) -> None:
|
|
433
|
-
"""Called when the environment is started.
|
|
434
|
-
|
|
435
|
-
Args:
|
|
436
|
-
environment: The environment.
|
|
437
|
-
duration: The environment start duration in seconds.
|
|
438
|
-
error: The error that failed the environment start. If None, the
|
|
439
|
-
environment started normally.
|
|
440
|
-
"""
|
|
441
|
-
|
|
442
|
-
def on_environment_housekeep(
|
|
443
|
-
self,
|
|
444
|
-
environment: 'Environment',
|
|
445
|
-
counter: int,
|
|
446
|
-
duration: float,
|
|
447
|
-
error: BaseException | None
|
|
448
|
-
) -> None:
|
|
449
|
-
"""Called when the environment finishes a round of housekeeping.
|
|
450
|
-
|
|
451
|
-
Args:
|
|
452
|
-
environment: The environment.
|
|
453
|
-
counter: Zero-based counter of the housekeeping round.
|
|
454
|
-
duration: The environment start duration in seconds.
|
|
455
|
-
error: The error that failed the housekeeping. If None, the
|
|
456
|
-
housekeeping succeeded.
|
|
457
|
-
"""
|
|
458
|
-
|
|
459
|
-
def on_environment_shutdown(
|
|
460
|
-
self,
|
|
461
|
-
environment: 'Environment',
|
|
462
|
-
lifetime: float,
|
|
463
|
-
error: BaseException | None
|
|
464
|
-
) -> None:
|
|
465
|
-
"""Called when the environment is shutdown.
|
|
466
|
-
|
|
467
|
-
Args:
|
|
468
|
-
environment: The environment.
|
|
469
|
-
lifetime: The environment lifetime in seconds.
|
|
470
|
-
error: The error that caused the environment to shutdown. If None, the
|
|
471
|
-
environment shutdown normally.
|
|
472
|
-
"""
|
|
473
|
-
|
|
474
|
-
|
|
475
165
|
#
|
|
476
166
|
# Interface for sandbox-based environment.
|
|
477
167
|
#
|
|
@@ -480,6 +170,20 @@ class EnvironmentEventHandler(SandboxEventHandler):
|
|
|
480
170
|
class Environment(pg.Object):
|
|
481
171
|
"""Base class for an environment."""
|
|
482
172
|
|
|
173
|
+
@dataclasses.dataclass(frozen=True)
|
|
174
|
+
class Id:
|
|
175
|
+
"""Identifier for an environment."""
|
|
176
|
+
environment_id: str
|
|
177
|
+
|
|
178
|
+
def __str__(self) -> str:
|
|
179
|
+
return self.environment_id
|
|
180
|
+
|
|
181
|
+
def working_dir(self, root_dir: str | None) -> str | None:
|
|
182
|
+
"""Returns the download directory for the service."""
|
|
183
|
+
if root_dir is None:
|
|
184
|
+
return None
|
|
185
|
+
return os.path.join(root_dir, _make_path_compatible(self.environment_id))
|
|
186
|
+
|
|
483
187
|
class Status(enum.Enum):
|
|
484
188
|
"""Environment state.
|
|
485
189
|
|
|
@@ -502,13 +206,6 @@ class Environment(pg.Object):
|
|
|
502
206
|
'Features to be exposed by the environment.'
|
|
503
207
|
] = {}
|
|
504
208
|
|
|
505
|
-
event_handlers: Annotated[
|
|
506
|
-
list[EnvironmentEventHandler],
|
|
507
|
-
(
|
|
508
|
-
'User handler for the environment events.'
|
|
509
|
-
)
|
|
510
|
-
] = []
|
|
511
|
-
|
|
512
209
|
_ENV_STACK: Annotated[
|
|
513
210
|
ClassVar[list['Environment']],
|
|
514
211
|
'Recording the environments stacked through context managers.'
|
|
@@ -520,7 +217,7 @@ class Environment(pg.Object):
|
|
|
520
217
|
|
|
521
218
|
@property
|
|
522
219
|
@abc.abstractmethod
|
|
523
|
-
def id(self) ->
|
|
220
|
+
def id(self) -> Id:
|
|
524
221
|
"""Returns the identifier for the environment."""
|
|
525
222
|
|
|
526
223
|
@property
|
|
@@ -584,6 +281,10 @@ class Environment(pg.Object):
|
|
|
584
281
|
Environment._ENV_STACK.pop()
|
|
585
282
|
self.shutdown()
|
|
586
283
|
|
|
284
|
+
def __del__(self):
|
|
285
|
+
"""Deletes the environment."""
|
|
286
|
+
self.shutdown()
|
|
287
|
+
|
|
587
288
|
@classmethod
|
|
588
289
|
def current(cls) -> Optional['Environment']:
|
|
589
290
|
"""Returns the current environment."""
|
|
@@ -624,56 +325,78 @@ class Environment(pg.Object):
|
|
|
624
325
|
raise AttributeError(name)
|
|
625
326
|
|
|
626
327
|
|
|
328
|
+
# Enable automatic conversion from str to Environment.Id.
|
|
329
|
+
pg.typing.register_converter(str, Environment.Id, Environment.Id)
|
|
330
|
+
|
|
331
|
+
|
|
627
332
|
class Sandbox(pg.Object):
|
|
628
333
|
"""Interface for sandboxes."""
|
|
629
334
|
|
|
335
|
+
@dataclasses.dataclass(frozen=True, slots=True)
|
|
336
|
+
class Id:
|
|
337
|
+
"""Identifier for a sandbox."""
|
|
338
|
+
environment_id: Environment.Id
|
|
339
|
+
sandbox_id: str
|
|
340
|
+
|
|
341
|
+
def __str__(self) -> str:
|
|
342
|
+
return f'{self.environment_id}/{self.sandbox_id}'
|
|
343
|
+
|
|
344
|
+
def working_dir(self, root_dir: str | None) -> str | None:
|
|
345
|
+
"""Returns the download directory for the sandbox."""
|
|
346
|
+
if root_dir is None:
|
|
347
|
+
return None
|
|
348
|
+
return os.path.join(
|
|
349
|
+
self.environment_id.working_dir(root_dir),
|
|
350
|
+
_make_path_compatible(self.sandbox_id)
|
|
351
|
+
)
|
|
352
|
+
|
|
630
353
|
class Status(enum.Enum):
|
|
631
|
-
"""Sandbox state.
|
|
354
|
+
r"""Sandbox state.
|
|
632
355
|
|
|
633
356
|
State transitions:
|
|
634
357
|
|
|
635
|
-
|
|
636
|
-
|
|
637
|
-
|
|
638
|
-
|
|
639
|
-
|
|
640
|
-
|
|
641
|
-
|
|
642
|
-
|
|
643
|
-
|
|
644
|
-
|
|
645
|
-
|
|
646
|
-
|
|
647
|
-
|
|
648
|
-
|
|
649
|
-
|
|
650
|
-
|
|
651
|
-
|
|
652
|
-
|
|
653
|
-
|
|
654
|
-
|
|
655
|
-
|
|
656
|
-
|
|
657
|
-
|
|
658
|
-
|
|
659
|
-
|
|
660
|
-
|
|
661
|
-
|
|
662
|
-
|
|
663
|
-
|
|
664
|
-
|
|
665
|
-
|
|
666
|
-
|
|
667
|
-
|
|
668
|
-
|
|
669
|
-
|
|
670
|
-
|
|
671
|
-
|
|
672
|
-
|
|
673
|
-
|
|
674
|
-
|
|
675
|
-
|
|
676
|
-
|
|
358
|
+
(sandbox / feature
|
|
359
|
+
+------------+ teardown) +---------------+
|
|
360
|
+
| <OFFLINE> | <--------------------- | SHUTTING_DOWN |
|
|
361
|
+
+------------+ +---------------+
|
|
362
|
+
^ ^
|
|
363
|
+
/ \
|
|
364
|
+
(setup failed) / \
|
|
365
|
+
/ \
|
|
366
|
+
+-----------+ (start) +------------+ \
|
|
367
|
+
| <CREATED> | --------> | SETTING_UP | \
|
|
368
|
+
+-----------+ ^ +------------+ \
|
|
369
|
+
/ | \
|
|
370
|
+
/ | (sandbox / \
|
|
371
|
+
/ | feature /session \
|
|
372
|
+
/ v setup succeeded) \
|
|
373
|
+
/ +---------+ \
|
|
374
|
+
/ | READY | \
|
|
375
|
+
/ +---------+ \
|
|
376
|
+
/ | \
|
|
377
|
+
/ | (acquire) \
|
|
378
|
+
/ v \
|
|
379
|
+
/ +----------+ \
|
|
380
|
+
| | ACQUIRED | \
|
|
381
|
+
| +----------+ |
|
|
382
|
+
| | |
|
|
383
|
+
| | (start_session) |
|
|
384
|
+
| +------------+ |
|
|
385
|
+
| | SETTING_UP |-- (setup failed) ------>+
|
|
386
|
+
| +------------+ |
|
|
387
|
+
| | |
|
|
388
|
+
| v (succeeded) |
|
|
389
|
+
| +--------------+ |
|
|
390
|
+
| | IN_SESSION |- (op failed) -------->+
|
|
391
|
+
| +--------------+ |
|
|
392
|
+
| | |
|
|
393
|
+
| | (end_session) |
|
|
394
|
+
| | |
|
|
395
|
+
| v (session teardown |
|
|
396
|
+
(setup next +-----------------+ failed OR |
|
|
397
|
+
session for <---------| EXITING_SESSION |- non-reusable -----+
|
|
398
|
+
reusable sandbox) +-----------------+ sandbox)
|
|
399
|
+
|
|
677
400
|
"""
|
|
678
401
|
|
|
679
402
|
# The sandbox is created, but not yet started.
|
|
@@ -712,7 +435,7 @@ class Sandbox(pg.Object):
|
|
|
712
435
|
|
|
713
436
|
@property
|
|
714
437
|
@abc.abstractmethod
|
|
715
|
-
def id(self) ->
|
|
438
|
+
def id(self) -> Id:
|
|
716
439
|
"""Returns the identifier for the sandbox."""
|
|
717
440
|
|
|
718
441
|
@property
|
|
@@ -735,24 +458,6 @@ class Sandbox(pg.Object):
|
|
|
735
458
|
"""Returns True if the sandbox is online."""
|
|
736
459
|
return self.status.is_online
|
|
737
460
|
|
|
738
|
-
@abc.abstractmethod
|
|
739
|
-
def set_acquired(self) -> None:
|
|
740
|
-
"""Marks the sandbox as acquired."""
|
|
741
|
-
|
|
742
|
-
@abc.abstractmethod
|
|
743
|
-
def add_event_handler(
|
|
744
|
-
self,
|
|
745
|
-
event_handler: EnvironmentEventHandler
|
|
746
|
-
) -> None:
|
|
747
|
-
"""Sets the status of the sandbox."""
|
|
748
|
-
|
|
749
|
-
@abc.abstractmethod
|
|
750
|
-
def remove_event_handler(
|
|
751
|
-
self,
|
|
752
|
-
event_handler: EnvironmentEventHandler
|
|
753
|
-
) -> None:
|
|
754
|
-
"""Removes the status of the sandbox."""
|
|
755
|
-
|
|
756
461
|
@property
|
|
757
462
|
@abc.abstractmethod
|
|
758
463
|
def state_errors(self) -> list[SandboxStateError]:
|
|
@@ -970,6 +675,10 @@ class Sandbox(pg.Object):
|
|
|
970
675
|
return self.features[name]
|
|
971
676
|
raise AttributeError(name)
|
|
972
677
|
|
|
678
|
+
def __del__(self):
|
|
679
|
+
"""Deletes the sandbox."""
|
|
680
|
+
self.shutdown()
|
|
681
|
+
|
|
973
682
|
|
|
974
683
|
class Feature(pg.Object):
|
|
975
684
|
"""Interface for sandbox features."""
|
|
@@ -1101,3 +810,17 @@ class Feature(pg.Object):
|
|
|
1101
810
|
"""Returns the current user session identifier."""
|
|
1102
811
|
assert self.sandbox is not None
|
|
1103
812
|
return self.sandbox.session_id
|
|
813
|
+
|
|
814
|
+
|
|
815
|
+
def _make_path_compatible(id_str: str) -> str:
|
|
816
|
+
"""Makes a path compatible with CNS."""
|
|
817
|
+
return id_str.translate(
|
|
818
|
+
str.maketrans({
|
|
819
|
+
'@': '_',
|
|
820
|
+
':': '_',
|
|
821
|
+
'#': '_',
|
|
822
|
+
' ': '',
|
|
823
|
+
'<': '',
|
|
824
|
+
'>': '',
|
|
825
|
+
})
|
|
826
|
+
)
|
langfun/env/interface_test.py
CHANGED
|
@@ -18,7 +18,7 @@ from langfun.env import interface
|
|
|
18
18
|
class IdTest(unittest.TestCase):
|
|
19
19
|
|
|
20
20
|
def test_environment_id(self):
|
|
21
|
-
env_id = interface.
|
|
21
|
+
env_id = interface.Environment.Id('env@1/a b:c#def')
|
|
22
22
|
self.assertEqual(str(env_id), 'env@1/a b:c#def')
|
|
23
23
|
self.assertEqual(
|
|
24
24
|
env_id.working_dir(root_dir='/tmp'),
|
|
@@ -27,8 +27,8 @@ class IdTest(unittest.TestCase):
|
|
|
27
27
|
self.assertIsNone(env_id.working_dir(root_dir=None))
|
|
28
28
|
|
|
29
29
|
def test_sandbox_id(self):
|
|
30
|
-
sandbox_id = interface.
|
|
31
|
-
environment_id=interface.
|
|
30
|
+
sandbox_id = interface.Sandbox.Id(
|
|
31
|
+
environment_id=interface.Environment.Id('env'),
|
|
32
32
|
sandbox_id='sandbox'
|
|
33
33
|
)
|
|
34
34
|
self.assertEqual(str(sandbox_id), 'env/sandbox')
|
|
@@ -28,9 +28,9 @@ class TestingSandbox(interface.Sandbox):
|
|
|
28
28
|
self._session_id = None
|
|
29
29
|
|
|
30
30
|
@property
|
|
31
|
-
def id(self) -> interface.
|
|
32
|
-
return interface.
|
|
33
|
-
environment_id=interface.
|
|
31
|
+
def id(self) -> interface.Sandbox.Id:
|
|
32
|
+
return interface.Sandbox.Id(
|
|
33
|
+
environment_id=interface.Environment.Id('testing-env'),
|
|
34
34
|
sandbox_id=self.sandbox_id
|
|
35
35
|
)
|
|
36
36
|
|
|
@@ -52,18 +52,6 @@ class TestingSandbox(interface.Sandbox):
|
|
|
52
52
|
def set_acquired(self) -> None:
|
|
53
53
|
self.set_status(self.Status.ACQUIRED)
|
|
54
54
|
|
|
55
|
-
def add_event_handler(
|
|
56
|
-
self,
|
|
57
|
-
event_handler: interface.EnvironmentEventHandler
|
|
58
|
-
) -> None:
|
|
59
|
-
pass
|
|
60
|
-
|
|
61
|
-
def remove_event_handler(
|
|
62
|
-
self,
|
|
63
|
-
event_handler: interface.EnvironmentEventHandler
|
|
64
|
-
) -> None:
|
|
65
|
-
pass
|
|
66
|
-
|
|
67
55
|
def start(self) -> None:
|
|
68
56
|
self.set_alive()
|
|
69
57
|
|