modal 1.1.2.dev37__tar.gz → 1.1.2.dev39__tar.gz
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-1.1.2.dev37 → modal-1.1.2.dev39}/PKG-INFO +1 -1
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/_container_entrypoint.py +6 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/_functions.py +1 -1
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/_runtime/asgi.py +3 -2
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/_runtime/container_io_manager.py +9 -4
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/_runtime/container_io_manager.pyi +32 -9
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/_utils/function_utils.py +4 -3
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/client.pyi +2 -2
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/functions.pyi +6 -6
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal.egg-info/PKG-INFO +1 -1
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal_version/__init__.py +1 -1
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/LICENSE +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/README.md +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/__init__.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/__main__.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/_clustered_functions.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/_clustered_functions.pyi +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/_ipython.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/_location.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/_object.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/_output.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/_partial_function.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/_pty.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/_resolver.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/_resources.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/_runtime/__init__.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/_runtime/execution_context.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/_runtime/execution_context.pyi +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/_runtime/gpu_memory_snapshot.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/_runtime/telemetry.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/_runtime/user_code_imports.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/_serialization.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/_traceback.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/_tunnel.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/_tunnel.pyi +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/_type_manager.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/_utils/__init__.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/_utils/app_utils.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/_utils/async_utils.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/_utils/auth_token_manager.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/_utils/blob_utils.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/_utils/bytes_io_segment_payload.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/_utils/deprecation.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/_utils/docker_utils.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/_utils/git_utils.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/_utils/grpc_testing.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/_utils/grpc_utils.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/_utils/hash_utils.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/_utils/http_utils.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/_utils/jwt_utils.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/_utils/logger.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/_utils/mount_utils.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/_utils/name_utils.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/_utils/package_utils.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/_utils/pattern_utils.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/_utils/rand_pb_testing.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/_utils/shell_utils.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/_utils/time_utils.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/_vendor/__init__.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/_vendor/a2wsgi_wsgi.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/_vendor/cloudpickle.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/_vendor/tblib.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/_watcher.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/app.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/app.pyi +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/builder/2023.12.312.txt +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/builder/2023.12.txt +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/builder/2024.04.txt +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/builder/2024.10.txt +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/builder/2025.06.txt +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/builder/PREVIEW.txt +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/builder/README.md +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/builder/base-images.json +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/call_graph.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/cli/__init__.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/cli/_download.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/cli/_traceback.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/cli/app.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/cli/cluster.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/cli/config.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/cli/container.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/cli/dict.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/cli/entry_point.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/cli/environment.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/cli/import_refs.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/cli/launch.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/cli/network_file_system.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/cli/profile.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/cli/programs/__init__.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/cli/programs/launch_instance_ssh.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/cli/programs/run_jupyter.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/cli/programs/run_marimo.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/cli/programs/vscode.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/cli/queues.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/cli/run.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/cli/secret.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/cli/token.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/cli/utils.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/cli/volume.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/client.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/cloud_bucket_mount.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/cloud_bucket_mount.pyi +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/cls.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/cls.pyi +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/config.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/container_process.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/container_process.pyi +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/dict.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/dict.pyi +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/environments.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/environments.pyi +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/exception.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/experimental/__init__.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/experimental/flash.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/experimental/flash.pyi +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/experimental/ipython.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/file_io.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/file_io.pyi +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/file_pattern_matcher.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/functions.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/gpu.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/image.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/image.pyi +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/io_streams.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/io_streams.pyi +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/mount.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/mount.pyi +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/network_file_system.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/network_file_system.pyi +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/object.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/object.pyi +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/output.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/parallel_map.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/parallel_map.pyi +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/partial_function.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/partial_function.pyi +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/proxy.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/proxy.pyi +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/py.typed +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/queue.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/queue.pyi +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/retries.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/runner.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/runner.pyi +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/running_app.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/sandbox.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/sandbox.pyi +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/schedule.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/scheduler_placement.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/secret.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/secret.pyi +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/serving.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/serving.pyi +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/snapshot.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/snapshot.pyi +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/stream_type.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/token_flow.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/token_flow.pyi +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/volume.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal/volume.pyi +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal.egg-info/SOURCES.txt +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal.egg-info/dependency_links.txt +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal.egg-info/entry_points.txt +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal.egg-info/requires.txt +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal.egg-info/top_level.txt +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal_docs/__init__.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal_docs/gen_cli_docs.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal_docs/gen_reference_docs.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal_docs/mdmd/__init__.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal_docs/mdmd/mdmd.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal_docs/mdmd/signatures.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal_proto/__init__.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal_proto/api.proto +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal_proto/api_grpc.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal_proto/api_pb2.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal_proto/api_pb2.pyi +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal_proto/api_pb2_grpc.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal_proto/api_pb2_grpc.pyi +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal_proto/modal_api_grpc.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal_proto/modal_options_grpc.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal_proto/options.proto +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal_proto/options_grpc.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal_proto/options_pb2.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal_proto/options_pb2.pyi +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal_proto/options_pb2_grpc.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal_proto/options_pb2_grpc.pyi +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal_proto/py.typed +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/modal_version/__main__.py +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/pyproject.toml +0 -0
- {modal-1.1.2.dev37 → modal-1.1.2.dev39}/setup.cfg +0 -0
@@ -198,9 +198,12 @@ def call_function(
|
|
198
198
|
# Send up to this many outputs at a time.
|
199
199
|
current_function_call_id = execution_context.current_function_call_id()
|
200
200
|
assert current_function_call_id is not None # Set above.
|
201
|
+
current_attempt_token = execution_context.current_attempt_token()
|
202
|
+
assert current_attempt_token is not None # Set above, but can be empty string.
|
201
203
|
generator_queue: asyncio.Queue[Any] = await container_io_manager._queue_create.aio(1024)
|
202
204
|
async with container_io_manager.generator_output_sender(
|
203
205
|
current_function_call_id,
|
206
|
+
current_attempt_token,
|
204
207
|
io_context.finalized_function.data_format,
|
205
208
|
generator_queue,
|
206
209
|
):
|
@@ -247,9 +250,12 @@ def call_function(
|
|
247
250
|
# Send up to this many outputs at a time.
|
248
251
|
current_function_call_id = execution_context.current_function_call_id()
|
249
252
|
assert current_function_call_id is not None # Set above.
|
253
|
+
current_attempt_token = execution_context.current_attempt_token()
|
254
|
+
assert current_attempt_token is not None # Set above, but can be empty string.
|
250
255
|
generator_queue: asyncio.Queue[Any] = container_io_manager._queue_create(1024)
|
251
256
|
with container_io_manager.generator_output_sender(
|
252
257
|
current_function_call_id,
|
258
|
+
current_attempt_token,
|
253
259
|
io_context.finalized_function.data_format,
|
254
260
|
generator_queue,
|
255
261
|
):
|
@@ -16,7 +16,7 @@ from modal.config import logger
|
|
16
16
|
from modal.exception import ExecutionError, InvalidError
|
17
17
|
from modal.experimental import stop_fetching_inputs
|
18
18
|
|
19
|
-
from .execution_context import current_function_call_id
|
19
|
+
from .execution_context import current_attempt_token, current_function_call_id
|
20
20
|
|
21
21
|
FIRST_MESSAGE_TIMEOUT_SECONDS = 5.0
|
22
22
|
|
@@ -106,6 +106,7 @@ def asgi_app_wrapper(asgi_app, container_io_manager) -> tuple[Callable[..., Asyn
|
|
106
106
|
raise ExecutionError("Unpexected state in ASGI scope")
|
107
107
|
scope["state"] = state
|
108
108
|
function_call_id = current_function_call_id()
|
109
|
+
attempt_token = current_attempt_token()
|
109
110
|
assert function_call_id, "internal error: function_call_id not set in asgi_app() scope"
|
110
111
|
|
111
112
|
messages_from_app: asyncio.Queue[dict[str, Any]] = asyncio.Queue(1)
|
@@ -142,7 +143,7 @@ def asgi_app_wrapper(asgi_app, container_io_manager) -> tuple[Callable[..., Asyn
|
|
142
143
|
# This initial message, "http.request" or "websocket.connect", should be sent
|
143
144
|
# immediately after starting the ASGI app's function call. If it is not received, that
|
144
145
|
# indicates a request cancellation or other abnormal circumstance.
|
145
|
-
message_gen = container_io_manager.get_data_in.aio(function_call_id)
|
146
|
+
message_gen = container_io_manager.get_data_in.aio(function_call_id, attempt_token)
|
146
147
|
first_message_task = asyncio.create_task(message_gen.__anext__())
|
147
148
|
|
148
149
|
try:
|
@@ -483,18 +483,21 @@ class _ContainerIOManager:
|
|
483
483
|
else {"data": data}
|
484
484
|
)
|
485
485
|
|
486
|
-
async def get_data_in(self, function_call_id: str) -> AsyncIterator[Any]:
|
486
|
+
async def get_data_in(self, function_call_id: str, attempt_token: Optional[str]) -> AsyncIterator[Any]:
|
487
487
|
"""Read from the `data_in` stream of a function call."""
|
488
488
|
stub = self._client.stub
|
489
489
|
if self.input_plane_server_url:
|
490
490
|
stub = await self._client.get_stub(self.input_plane_server_url)
|
491
491
|
|
492
|
-
async for data in _stream_function_call_data(
|
492
|
+
async for data in _stream_function_call_data(
|
493
|
+
self._client, stub, function_call_id, variant="data_in", attempt_token=attempt_token
|
494
|
+
):
|
493
495
|
yield data
|
494
496
|
|
495
497
|
async def put_data_out(
|
496
498
|
self,
|
497
499
|
function_call_id: str,
|
500
|
+
attempt_token: str,
|
498
501
|
start_index: int,
|
499
502
|
data_format: int,
|
500
503
|
serialized_messages: list[Any],
|
@@ -515,6 +518,8 @@ class _ContainerIOManager:
|
|
515
518
|
data_chunks.append(chunk)
|
516
519
|
|
517
520
|
req = api_pb2.FunctionCallPutDataRequest(function_call_id=function_call_id, data_chunks=data_chunks)
|
521
|
+
if attempt_token:
|
522
|
+
req.attempt_token = attempt_token # oneof clears function_call_id.
|
518
523
|
|
519
524
|
if self.input_plane_server_url:
|
520
525
|
stub = await self._client.get_stub(self.input_plane_server_url)
|
@@ -524,7 +529,7 @@ class _ContainerIOManager:
|
|
524
529
|
|
525
530
|
@asynccontextmanager
|
526
531
|
async def generator_output_sender(
|
527
|
-
self, function_call_id: str, data_format: int, message_rx: asyncio.Queue
|
532
|
+
self, function_call_id: str, attempt_token: str, data_format: int, message_rx: asyncio.Queue
|
528
533
|
) -> AsyncGenerator[None, None]:
|
529
534
|
"""Runs background task that feeds generator outputs into a function call's `data_out` stream."""
|
530
535
|
GENERATOR_STOP_SENTINEL = Sentinel()
|
@@ -553,7 +558,7 @@ class _ContainerIOManager:
|
|
553
558
|
else:
|
554
559
|
serialized_messages.append(serialize_data_format(message, data_format))
|
555
560
|
total_size += len(serialized_messages[-1]) + 512 # 512 bytes for estimated framing overhead
|
556
|
-
await self.put_data_out(function_call_id, index, data_format, serialized_messages)
|
561
|
+
await self.put_data_out(function_call_id, attempt_token, index, data_format, serialized_messages)
|
557
562
|
index += len(serialized_messages)
|
558
563
|
|
559
564
|
task = asyncio.create_task(generator_output_task())
|
@@ -135,12 +135,19 @@ class _ContainerIOManager:
|
|
135
135
|
async def _dynamic_concurrency_loop(self): ...
|
136
136
|
def serialize_data_format(self, obj: typing.Any, data_format: int) -> bytes: ...
|
137
137
|
async def format_blob_data(self, data: bytes) -> dict[str, typing.Any]: ...
|
138
|
-
def get_data_in(
|
138
|
+
def get_data_in(
|
139
|
+
self, function_call_id: str, attempt_token: typing.Optional[str]
|
140
|
+
) -> collections.abc.AsyncIterator[typing.Any]:
|
139
141
|
"""Read from the `data_in` stream of a function call."""
|
140
142
|
...
|
141
143
|
|
142
144
|
async def put_data_out(
|
143
|
-
self,
|
145
|
+
self,
|
146
|
+
function_call_id: str,
|
147
|
+
attempt_token: str,
|
148
|
+
start_index: int,
|
149
|
+
data_format: int,
|
150
|
+
serialized_messages: list[typing.Any],
|
144
151
|
) -> None:
|
145
152
|
"""Put data onto the `data_out` stream of a function call.
|
146
153
|
|
@@ -151,7 +158,7 @@ class _ContainerIOManager:
|
|
151
158
|
...
|
152
159
|
|
153
160
|
def generator_output_sender(
|
154
|
-
self, function_call_id: str, data_format: int, message_rx: asyncio.queues.Queue
|
161
|
+
self, function_call_id: str, attempt_token: str, data_format: int, message_rx: asyncio.queues.Queue
|
155
162
|
) -> typing.AsyncContextManager[None]:
|
156
163
|
"""Runs background task that feeds generator outputs into a function call's `data_out` stream."""
|
157
164
|
...
|
@@ -334,11 +341,15 @@ class ContainerIOManager:
|
|
334
341
|
format_blob_data: __format_blob_data_spec[typing_extensions.Self]
|
335
342
|
|
336
343
|
class __get_data_in_spec(typing_extensions.Protocol[SUPERSELF]):
|
337
|
-
def __call__(
|
344
|
+
def __call__(
|
345
|
+
self, /, function_call_id: str, attempt_token: typing.Optional[str]
|
346
|
+
) -> typing.Iterator[typing.Any]:
|
338
347
|
"""Read from the `data_in` stream of a function call."""
|
339
348
|
...
|
340
349
|
|
341
|
-
def aio(
|
350
|
+
def aio(
|
351
|
+
self, /, function_call_id: str, attempt_token: typing.Optional[str]
|
352
|
+
) -> collections.abc.AsyncIterator[typing.Any]:
|
342
353
|
"""Read from the `data_in` stream of a function call."""
|
343
354
|
...
|
344
355
|
|
@@ -346,7 +357,13 @@ class ContainerIOManager:
|
|
346
357
|
|
347
358
|
class __put_data_out_spec(typing_extensions.Protocol[SUPERSELF]):
|
348
359
|
def __call__(
|
349
|
-
self,
|
360
|
+
self,
|
361
|
+
/,
|
362
|
+
function_call_id: str,
|
363
|
+
attempt_token: str,
|
364
|
+
start_index: int,
|
365
|
+
data_format: int,
|
366
|
+
serialized_messages: list[typing.Any],
|
350
367
|
) -> None:
|
351
368
|
"""Put data onto the `data_out` stream of a function call.
|
352
369
|
|
@@ -357,7 +374,13 @@ class ContainerIOManager:
|
|
357
374
|
...
|
358
375
|
|
359
376
|
async def aio(
|
360
|
-
self,
|
377
|
+
self,
|
378
|
+
/,
|
379
|
+
function_call_id: str,
|
380
|
+
attempt_token: str,
|
381
|
+
start_index: int,
|
382
|
+
data_format: int,
|
383
|
+
serialized_messages: list[typing.Any],
|
361
384
|
) -> None:
|
362
385
|
"""Put data onto the `data_out` stream of a function call.
|
363
386
|
|
@@ -371,13 +394,13 @@ class ContainerIOManager:
|
|
371
394
|
|
372
395
|
class __generator_output_sender_spec(typing_extensions.Protocol[SUPERSELF]):
|
373
396
|
def __call__(
|
374
|
-
self, /, function_call_id: str, data_format: int, message_rx: asyncio.queues.Queue
|
397
|
+
self, /, function_call_id: str, attempt_token: str, data_format: int, message_rx: asyncio.queues.Queue
|
375
398
|
) -> synchronicity.combined_types.AsyncAndBlockingContextManager[None]:
|
376
399
|
"""Runs background task that feeds generator outputs into a function call's `data_out` stream."""
|
377
400
|
...
|
378
401
|
|
379
402
|
def aio(
|
380
|
-
self, /, function_call_id: str, data_format: int, message_rx: asyncio.queues.Queue
|
403
|
+
self, /, function_call_id: str, attempt_token: str, data_format: int, message_rx: asyncio.queues.Queue
|
381
404
|
) -> typing.AsyncContextManager[None]:
|
382
405
|
"""Runs background task that feeds generator outputs into a function call's `data_out` stream."""
|
383
406
|
...
|
@@ -392,8 +392,8 @@ async def _stream_function_call_data(
|
|
392
392
|
attempt_token: Optional[str] = None,
|
393
393
|
) -> AsyncGenerator[Any, None]:
|
394
394
|
"""Read from the `data_in` or `data_out` stream of a function call."""
|
395
|
-
if function_call_id
|
396
|
-
raise ValueError("function_call_id or attempt_token is required
|
395
|
+
if not function_call_id and not attempt_token:
|
396
|
+
raise ValueError("function_call_id or attempt_token is required to read from a data stream")
|
397
397
|
|
398
398
|
if stub is None:
|
399
399
|
stub = client.stub
|
@@ -415,8 +415,9 @@ async def _stream_function_call_data(
|
|
415
415
|
req = api_pb2.FunctionCallGetDataRequest(
|
416
416
|
function_call_id=function_call_id,
|
417
417
|
last_index=last_index,
|
418
|
-
attempt_token=attempt_token,
|
419
418
|
)
|
419
|
+
if attempt_token:
|
420
|
+
req.attempt_token = attempt_token # oneof clears function_call_id.
|
420
421
|
try:
|
421
422
|
async for chunk in stub_fn.unary_stream(req):
|
422
423
|
if chunk.index <= last_index:
|
@@ -33,7 +33,7 @@ class _Client:
|
|
33
33
|
server_url: str,
|
34
34
|
client_type: int,
|
35
35
|
credentials: typing.Optional[tuple[str, str]],
|
36
|
-
version: str = "1.1.2.
|
36
|
+
version: str = "1.1.2.dev39",
|
37
37
|
):
|
38
38
|
"""mdmd:hidden
|
39
39
|
The Modal client object is not intended to be instantiated directly by users.
|
@@ -164,7 +164,7 @@ class Client:
|
|
164
164
|
server_url: str,
|
165
165
|
client_type: int,
|
166
166
|
credentials: typing.Optional[tuple[str, str]],
|
167
|
-
version: str = "1.1.2.
|
167
|
+
version: str = "1.1.2.dev39",
|
168
168
|
):
|
169
169
|
"""mdmd:hidden
|
170
170
|
The Modal client object is not intended to be instantiated directly by users.
|
@@ -433,7 +433,7 @@ class Function(
|
|
433
433
|
|
434
434
|
_call_generator: ___call_generator_spec[typing_extensions.Self]
|
435
435
|
|
436
|
-
class __remote_spec(typing_extensions.Protocol[
|
436
|
+
class __remote_spec(typing_extensions.Protocol[P_INNER, ReturnType_INNER, SUPERSELF]):
|
437
437
|
def __call__(self, /, *args: P_INNER.args, **kwargs: P_INNER.kwargs) -> ReturnType_INNER:
|
438
438
|
"""Calls the function remotely, executing it with the given arguments and returning the execution's result."""
|
439
439
|
...
|
@@ -442,7 +442,7 @@ class Function(
|
|
442
442
|
"""Calls the function remotely, executing it with the given arguments and returning the execution's result."""
|
443
443
|
...
|
444
444
|
|
445
|
-
remote: __remote_spec[modal._functions.
|
445
|
+
remote: __remote_spec[modal._functions.P, modal._functions.ReturnType, typing_extensions.Self]
|
446
446
|
|
447
447
|
class __remote_gen_spec(typing_extensions.Protocol[SUPERSELF]):
|
448
448
|
def __call__(self, /, *args, **kwargs) -> typing.Generator[typing.Any, None, None]:
|
@@ -469,7 +469,7 @@ class Function(
|
|
469
469
|
"""
|
470
470
|
...
|
471
471
|
|
472
|
-
class ___experimental_spawn_spec(typing_extensions.Protocol[
|
472
|
+
class ___experimental_spawn_spec(typing_extensions.Protocol[P_INNER, ReturnType_INNER, SUPERSELF]):
|
473
473
|
def __call__(self, /, *args: P_INNER.args, **kwargs: P_INNER.kwargs) -> FunctionCall[ReturnType_INNER]:
|
474
474
|
"""[Experimental] Calls the function with the given arguments, without waiting for the results.
|
475
475
|
|
@@ -493,7 +493,7 @@ class Function(
|
|
493
493
|
...
|
494
494
|
|
495
495
|
_experimental_spawn: ___experimental_spawn_spec[
|
496
|
-
modal._functions.
|
496
|
+
modal._functions.P, modal._functions.ReturnType, typing_extensions.Self
|
497
497
|
]
|
498
498
|
|
499
499
|
class ___spawn_map_inner_spec(typing_extensions.Protocol[P_INNER, SUPERSELF]):
|
@@ -502,7 +502,7 @@ class Function(
|
|
502
502
|
|
503
503
|
_spawn_map_inner: ___spawn_map_inner_spec[modal._functions.P, typing_extensions.Self]
|
504
504
|
|
505
|
-
class __spawn_spec(typing_extensions.Protocol[
|
505
|
+
class __spawn_spec(typing_extensions.Protocol[P_INNER, ReturnType_INNER, SUPERSELF]):
|
506
506
|
def __call__(self, /, *args: P_INNER.args, **kwargs: P_INNER.kwargs) -> FunctionCall[ReturnType_INNER]:
|
507
507
|
"""Calls the function with the given arguments, without waiting for the results.
|
508
508
|
|
@@ -523,7 +523,7 @@ class Function(
|
|
523
523
|
"""
|
524
524
|
...
|
525
525
|
|
526
|
-
spawn: __spawn_spec[modal._functions.
|
526
|
+
spawn: __spawn_spec[modal._functions.P, modal._functions.ReturnType, typing_extensions.Self]
|
527
527
|
|
528
528
|
def get_raw_f(self) -> collections.abc.Callable[..., typing.Any]:
|
529
529
|
"""Return the inner Python object wrapped by this Modal Function."""
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|