modal 1.0.5.dev2__py3-none-any.whl → 1.0.5.dev3__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.
- modal/_clustered_functions.pyi +13 -3
- modal/_runtime/container_io_manager.pyi +222 -40
- modal/_runtime/execution_context.pyi +60 -6
- modal/_tunnel.pyi +380 -12
- modal/app.pyi +658 -48
- modal/client.pyi +224 -28
- modal/cloud_bucket_mount.pyi +192 -4
- modal/cls.pyi +442 -35
- modal/container_process.pyi +103 -14
- modal/dict.pyi +453 -51
- modal/environments.pyi +41 -9
- modal/file_io.pyi +236 -45
- modal/functions.pyi +543 -56
- modal/image.pyi +1256 -74
- modal/io_streams.pyi +342 -39
- modal/mount.pyi +261 -31
- modal/network_file_system.pyi +307 -26
- modal/object.pyi +48 -9
- modal/parallel_map.pyi +144 -14
- modal/partial_function.pyi +255 -14
- modal/proxy.pyi +28 -3
- modal/queue.pyi +447 -30
- modal/runner.pyi +160 -22
- modal/sandbox.pyi +310 -50
- modal/secret.pyi +164 -15
- modal/snapshot.pyi +25 -4
- modal/token_flow.pyi +28 -8
- modal/volume.pyi +649 -59
- {modal-1.0.5.dev2.dist-info → modal-1.0.5.dev3.dist-info}/METADATA +1 -1
- {modal-1.0.5.dev2.dist-info → modal-1.0.5.dev3.dist-info}/RECORD +35 -35
- modal_version/__init__.py +1 -1
- {modal-1.0.5.dev2.dist-info → modal-1.0.5.dev3.dist-info}/WHEEL +0 -0
- {modal-1.0.5.dev2.dist-info → modal-1.0.5.dev3.dist-info}/entry_points.txt +0 -0
- {modal-1.0.5.dev2.dist-info → modal-1.0.5.dev3.dist-info}/licenses/LICENSE +0 -0
- {modal-1.0.5.dev2.dist-info → modal-1.0.5.dev3.dist-info}/top_level.txt +0 -0
modal/cls.pyi
CHANGED
@@ -24,6 +24,8 @@ def _use_annotation_parameters(user_cls: type) -> bool: ...
|
|
24
24
|
def _get_class_constructor_signature(user_cls: type) -> inspect.Signature: ...
|
25
25
|
|
26
26
|
class _ServiceOptions:
|
27
|
+
"""_ServiceOptions(secrets: Collection[modal.secret._Secret] = (), validated_volumes: Sequence[tuple[str, modal.volume._Volume]] = (), resources: Optional[modal_proto.api_pb2.Resources] = None, retry_policy: Optional[modal_proto.api_pb2.FunctionRetryPolicy] = None, max_containers: Optional[int] = None, buffer_containers: Optional[int] = None, scaledown_window: Optional[int] = None, timeout_secs: Optional[int] = None, max_concurrent_inputs: Optional[int] = None, target_concurrent_inputs: Optional[int] = None, batch_max_size: Optional[int] = None, batch_wait_ms: Optional[int] = None)"""
|
28
|
+
|
27
29
|
secrets: typing.Collection[modal.secret._Secret]
|
28
30
|
validated_volumes: typing.Sequence[tuple[str, modal.volume._Volume]]
|
29
31
|
resources: typing.Optional[modal_proto.api_pb2.Resources]
|
@@ -37,7 +39,13 @@ class _ServiceOptions:
|
|
37
39
|
batch_max_size: typing.Optional[int]
|
38
40
|
batch_wait_ms: typing.Optional[int]
|
39
41
|
|
40
|
-
def merge_options(self, new_options: _ServiceOptions) -> _ServiceOptions:
|
42
|
+
def merge_options(self, new_options: _ServiceOptions) -> _ServiceOptions:
|
43
|
+
"""Implement protobuf-like MergeFrom semantics for this dataclass.
|
44
|
+
|
45
|
+
This mostly exists to support "stacking" of `.with_options()` calls.
|
46
|
+
"""
|
47
|
+
...
|
48
|
+
|
41
49
|
def __init__(
|
42
50
|
self,
|
43
51
|
secrets: typing.Collection[modal.secret._Secret] = (),
|
@@ -52,13 +60,32 @@ class _ServiceOptions:
|
|
52
60
|
target_concurrent_inputs: typing.Optional[int] = None,
|
53
61
|
batch_max_size: typing.Optional[int] = None,
|
54
62
|
batch_wait_ms: typing.Optional[int] = None,
|
55
|
-
) -> None:
|
56
|
-
|
57
|
-
|
63
|
+
) -> None:
|
64
|
+
"""Initialize self. See help(type(self)) for accurate signature."""
|
65
|
+
...
|
66
|
+
|
67
|
+
def __repr__(self):
|
68
|
+
"""Return repr(self)."""
|
69
|
+
...
|
58
70
|
|
59
|
-
def
|
71
|
+
def __eq__(self, other):
|
72
|
+
"""Return self==value."""
|
73
|
+
...
|
74
|
+
|
75
|
+
def _bind_instance_method(cls: _Cls, service_function: modal._functions._Function, method_name: str):
|
76
|
+
"""Binds an "instance service function" to a specific method using metadata for that method
|
77
|
+
|
78
|
+
This "dummy" _Function gets no unique object_id and isn't backend-backed at all, since all
|
79
|
+
it does it forward invocations to the underlying instance_service_function with the specified method
|
80
|
+
"""
|
81
|
+
...
|
60
82
|
|
61
83
|
class _Obj:
|
84
|
+
"""An instance of a `Cls`, i.e. `Cls("foo", 42)` returns an `Obj`.
|
85
|
+
|
86
|
+
All this class does is to return `Function` objects.
|
87
|
+
"""
|
88
|
+
|
62
89
|
_cls: _Cls
|
63
90
|
_functions: dict[str, modal._functions._Function]
|
64
91
|
_has_entered: bool
|
@@ -70,7 +97,10 @@ class _Obj:
|
|
70
97
|
|
71
98
|
def __init__(
|
72
99
|
self, cls: _Cls, user_cls: typing.Optional[type], options: typing.Optional[_ServiceOptions], args, kwargs
|
73
|
-
):
|
100
|
+
):
|
101
|
+
"""Initialize self. See help(type(self)) for accurate signature."""
|
102
|
+
...
|
103
|
+
|
74
104
|
def _cached_service_function(self) -> modal._functions._Function: ...
|
75
105
|
def _get_parameter_values(self) -> dict[str, typing.Any]: ...
|
76
106
|
def _new_user_cls_instance(self): ...
|
@@ -81,9 +111,59 @@ class _Obj:
|
|
81
111
|
max_containers: typing.Optional[int] = None,
|
82
112
|
scaledown_window: typing.Optional[int] = None,
|
83
113
|
buffer_containers: typing.Optional[int] = None,
|
84
|
-
) -> None:
|
85
|
-
|
86
|
-
|
114
|
+
) -> None:
|
115
|
+
"""Override the current autoscaler behavior for this Cls instance.
|
116
|
+
|
117
|
+
Unspecified parameters will retain their current value, i.e. either the static value
|
118
|
+
from the function decorator, or an override value from a previous call to this method.
|
119
|
+
|
120
|
+
Subsequent deployments of the App containing this Cls will reset the autoscaler back to
|
121
|
+
its static configuration.
|
122
|
+
|
123
|
+
Note: When calling this method on a Cls that is defined locally, static type checkers will
|
124
|
+
issue an error, because the object will appear to have the user-defined type.
|
125
|
+
|
126
|
+
Examples:
|
127
|
+
|
128
|
+
```python notest
|
129
|
+
Model = modal.Cls.from_name("my-app", "Model")
|
130
|
+
model = Model() # This method is called on an *instance* of the class
|
131
|
+
|
132
|
+
# Always have at least 2 containers running, with an extra buffer when the Function is active
|
133
|
+
model.update_autoscaler(min_containers=2, buffer_containers=1)
|
134
|
+
|
135
|
+
# Limit this Function to avoid spinning up more than 5 containers
|
136
|
+
f.update_autoscaler(max_containers=5)
|
137
|
+
```
|
138
|
+
"""
|
139
|
+
...
|
140
|
+
|
141
|
+
async def keep_warm(self, warm_pool_size: int) -> None:
|
142
|
+
"""mdmd:hidden
|
143
|
+
Set the warm pool size for the class containers
|
144
|
+
|
145
|
+
DEPRECATED: Please adapt your code to use the more general `update_autoscaler` method instead:
|
146
|
+
|
147
|
+
```python notest
|
148
|
+
Model = modal.Cls.from_name("my-app", "Model")
|
149
|
+
model = Model() # This method is called on an *instance* of the class
|
150
|
+
|
151
|
+
# Old pattern (deprecated)
|
152
|
+
model.keep_warm(2)
|
153
|
+
|
154
|
+
# New pattern
|
155
|
+
model.update_autoscaler(min_containers=2)
|
156
|
+
```
|
157
|
+
"""
|
158
|
+
...
|
159
|
+
|
160
|
+
def _cached_user_cls_instance(self):
|
161
|
+
"""Get or construct the local object
|
162
|
+
|
163
|
+
Used for .local() calls and getting attributes of classes
|
164
|
+
"""
|
165
|
+
...
|
166
|
+
|
87
167
|
def _enter(self): ...
|
88
168
|
@property
|
89
169
|
def _entered(self) -> bool: ...
|
@@ -95,6 +175,11 @@ class _Obj:
|
|
95
175
|
SUPERSELF = typing.TypeVar("SUPERSELF", covariant=True)
|
96
176
|
|
97
177
|
class Obj:
|
178
|
+
"""An instance of a `Cls`, i.e. `Cls("foo", 42)` returns an `Obj`.
|
179
|
+
|
180
|
+
All this class does is to return `Function` objects.
|
181
|
+
"""
|
182
|
+
|
98
183
|
_cls: Cls
|
99
184
|
_functions: dict[str, modal.functions.Function]
|
100
185
|
_has_entered: bool
|
@@ -120,7 +205,33 @@ class Obj:
|
|
120
205
|
max_containers: typing.Optional[int] = None,
|
121
206
|
scaledown_window: typing.Optional[int] = None,
|
122
207
|
buffer_containers: typing.Optional[int] = None,
|
123
|
-
) -> None:
|
208
|
+
) -> None:
|
209
|
+
"""Override the current autoscaler behavior for this Cls instance.
|
210
|
+
|
211
|
+
Unspecified parameters will retain their current value, i.e. either the static value
|
212
|
+
from the function decorator, or an override value from a previous call to this method.
|
213
|
+
|
214
|
+
Subsequent deployments of the App containing this Cls will reset the autoscaler back to
|
215
|
+
its static configuration.
|
216
|
+
|
217
|
+
Note: When calling this method on a Cls that is defined locally, static type checkers will
|
218
|
+
issue an error, because the object will appear to have the user-defined type.
|
219
|
+
|
220
|
+
Examples:
|
221
|
+
|
222
|
+
```python notest
|
223
|
+
Model = modal.Cls.from_name("my-app", "Model")
|
224
|
+
model = Model() # This method is called on an *instance* of the class
|
225
|
+
|
226
|
+
# Always have at least 2 containers running, with an extra buffer when the Function is active
|
227
|
+
model.update_autoscaler(min_containers=2, buffer_containers=1)
|
228
|
+
|
229
|
+
# Limit this Function to avoid spinning up more than 5 containers
|
230
|
+
f.update_autoscaler(max_containers=5)
|
231
|
+
```
|
232
|
+
"""
|
233
|
+
...
|
234
|
+
|
124
235
|
async def aio(
|
125
236
|
self,
|
126
237
|
/,
|
@@ -129,17 +240,83 @@ class Obj:
|
|
129
240
|
max_containers: typing.Optional[int] = None,
|
130
241
|
scaledown_window: typing.Optional[int] = None,
|
131
242
|
buffer_containers: typing.Optional[int] = None,
|
132
|
-
) -> None:
|
243
|
+
) -> None:
|
244
|
+
"""Override the current autoscaler behavior for this Cls instance.
|
245
|
+
|
246
|
+
Unspecified parameters will retain their current value, i.e. either the static value
|
247
|
+
from the function decorator, or an override value from a previous call to this method.
|
248
|
+
|
249
|
+
Subsequent deployments of the App containing this Cls will reset the autoscaler back to
|
250
|
+
its static configuration.
|
251
|
+
|
252
|
+
Note: When calling this method on a Cls that is defined locally, static type checkers will
|
253
|
+
issue an error, because the object will appear to have the user-defined type.
|
254
|
+
|
255
|
+
Examples:
|
256
|
+
|
257
|
+
```python notest
|
258
|
+
Model = modal.Cls.from_name("my-app", "Model")
|
259
|
+
model = Model() # This method is called on an *instance* of the class
|
260
|
+
|
261
|
+
# Always have at least 2 containers running, with an extra buffer when the Function is active
|
262
|
+
model.update_autoscaler(min_containers=2, buffer_containers=1)
|
263
|
+
|
264
|
+
# Limit this Function to avoid spinning up more than 5 containers
|
265
|
+
f.update_autoscaler(max_containers=5)
|
266
|
+
```
|
267
|
+
"""
|
268
|
+
...
|
133
269
|
|
134
270
|
update_autoscaler: __update_autoscaler_spec[typing_extensions.Self]
|
135
271
|
|
136
272
|
class __keep_warm_spec(typing_extensions.Protocol[SUPERSELF]):
|
137
|
-
def __call__(self, /, warm_pool_size: int) -> None:
|
138
|
-
|
273
|
+
def __call__(self, /, warm_pool_size: int) -> None:
|
274
|
+
"""mdmd:hidden
|
275
|
+
Set the warm pool size for the class containers
|
276
|
+
|
277
|
+
DEPRECATED: Please adapt your code to use the more general `update_autoscaler` method instead:
|
278
|
+
|
279
|
+
```python notest
|
280
|
+
Model = modal.Cls.from_name("my-app", "Model")
|
281
|
+
model = Model() # This method is called on an *instance* of the class
|
282
|
+
|
283
|
+
# Old pattern (deprecated)
|
284
|
+
model.keep_warm(2)
|
285
|
+
|
286
|
+
# New pattern
|
287
|
+
model.update_autoscaler(min_containers=2)
|
288
|
+
```
|
289
|
+
"""
|
290
|
+
...
|
291
|
+
|
292
|
+
async def aio(self, /, warm_pool_size: int) -> None:
|
293
|
+
"""mdmd:hidden
|
294
|
+
Set the warm pool size for the class containers
|
295
|
+
|
296
|
+
DEPRECATED: Please adapt your code to use the more general `update_autoscaler` method instead:
|
297
|
+
|
298
|
+
```python notest
|
299
|
+
Model = modal.Cls.from_name("my-app", "Model")
|
300
|
+
model = Model() # This method is called on an *instance* of the class
|
301
|
+
|
302
|
+
# Old pattern (deprecated)
|
303
|
+
model.keep_warm(2)
|
304
|
+
|
305
|
+
# New pattern
|
306
|
+
model.update_autoscaler(min_containers=2)
|
307
|
+
```
|
308
|
+
"""
|
309
|
+
...
|
139
310
|
|
140
311
|
keep_warm: __keep_warm_spec[typing_extensions.Self]
|
141
312
|
|
142
|
-
def _cached_user_cls_instance(self):
|
313
|
+
def _cached_user_cls_instance(self):
|
314
|
+
"""Get or construct the local object
|
315
|
+
|
316
|
+
Used for .local() calls and getting attributes of classes
|
317
|
+
"""
|
318
|
+
...
|
319
|
+
|
143
320
|
def _enter(self): ...
|
144
321
|
@property
|
145
322
|
def _entered(self) -> bool: ...
|
@@ -149,6 +326,13 @@ class Obj:
|
|
149
326
|
def __getattr__(self, k): ...
|
150
327
|
|
151
328
|
class _Cls(modal._object._Object):
|
329
|
+
"""Cls adds method pooling and [lifecycle hook](/docs/guide/lifecycle-functions) behavior
|
330
|
+
to [modal.Function](/docs/reference/modal.Function).
|
331
|
+
|
332
|
+
Generally, you will not construct a Cls directly.
|
333
|
+
Instead, use the [`@app.cls()`](/docs/reference/modal.App#cls) decorator on the App object.
|
334
|
+
"""
|
335
|
+
|
152
336
|
_class_service_function: typing.Optional[modal._functions._Function]
|
153
337
|
_options: _ServiceOptions
|
154
338
|
_app: typing.Optional[modal.app._App]
|
@@ -168,13 +352,31 @@ class _Cls(modal._object._Object):
|
|
168
352
|
def _get_method_names(self) -> collections.abc.Collection[str]: ...
|
169
353
|
def _hydrate_metadata(self, metadata: google.protobuf.message.Message): ...
|
170
354
|
@staticmethod
|
171
|
-
def validate_construction_mechanism(user_cls):
|
355
|
+
def validate_construction_mechanism(user_cls):
|
356
|
+
"""mdmd:hidden"""
|
357
|
+
...
|
358
|
+
|
172
359
|
@staticmethod
|
173
|
-
def from_local(user_cls, app: modal.app._App, class_service_function: modal._functions._Function) -> _Cls:
|
360
|
+
def from_local(user_cls, app: modal.app._App, class_service_function: modal._functions._Function) -> _Cls:
|
361
|
+
"""mdmd:hidden"""
|
362
|
+
...
|
363
|
+
|
174
364
|
@classmethod
|
175
365
|
def from_name(
|
176
366
|
cls: type[_Cls], app_name: str, name: str, *, namespace=1, environment_name: typing.Optional[str] = None
|
177
|
-
) -> _Cls:
|
367
|
+
) -> _Cls:
|
368
|
+
"""Reference a Cls from a deployed App by its name.
|
369
|
+
|
370
|
+
In contrast to `modal.Cls.lookup`, this is a lazy method
|
371
|
+
that defers hydrating the local object with metadata from
|
372
|
+
Modal servers until the first time it is actually used.
|
373
|
+
|
374
|
+
```python
|
375
|
+
Model = modal.Cls.from_name("other-app", "Model")
|
376
|
+
```
|
377
|
+
"""
|
378
|
+
...
|
379
|
+
|
178
380
|
def with_options(
|
179
381
|
self: _Cls,
|
180
382
|
*,
|
@@ -191,9 +393,62 @@ class _Cls(modal._object._Object):
|
|
191
393
|
concurrency_limit: typing.Optional[int] = None,
|
192
394
|
container_idle_timeout: typing.Optional[int] = None,
|
193
395
|
allow_concurrent_inputs: typing.Optional[int] = None,
|
194
|
-
) -> _Cls:
|
195
|
-
|
196
|
-
|
396
|
+
) -> _Cls:
|
397
|
+
"""Override the static Function configuration at runtime.
|
398
|
+
|
399
|
+
This method will return a new instance of the cls that will autoscale independently of the
|
400
|
+
original instance. Note that options cannot be "unset" with this method (i.e., if a GPU
|
401
|
+
is configured in the `@app.cls()` decorator, passing `gpu=None` here will not create a
|
402
|
+
CPU-only instance).
|
403
|
+
|
404
|
+
**Usage:**
|
405
|
+
|
406
|
+
You can use this method after looking up the Cls from a deployed App or if you have a
|
407
|
+
direct reference to a Cls from another Function or local entrypoint on its App:
|
408
|
+
|
409
|
+
```python notest
|
410
|
+
Model = modal.Cls.from_name("my_app", "Model")
|
411
|
+
ModelUsingGPU = Model.with_options(gpu="A100")
|
412
|
+
ModelUsingGPU().generate.remote(input_prompt) # Run with an A100 GPU
|
413
|
+
```
|
414
|
+
|
415
|
+
The method can be called multiple times to "stack" updates:
|
416
|
+
|
417
|
+
```python notest
|
418
|
+
Model.with_options(gpu="A100").with_options(scaledown_window=300) # Use an A100 with slow scaledown
|
419
|
+
```
|
420
|
+
|
421
|
+
Note that container arguments (i.e. `volumes` and `secrets`) passed in subsequent calls
|
422
|
+
will not be merged.
|
423
|
+
"""
|
424
|
+
...
|
425
|
+
|
426
|
+
def with_concurrency(self: _Cls, *, max_inputs: int, target_inputs: typing.Optional[int] = None) -> _Cls:
|
427
|
+
"""Create an instance of the Cls with input concurrency enabled or overridden with new values.
|
428
|
+
|
429
|
+
**Usage:**
|
430
|
+
|
431
|
+
```python notest
|
432
|
+
Model = modal.Cls.from_name("my_app", "Model")
|
433
|
+
ModelUsingGPU = Model.with_options(gpu="A100").with_concurrency(max_inputs=100)
|
434
|
+
ModelUsingGPU().generate.remote(42) # will run on an A100 GPU with input concurrency enabled
|
435
|
+
```
|
436
|
+
"""
|
437
|
+
...
|
438
|
+
|
439
|
+
def with_batching(self: _Cls, *, max_batch_size: int, wait_ms: int) -> _Cls:
|
440
|
+
"""Create an instance of the Cls with dynamic batching enabled or overridden with new values.
|
441
|
+
|
442
|
+
**Usage:**
|
443
|
+
|
444
|
+
```python notest
|
445
|
+
Model = modal.Cls.from_name("my_app", "Model")
|
446
|
+
ModelUsingGPU = Model.with_options(gpu="A100").with_batching(max_batch_size=100, batch_wait_ms=1000)
|
447
|
+
ModelUsingGPU().generate.remote(42) # will run on an A100 GPU with input concurrency enabled
|
448
|
+
```
|
449
|
+
"""
|
450
|
+
...
|
451
|
+
|
197
452
|
@staticmethod
|
198
453
|
async def lookup(
|
199
454
|
app_name: str,
|
@@ -201,12 +456,38 @@ class _Cls(modal._object._Object):
|
|
201
456
|
namespace=1,
|
202
457
|
client: typing.Optional[modal.client._Client] = None,
|
203
458
|
environment_name: typing.Optional[str] = None,
|
204
|
-
) -> _Cls:
|
205
|
-
|
459
|
+
) -> _Cls:
|
460
|
+
"""mdmd:hidden
|
461
|
+
Lookup a Cls from a deployed App by its name.
|
462
|
+
|
463
|
+
DEPRECATED: This method is deprecated in favor of `modal.Cls.from_name`.
|
464
|
+
|
465
|
+
In contrast to `modal.Cls.from_name`, this is an eager method
|
466
|
+
that will hydrate the local object with metadata from Modal servers.
|
467
|
+
|
468
|
+
```python notest
|
469
|
+
Model = modal.Cls.from_name("other-app", "Model")
|
470
|
+
model = Model()
|
471
|
+
model.inference(...)
|
472
|
+
```
|
473
|
+
"""
|
474
|
+
...
|
475
|
+
|
476
|
+
def __call__(self, *args, **kwargs) -> _Obj:
|
477
|
+
"""This acts as the class constructor."""
|
478
|
+
...
|
479
|
+
|
206
480
|
def __getattr__(self, k): ...
|
207
481
|
def _is_local(self) -> bool: ...
|
208
482
|
|
209
483
|
class Cls(modal.object.Object):
|
484
|
+
"""Cls adds method pooling and [lifecycle hook](/docs/guide/lifecycle-functions) behavior
|
485
|
+
to [modal.Function](/docs/reference/modal.Function).
|
486
|
+
|
487
|
+
Generally, you will not construct a Cls directly.
|
488
|
+
Instead, use the [`@app.cls()`](/docs/reference/modal.App#cls) decorator on the App object.
|
489
|
+
"""
|
490
|
+
|
210
491
|
_class_service_function: typing.Optional[modal.functions.Function]
|
211
492
|
_options: _ServiceOptions
|
212
493
|
_app: typing.Optional[modal.app.App]
|
@@ -216,7 +497,10 @@ class Cls(modal.object.Object):
|
|
216
497
|
_method_partials: typing.Optional[dict[str, modal.partial_function.PartialFunction]]
|
217
498
|
_callables: dict[str, collections.abc.Callable[..., typing.Any]]
|
218
499
|
|
219
|
-
def __init__(self, *args, **kwargs):
|
500
|
+
def __init__(self, *args, **kwargs):
|
501
|
+
"""mdmd:hidden"""
|
502
|
+
...
|
503
|
+
|
220
504
|
def _initialize_from_empty(self): ...
|
221
505
|
def _initialize_from_other(self, other: Cls): ...
|
222
506
|
def _get_partial_functions(self) -> dict[str, modal.partial_function.PartialFunction]: ...
|
@@ -227,13 +511,31 @@ class Cls(modal.object.Object):
|
|
227
511
|
def _get_method_names(self) -> collections.abc.Collection[str]: ...
|
228
512
|
def _hydrate_metadata(self, metadata: google.protobuf.message.Message): ...
|
229
513
|
@staticmethod
|
230
|
-
def validate_construction_mechanism(user_cls):
|
514
|
+
def validate_construction_mechanism(user_cls):
|
515
|
+
"""mdmd:hidden"""
|
516
|
+
...
|
517
|
+
|
231
518
|
@staticmethod
|
232
|
-
def from_local(user_cls, app: modal.app.App, class_service_function: modal.functions.Function) -> Cls:
|
519
|
+
def from_local(user_cls, app: modal.app.App, class_service_function: modal.functions.Function) -> Cls:
|
520
|
+
"""mdmd:hidden"""
|
521
|
+
...
|
522
|
+
|
233
523
|
@classmethod
|
234
524
|
def from_name(
|
235
525
|
cls: type[Cls], app_name: str, name: str, *, namespace=1, environment_name: typing.Optional[str] = None
|
236
|
-
) -> Cls:
|
526
|
+
) -> Cls:
|
527
|
+
"""Reference a Cls from a deployed App by its name.
|
528
|
+
|
529
|
+
In contrast to `modal.Cls.lookup`, this is a lazy method
|
530
|
+
that defers hydrating the local object with metadata from
|
531
|
+
Modal servers until the first time it is actually used.
|
532
|
+
|
533
|
+
```python
|
534
|
+
Model = modal.Cls.from_name("other-app", "Model")
|
535
|
+
```
|
536
|
+
"""
|
537
|
+
...
|
538
|
+
|
237
539
|
def with_options(
|
238
540
|
self: Cls,
|
239
541
|
*,
|
@@ -250,9 +552,61 @@ class Cls(modal.object.Object):
|
|
250
552
|
concurrency_limit: typing.Optional[int] = None,
|
251
553
|
container_idle_timeout: typing.Optional[int] = None,
|
252
554
|
allow_concurrent_inputs: typing.Optional[int] = None,
|
253
|
-
) -> Cls:
|
254
|
-
|
255
|
-
|
555
|
+
) -> Cls:
|
556
|
+
"""Override the static Function configuration at runtime.
|
557
|
+
|
558
|
+
This method will return a new instance of the cls that will autoscale independently of the
|
559
|
+
original instance. Note that options cannot be "unset" with this method (i.e., if a GPU
|
560
|
+
is configured in the `@app.cls()` decorator, passing `gpu=None` here will not create a
|
561
|
+
CPU-only instance).
|
562
|
+
|
563
|
+
**Usage:**
|
564
|
+
|
565
|
+
You can use this method after looking up the Cls from a deployed App or if you have a
|
566
|
+
direct reference to a Cls from another Function or local entrypoint on its App:
|
567
|
+
|
568
|
+
```python notest
|
569
|
+
Model = modal.Cls.from_name("my_app", "Model")
|
570
|
+
ModelUsingGPU = Model.with_options(gpu="A100")
|
571
|
+
ModelUsingGPU().generate.remote(input_prompt) # Run with an A100 GPU
|
572
|
+
```
|
573
|
+
|
574
|
+
The method can be called multiple times to "stack" updates:
|
575
|
+
|
576
|
+
```python notest
|
577
|
+
Model.with_options(gpu="A100").with_options(scaledown_window=300) # Use an A100 with slow scaledown
|
578
|
+
```
|
579
|
+
|
580
|
+
Note that container arguments (i.e. `volumes` and `secrets`) passed in subsequent calls
|
581
|
+
will not be merged.
|
582
|
+
"""
|
583
|
+
...
|
584
|
+
|
585
|
+
def with_concurrency(self: Cls, *, max_inputs: int, target_inputs: typing.Optional[int] = None) -> Cls:
|
586
|
+
"""Create an instance of the Cls with input concurrency enabled or overridden with new values.
|
587
|
+
|
588
|
+
**Usage:**
|
589
|
+
|
590
|
+
```python notest
|
591
|
+
Model = modal.Cls.from_name("my_app", "Model")
|
592
|
+
ModelUsingGPU = Model.with_options(gpu="A100").with_concurrency(max_inputs=100)
|
593
|
+
ModelUsingGPU().generate.remote(42) # will run on an A100 GPU with input concurrency enabled
|
594
|
+
```
|
595
|
+
"""
|
596
|
+
...
|
597
|
+
|
598
|
+
def with_batching(self: Cls, *, max_batch_size: int, wait_ms: int) -> Cls:
|
599
|
+
"""Create an instance of the Cls with dynamic batching enabled or overridden with new values.
|
600
|
+
|
601
|
+
**Usage:**
|
602
|
+
|
603
|
+
```python notest
|
604
|
+
Model = modal.Cls.from_name("my_app", "Model")
|
605
|
+
ModelUsingGPU = Model.with_options(gpu="A100").with_batching(max_batch_size=100, batch_wait_ms=1000)
|
606
|
+
ModelUsingGPU().generate.remote(42) # will run on an A100 GPU with input concurrency enabled
|
607
|
+
```
|
608
|
+
"""
|
609
|
+
...
|
256
610
|
|
257
611
|
class __lookup_spec(typing_extensions.Protocol):
|
258
612
|
def __call__(
|
@@ -263,7 +617,23 @@ class Cls(modal.object.Object):
|
|
263
617
|
namespace=1,
|
264
618
|
client: typing.Optional[modal.client.Client] = None,
|
265
619
|
environment_name: typing.Optional[str] = None,
|
266
|
-
) -> Cls:
|
620
|
+
) -> Cls:
|
621
|
+
"""mdmd:hidden
|
622
|
+
Lookup a Cls from a deployed App by its name.
|
623
|
+
|
624
|
+
DEPRECATED: This method is deprecated in favor of `modal.Cls.from_name`.
|
625
|
+
|
626
|
+
In contrast to `modal.Cls.from_name`, this is an eager method
|
627
|
+
that will hydrate the local object with metadata from Modal servers.
|
628
|
+
|
629
|
+
```python notest
|
630
|
+
Model = modal.Cls.from_name("other-app", "Model")
|
631
|
+
model = Model()
|
632
|
+
model.inference(...)
|
633
|
+
```
|
634
|
+
"""
|
635
|
+
...
|
636
|
+
|
267
637
|
async def aio(
|
268
638
|
self,
|
269
639
|
/,
|
@@ -272,11 +642,29 @@ class Cls(modal.object.Object):
|
|
272
642
|
namespace=1,
|
273
643
|
client: typing.Optional[modal.client.Client] = None,
|
274
644
|
environment_name: typing.Optional[str] = None,
|
275
|
-
) -> Cls:
|
645
|
+
) -> Cls:
|
646
|
+
"""mdmd:hidden
|
647
|
+
Lookup a Cls from a deployed App by its name.
|
648
|
+
|
649
|
+
DEPRECATED: This method is deprecated in favor of `modal.Cls.from_name`.
|
650
|
+
|
651
|
+
In contrast to `modal.Cls.from_name`, this is an eager method
|
652
|
+
that will hydrate the local object with metadata from Modal servers.
|
653
|
+
|
654
|
+
```python notest
|
655
|
+
Model = modal.Cls.from_name("other-app", "Model")
|
656
|
+
model = Model()
|
657
|
+
model.inference(...)
|
658
|
+
```
|
659
|
+
"""
|
660
|
+
...
|
276
661
|
|
277
662
|
lookup: __lookup_spec
|
278
663
|
|
279
|
-
def __call__(self, *args, **kwargs) -> Obj:
|
664
|
+
def __call__(self, *args, **kwargs) -> Obj:
|
665
|
+
"""This acts as the class constructor."""
|
666
|
+
...
|
667
|
+
|
280
668
|
def __getattr__(self, k): ...
|
281
669
|
def _is_local(self) -> bool: ...
|
282
670
|
|
@@ -293,7 +681,9 @@ class ___get_method_schemas_spec(typing_extensions.Protocol):
|
|
293
681
|
_get_method_schemas: ___get_method_schemas_spec
|
294
682
|
|
295
683
|
class _NO_DEFAULT:
|
296
|
-
def __repr__(self):
|
684
|
+
def __repr__(self):
|
685
|
+
"""Return repr(self)."""
|
686
|
+
...
|
297
687
|
|
298
688
|
_no_default: _NO_DEFAULT
|
299
689
|
|
@@ -301,8 +691,25 @@ class _Parameter:
|
|
301
691
|
default: typing.Any
|
302
692
|
init: bool
|
303
693
|
|
304
|
-
def __init__(self, default: typing.Any, init: bool):
|
694
|
+
def __init__(self, default: typing.Any, init: bool):
|
695
|
+
"""Initialize self. See help(type(self)) for accurate signature."""
|
696
|
+
...
|
697
|
+
|
305
698
|
def __get__(self, obj, obj_type=None) -> typing.Any: ...
|
306
699
|
|
307
700
|
def is_parameter(p: typing.Any) -> bool: ...
|
308
|
-
def parameter(*, default: typing.Any = modal.cls._NO_DEFAULT(), init: bool = True) -> typing.Any:
|
701
|
+
def parameter(*, default: typing.Any = modal.cls._NO_DEFAULT(), init: bool = True) -> typing.Any:
|
702
|
+
"""Used to specify options for modal.cls parameters, similar to dataclass.field for dataclasses
|
703
|
+
```
|
704
|
+
class A:
|
705
|
+
a: str = modal.parameter()
|
706
|
+
|
707
|
+
```
|
708
|
+
|
709
|
+
If `init=False` is specified, the field is not considered a parameter for the
|
710
|
+
Modal class and not used in the synthesized constructor. This can be used to
|
711
|
+
optionally annotate the type of a field that's used internally, for example values
|
712
|
+
being set by @enter lifecycle methods, without breaking type checkers, but it has
|
713
|
+
no runtime effect on the class.
|
714
|
+
"""
|
715
|
+
...
|