modal 1.1.5.dev76__tar.gz → 1.1.5.dev78__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.
Potentially problematic release.
This version of modal might be problematic. Click here for more details.
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/PKG-INFO +1 -1
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/_utils/name_utils.py +2 -3
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/app.py +40 -2
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/app.pyi +60 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/client.pyi +2 -2
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/functions.pyi +6 -6
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/image.py +9 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/image.pyi +18 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal.egg-info/PKG-INFO +1 -1
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal_version/__init__.py +1 -1
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/LICENSE +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/README.md +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/__init__.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/__main__.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/_clustered_functions.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/_clustered_functions.pyi +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/_container_entrypoint.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/_functions.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/_ipython.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/_location.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/_object.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/_output.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/_partial_function.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/_pty.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/_resolver.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/_resources.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/_runtime/__init__.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/_runtime/asgi.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/_runtime/container_io_manager.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/_runtime/container_io_manager.pyi +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/_runtime/execution_context.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/_runtime/execution_context.pyi +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/_runtime/gpu_memory_snapshot.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/_runtime/telemetry.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/_runtime/user_code_imports.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/_serialization.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/_traceback.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/_tunnel.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/_tunnel.pyi +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/_type_manager.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/_utils/__init__.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/_utils/app_utils.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/_utils/async_utils.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/_utils/auth_token_manager.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/_utils/blob_utils.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/_utils/bytes_io_segment_payload.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/_utils/deprecation.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/_utils/docker_utils.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/_utils/function_utils.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/_utils/git_utils.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/_utils/grpc_testing.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/_utils/grpc_utils.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/_utils/hash_utils.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/_utils/http_utils.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/_utils/jwt_utils.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/_utils/logger.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/_utils/mount_utils.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/_utils/package_utils.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/_utils/pattern_utils.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/_utils/rand_pb_testing.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/_utils/shell_utils.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/_utils/time_utils.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/_vendor/__init__.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/_vendor/a2wsgi_wsgi.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/_vendor/cloudpickle.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/_vendor/tblib.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/_watcher.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/builder/2023.12.312.txt +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/builder/2023.12.txt +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/builder/2024.04.txt +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/builder/2024.10.txt +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/builder/2025.06.txt +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/builder/PREVIEW.txt +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/builder/README.md +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/builder/base-images.json +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/call_graph.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/cli/__init__.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/cli/_download.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/cli/_traceback.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/cli/app.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/cli/cluster.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/cli/config.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/cli/container.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/cli/dict.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/cli/entry_point.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/cli/environment.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/cli/import_refs.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/cli/launch.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/cli/network_file_system.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/cli/profile.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/cli/programs/__init__.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/cli/programs/launch_instance_ssh.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/cli/programs/run_jupyter.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/cli/programs/run_marimo.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/cli/programs/vscode.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/cli/queues.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/cli/run.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/cli/secret.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/cli/token.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/cli/utils.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/cli/volume.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/client.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/cloud_bucket_mount.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/cloud_bucket_mount.pyi +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/cls.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/cls.pyi +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/config.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/container_process.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/container_process.pyi +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/dict.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/dict.pyi +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/environments.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/environments.pyi +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/exception.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/experimental/__init__.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/experimental/flash.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/experimental/flash.pyi +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/experimental/ipython.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/file_io.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/file_io.pyi +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/file_pattern_matcher.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/functions.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/gpu.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/io_streams.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/io_streams.pyi +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/mount.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/mount.pyi +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/network_file_system.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/network_file_system.pyi +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/object.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/object.pyi +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/output.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/parallel_map.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/parallel_map.pyi +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/partial_function.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/partial_function.pyi +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/proxy.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/proxy.pyi +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/py.typed +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/queue.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/queue.pyi +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/retries.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/runner.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/runner.pyi +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/running_app.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/sandbox.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/sandbox.pyi +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/schedule.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/scheduler_placement.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/secret.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/secret.pyi +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/serving.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/serving.pyi +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/snapshot.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/snapshot.pyi +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/stream_type.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/token_flow.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/token_flow.pyi +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/volume.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal/volume.pyi +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal.egg-info/SOURCES.txt +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal.egg-info/dependency_links.txt +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal.egg-info/entry_points.txt +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal.egg-info/requires.txt +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal.egg-info/top_level.txt +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal_docs/__init__.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal_docs/gen_cli_docs.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal_docs/gen_reference_docs.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal_docs/mdmd/__init__.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal_docs/mdmd/mdmd.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal_docs/mdmd/signatures.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal_proto/__init__.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal_proto/api.proto +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal_proto/api_grpc.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal_proto/api_pb2.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal_proto/api_pb2.pyi +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal_proto/api_pb2_grpc.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal_proto/api_pb2_grpc.pyi +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal_proto/modal_api_grpc.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal_proto/modal_options_grpc.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal_proto/options.proto +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal_proto/options_grpc.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal_proto/options_pb2.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal_proto/options_pb2.pyi +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal_proto/options_pb2_grpc.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal_proto/options_pb2_grpc.pyi +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal_proto/py.typed +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal_proto/sandbox_router.proto +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal_proto/sandbox_router_grpc.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal_proto/sandbox_router_pb2.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal_proto/sandbox_router_pb2.pyi +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal_proto/sandbox_router_pb2_grpc.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal_proto/sandbox_router_pb2_grpc.pyi +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/modal_version/__main__.py +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/pyproject.toml +0 -0
- {modal-1.1.5.dev76 → modal-1.1.5.dev78}/setup.cfg +0 -0
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
# Copyright Modal Labs 2022
|
|
2
2
|
import re
|
|
3
|
+
from collections.abc import Mapping
|
|
3
4
|
|
|
4
5
|
from ..exception import InvalidError
|
|
5
6
|
|
|
@@ -37,7 +38,7 @@ def is_valid_tag(tag: str, max_length: int = 50) -> bool:
|
|
|
37
38
|
return bool(re.match(pattern, tag))
|
|
38
39
|
|
|
39
40
|
|
|
40
|
-
def check_tag_dict(tags:
|
|
41
|
+
def check_tag_dict(tags: Mapping[str, str]) -> None:
|
|
41
42
|
rules = (
|
|
42
43
|
"\n\nTags may contain only alphanumeric characters, dashes, periods, or underscores, "
|
|
43
44
|
"and must be 63 characters or less."
|
|
@@ -49,8 +50,6 @@ def check_tag_dict(tags: dict[str, str]) -> dict[str, str]:
|
|
|
49
50
|
if not is_valid_tag(value, max_length):
|
|
50
51
|
raise InvalidError(f"Invalid tag value: {value!r}.{rules}")
|
|
51
52
|
|
|
52
|
-
return tags
|
|
53
|
-
|
|
54
53
|
|
|
55
54
|
def check_object_name(name: str, object_type: str) -> None:
|
|
56
55
|
message = (
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
# Copyright Modal Labs 2022
|
|
2
2
|
import inspect
|
|
3
3
|
import typing
|
|
4
|
-
from collections.abc import AsyncGenerator, Collection, Coroutine, Sequence
|
|
4
|
+
from collections.abc import AsyncGenerator, Collection, Coroutine, Mapping, Sequence
|
|
5
5
|
from pathlib import PurePosixPath
|
|
6
6
|
from textwrap import dedent
|
|
7
7
|
from typing import (
|
|
@@ -191,9 +191,12 @@ class _App:
|
|
|
191
191
|
if name is not None and not isinstance(name, str):
|
|
192
192
|
raise InvalidError("Invalid value for `name`: Must be string.")
|
|
193
193
|
|
|
194
|
+
if tags is not None:
|
|
195
|
+
check_tag_dict(tags)
|
|
196
|
+
|
|
194
197
|
self._name = name
|
|
195
198
|
self._description = name
|
|
196
|
-
self._tags =
|
|
199
|
+
self._tags = tags or {}
|
|
197
200
|
self._include_source_default = include_source
|
|
198
201
|
|
|
199
202
|
check_sequence(secrets, _Secret, "`secrets=` has to be a list or tuple of `modal.Secret` objects")
|
|
@@ -1088,6 +1091,41 @@ class _App:
|
|
|
1088
1091
|
|
|
1089
1092
|
return self
|
|
1090
1093
|
|
|
1094
|
+
async def set_tags(self, tags: Mapping[str, str], *, client: Optional[_Client] = None) -> None:
|
|
1095
|
+
"""Attach key-value metadata to the App.
|
|
1096
|
+
|
|
1097
|
+
Tag metadata can be used to add organization-specific context to the App and can be
|
|
1098
|
+
included in billing reports and other informational APIs. Tags can also be set in
|
|
1099
|
+
the App constructor.
|
|
1100
|
+
|
|
1101
|
+
Any tags set on the App before calling this method will be removed if they are not
|
|
1102
|
+
included in the argument (i.e., this method does not have `.update()` semantics).
|
|
1103
|
+
|
|
1104
|
+
"""
|
|
1105
|
+
# Note that we are requiring the App to be "running" before we set the tags.
|
|
1106
|
+
# Alternatively, we could hold onto the tags (i.e. in `self._tags`) and then pass
|
|
1107
|
+
# then up when AppPublish gets called. I'm not certain we want to support it, though.
|
|
1108
|
+
# It might not be obvious to users that `.set_tags()` is eager and has immediate effect
|
|
1109
|
+
# when the App is running, but lazy (and potentially ignored) otherwise. There would be
|
|
1110
|
+
# other complications, like what do you do with any tags set in the constructor, and
|
|
1111
|
+
# what should `.get_tags()` do when it's called before the App is running?
|
|
1112
|
+
if self._app_id is None:
|
|
1113
|
+
raise InvalidError("`App.set_tags` cannot be called before the App is running.")
|
|
1114
|
+
check_tag_dict(tags)
|
|
1115
|
+
req = api_pb2.AppSetTagsRequest(app_id=self._app_id, tags=tags)
|
|
1116
|
+
|
|
1117
|
+
client = client or self._client or await _Client.from_env()
|
|
1118
|
+
await retry_transient_errors(client.stub.AppSetTags, req)
|
|
1119
|
+
|
|
1120
|
+
async def get_tags(self, *, client: Optional[_Client] = None) -> dict[str, str]:
|
|
1121
|
+
"""Get the tags that are currently attached to the App."""
|
|
1122
|
+
if self._app_id is None:
|
|
1123
|
+
raise InvalidError("`App.get_tags` cannot be called before the App is running.")
|
|
1124
|
+
req = api_pb2.AppGetTagsRequest(app_id=self._app_id)
|
|
1125
|
+
client = client or self._client or await _Client.from_env()
|
|
1126
|
+
resp = await retry_transient_errors(client.stub.AppGetTags, req)
|
|
1127
|
+
return dict(resp.tags)
|
|
1128
|
+
|
|
1091
1129
|
async def _logs(self, client: Optional[_Client] = None) -> AsyncGenerator[str, None]:
|
|
1092
1130
|
"""Stream logs from the app.
|
|
1093
1131
|
|
|
@@ -521,6 +521,24 @@ class _App:
|
|
|
521
521
|
"""
|
|
522
522
|
...
|
|
523
523
|
|
|
524
|
+
async def set_tags(
|
|
525
|
+
self, tags: collections.abc.Mapping[str, str], *, client: typing.Optional[modal.client._Client] = None
|
|
526
|
+
) -> None:
|
|
527
|
+
"""Attach key-value metadata to the App.
|
|
528
|
+
|
|
529
|
+
Tag metadata can be used to add organization-specific context to the App and can be
|
|
530
|
+
included in billing reports and other informational APIs. Tags can also be set in
|
|
531
|
+
the App constructor.
|
|
532
|
+
|
|
533
|
+
Any tags set on the App before calling this method will be removed if they are not
|
|
534
|
+
included in the argument (i.e., this method does not have `.update()` semantics).
|
|
535
|
+
"""
|
|
536
|
+
...
|
|
537
|
+
|
|
538
|
+
async def get_tags(self, *, client: typing.Optional[modal.client._Client] = None) -> dict[str, str]:
|
|
539
|
+
"""Get the tags that are currently attached to the App."""
|
|
540
|
+
...
|
|
541
|
+
|
|
524
542
|
def _logs(self, client: typing.Optional[modal.client._Client] = None) -> collections.abc.AsyncGenerator[str, None]:
|
|
525
543
|
"""Stream logs from the app.
|
|
526
544
|
|
|
@@ -1133,6 +1151,48 @@ class App:
|
|
|
1133
1151
|
"""
|
|
1134
1152
|
...
|
|
1135
1153
|
|
|
1154
|
+
class __set_tags_spec(typing_extensions.Protocol[SUPERSELF]):
|
|
1155
|
+
def __call__(
|
|
1156
|
+
self, /, tags: collections.abc.Mapping[str, str], *, client: typing.Optional[modal.client.Client] = None
|
|
1157
|
+
) -> None:
|
|
1158
|
+
"""Attach key-value metadata to the App.
|
|
1159
|
+
|
|
1160
|
+
Tag metadata can be used to add organization-specific context to the App and can be
|
|
1161
|
+
included in billing reports and other informational APIs. Tags can also be set in
|
|
1162
|
+
the App constructor.
|
|
1163
|
+
|
|
1164
|
+
Any tags set on the App before calling this method will be removed if they are not
|
|
1165
|
+
included in the argument (i.e., this method does not have `.update()` semantics).
|
|
1166
|
+
"""
|
|
1167
|
+
...
|
|
1168
|
+
|
|
1169
|
+
async def aio(
|
|
1170
|
+
self, /, tags: collections.abc.Mapping[str, str], *, client: typing.Optional[modal.client.Client] = None
|
|
1171
|
+
) -> None:
|
|
1172
|
+
"""Attach key-value metadata to the App.
|
|
1173
|
+
|
|
1174
|
+
Tag metadata can be used to add organization-specific context to the App and can be
|
|
1175
|
+
included in billing reports and other informational APIs. Tags can also be set in
|
|
1176
|
+
the App constructor.
|
|
1177
|
+
|
|
1178
|
+
Any tags set on the App before calling this method will be removed if they are not
|
|
1179
|
+
included in the argument (i.e., this method does not have `.update()` semantics).
|
|
1180
|
+
"""
|
|
1181
|
+
...
|
|
1182
|
+
|
|
1183
|
+
set_tags: __set_tags_spec[typing_extensions.Self]
|
|
1184
|
+
|
|
1185
|
+
class __get_tags_spec(typing_extensions.Protocol[SUPERSELF]):
|
|
1186
|
+
def __call__(self, /, *, client: typing.Optional[modal.client.Client] = None) -> dict[str, str]:
|
|
1187
|
+
"""Get the tags that are currently attached to the App."""
|
|
1188
|
+
...
|
|
1189
|
+
|
|
1190
|
+
async def aio(self, /, *, client: typing.Optional[modal.client.Client] = None) -> dict[str, str]:
|
|
1191
|
+
"""Get the tags that are currently attached to the App."""
|
|
1192
|
+
...
|
|
1193
|
+
|
|
1194
|
+
get_tags: __get_tags_spec[typing_extensions.Self]
|
|
1195
|
+
|
|
1136
1196
|
class ___logs_spec(typing_extensions.Protocol[SUPERSELF]):
|
|
1137
1197
|
def __call__(self, /, client: typing.Optional[modal.client.Client] = None) -> typing.Generator[str, None, None]:
|
|
1138
1198
|
"""Stream logs from the app.
|
|
@@ -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.5.
|
|
36
|
+
version: str = "1.1.5.dev78",
|
|
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.5.
|
|
167
|
+
version: str = "1.1.5.dev78",
|
|
168
168
|
):
|
|
169
169
|
"""mdmd:hidden
|
|
170
170
|
The Modal client object is not intended to be instantiated directly by users.
|
|
@@ -401,7 +401,7 @@ class Function(
|
|
|
401
401
|
|
|
402
402
|
_call_generator: ___call_generator_spec[typing_extensions.Self]
|
|
403
403
|
|
|
404
|
-
class __remote_spec(typing_extensions.Protocol[
|
|
404
|
+
class __remote_spec(typing_extensions.Protocol[P_INNER, ReturnType_INNER, SUPERSELF]):
|
|
405
405
|
def __call__(self, /, *args: P_INNER.args, **kwargs: P_INNER.kwargs) -> ReturnType_INNER:
|
|
406
406
|
"""Calls the function remotely, executing it with the given arguments and returning the execution's result."""
|
|
407
407
|
...
|
|
@@ -410,7 +410,7 @@ class Function(
|
|
|
410
410
|
"""Calls the function remotely, executing it with the given arguments and returning the execution's result."""
|
|
411
411
|
...
|
|
412
412
|
|
|
413
|
-
remote: __remote_spec[modal._functions.
|
|
413
|
+
remote: __remote_spec[modal._functions.P, modal._functions.ReturnType, typing_extensions.Self]
|
|
414
414
|
|
|
415
415
|
class __remote_gen_spec(typing_extensions.Protocol[SUPERSELF]):
|
|
416
416
|
def __call__(self, /, *args, **kwargs) -> typing.Generator[typing.Any, None, None]:
|
|
@@ -437,7 +437,7 @@ class Function(
|
|
|
437
437
|
"""
|
|
438
438
|
...
|
|
439
439
|
|
|
440
|
-
class ___experimental_spawn_spec(typing_extensions.Protocol[
|
|
440
|
+
class ___experimental_spawn_spec(typing_extensions.Protocol[P_INNER, ReturnType_INNER, SUPERSELF]):
|
|
441
441
|
def __call__(self, /, *args: P_INNER.args, **kwargs: P_INNER.kwargs) -> FunctionCall[ReturnType_INNER]:
|
|
442
442
|
"""[Experimental] Calls the function with the given arguments, without waiting for the results.
|
|
443
443
|
|
|
@@ -461,7 +461,7 @@ class Function(
|
|
|
461
461
|
...
|
|
462
462
|
|
|
463
463
|
_experimental_spawn: ___experimental_spawn_spec[
|
|
464
|
-
modal._functions.
|
|
464
|
+
modal._functions.P, modal._functions.ReturnType, typing_extensions.Self
|
|
465
465
|
]
|
|
466
466
|
|
|
467
467
|
class ___spawn_map_inner_spec(typing_extensions.Protocol[P_INNER, SUPERSELF]):
|
|
@@ -470,7 +470,7 @@ class Function(
|
|
|
470
470
|
|
|
471
471
|
_spawn_map_inner: ___spawn_map_inner_spec[modal._functions.P, typing_extensions.Self]
|
|
472
472
|
|
|
473
|
-
class __spawn_spec(typing_extensions.Protocol[
|
|
473
|
+
class __spawn_spec(typing_extensions.Protocol[P_INNER, ReturnType_INNER, SUPERSELF]):
|
|
474
474
|
def __call__(self, /, *args: P_INNER.args, **kwargs: P_INNER.kwargs) -> FunctionCall[ReturnType_INNER]:
|
|
475
475
|
"""Calls the function with the given arguments, without waiting for the results.
|
|
476
476
|
|
|
@@ -491,7 +491,7 @@ class Function(
|
|
|
491
491
|
"""
|
|
492
492
|
...
|
|
493
493
|
|
|
494
|
-
spawn: __spawn_spec[modal._functions.
|
|
494
|
+
spawn: __spawn_spec[modal._functions.P, modal._functions.ReturnType, typing_extensions.Self]
|
|
495
495
|
|
|
496
496
|
def get_raw_f(self) -> collections.abc.Callable[..., typing.Any]:
|
|
497
497
|
"""Return the inner Python object wrapped by this Modal Function."""
|
|
@@ -1441,6 +1441,15 @@ class _Image(_Object, type_prefix="im"):
|
|
|
1441
1441
|
The `pyproject.toml` and `uv.lock` in `uv_project_dir` are automatically added to the build context. The
|
|
1442
1442
|
`uv_project_dir` is relative to the current working directory of where `modal` is called.
|
|
1443
1443
|
|
|
1444
|
+
NOTE: This does *not* install the project itself into the environment (this is equivalent to the
|
|
1445
|
+
`--no-install-project` flag in the `uv sync` command) and you would be expected to add any local python source
|
|
1446
|
+
files using `Image.add_local_python_source` or similar methods after this call.
|
|
1447
|
+
|
|
1448
|
+
This ensures that updates to your project code wouldn't require reinstalling third-party dependencies
|
|
1449
|
+
after every change.
|
|
1450
|
+
|
|
1451
|
+
uv workspaces are currently not supported.
|
|
1452
|
+
|
|
1444
1453
|
Added in v1.1.0.
|
|
1445
1454
|
"""
|
|
1446
1455
|
|
|
@@ -587,6 +587,15 @@ class _Image(modal._object._Object):
|
|
|
587
587
|
The `pyproject.toml` and `uv.lock` in `uv_project_dir` are automatically added to the build context. The
|
|
588
588
|
`uv_project_dir` is relative to the current working directory of where `modal` is called.
|
|
589
589
|
|
|
590
|
+
NOTE: This does *not* install the project itself into the environment (this is equivalent to the
|
|
591
|
+
`--no-install-project` flag in the `uv sync` command) and you would be expected to add any local python source
|
|
592
|
+
files using `Image.add_local_python_source` or similar methods after this call.
|
|
593
|
+
|
|
594
|
+
This ensures that updates to your project code wouldn't require reinstalling third-party dependencies
|
|
595
|
+
after every change.
|
|
596
|
+
|
|
597
|
+
uv workspaces are currently not supported.
|
|
598
|
+
|
|
590
599
|
Added in v1.1.0.
|
|
591
600
|
"""
|
|
592
601
|
...
|
|
@@ -1558,6 +1567,15 @@ class Image(modal.object.Object):
|
|
|
1558
1567
|
The `pyproject.toml` and `uv.lock` in `uv_project_dir` are automatically added to the build context. The
|
|
1559
1568
|
`uv_project_dir` is relative to the current working directory of where `modal` is called.
|
|
1560
1569
|
|
|
1570
|
+
NOTE: This does *not* install the project itself into the environment (this is equivalent to the
|
|
1571
|
+
`--no-install-project` flag in the `uv sync` command) and you would be expected to add any local python source
|
|
1572
|
+
files using `Image.add_local_python_source` or similar methods after this call.
|
|
1573
|
+
|
|
1574
|
+
This ensures that updates to your project code wouldn't require reinstalling third-party dependencies
|
|
1575
|
+
after every change.
|
|
1576
|
+
|
|
1577
|
+
uv workspaces are currently not supported.
|
|
1578
|
+
|
|
1561
1579
|
Added in v1.1.0.
|
|
1562
1580
|
"""
|
|
1563
1581
|
...
|
|
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
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|