modal 0.71.2__py3-none-any.whl → 0.71.4__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.
@@ -17,7 +17,14 @@ from modal_proto import api_pb2
17
17
  from .._serialization import deserialize, deserialize_data_format, serialize
18
18
  from .._traceback import append_modal_tb
19
19
  from ..config import config, logger
20
- from ..exception import DeserializationError, ExecutionError, FunctionTimeoutError, InvalidError, RemoteError
20
+ from ..exception import (
21
+ DeserializationError,
22
+ ExecutionError,
23
+ FunctionTimeoutError,
24
+ InternalFailure,
25
+ InvalidError,
26
+ RemoteError,
27
+ )
21
28
  from ..mount import ROOT_DIR, _is_modal_path, _Mount
22
29
  from .blob_utils import MAX_OBJECT_SIZE_BYTES, blob_download, blob_upload
23
30
  from .grpc_utils import RETRYABLE_GRPC_STATUS_CODES
@@ -463,6 +470,8 @@ async def _process_result(result: api_pb2.GenericResult, data_format: int, stub,
463
470
 
464
471
  if result.status == api_pb2.GenericResult.GENERIC_STATUS_TIMEOUT:
465
472
  raise FunctionTimeoutError(result.exception)
473
+ elif result.status == api_pb2.GenericResult.GENERIC_STATUS_INTERNAL_FAILURE:
474
+ raise InternalFailure(result.exception)
466
475
  elif result.status != api_pb2.GenericResult.GENERIC_STATUS_SUCCESS:
467
476
  if data:
468
477
  try:
modal/cli/run.py CHANGED
@@ -461,7 +461,7 @@ def shell(
461
461
  ):
462
462
  from .container import exec
463
463
 
464
- exec(container_id=container_or_function, command=shlex.split(cmd))
464
+ exec(container_id=container_or_function, command=shlex.split(cmd), pty=pty)
465
465
  return
466
466
 
467
467
  function = import_function(
modal/client.pyi CHANGED
@@ -26,7 +26,7 @@ class _Client:
26
26
  _stub: typing.Optional[modal_proto.api_grpc.ModalClientStub]
27
27
 
28
28
  def __init__(
29
- self, server_url: str, client_type: int, credentials: typing.Optional[tuple[str, str]], version: str = "0.71.2"
29
+ self, server_url: str, client_type: int, credentials: typing.Optional[tuple[str, str]], version: str = "0.71.4"
30
30
  ): ...
31
31
  def is_closed(self) -> bool: ...
32
32
  @property
@@ -81,7 +81,7 @@ class Client:
81
81
  _stub: typing.Optional[modal_proto.api_grpc.ModalClientStub]
82
82
 
83
83
  def __init__(
84
- self, server_url: str, client_type: int, credentials: typing.Optional[tuple[str, str]], version: str = "0.71.2"
84
+ self, server_url: str, client_type: int, credentials: typing.Optional[tuple[str, str]], version: str = "0.71.4"
85
85
  ): ...
86
86
  def is_closed(self) -> bool: ...
87
87
  @property
modal/exception.py CHANGED
@@ -108,6 +108,12 @@ class ServerWarning(UserWarning):
108
108
  """Warning originating from the Modal server and re-issued in client code."""
109
109
 
110
110
 
111
+ class InternalFailure(Error):
112
+ """
113
+ Retriable internal error.
114
+ """
115
+
116
+
111
117
  class _CliUserExecutionError(Exception):
112
118
  """mdmd:hidden
113
119
  Private wrapper for exceptions during when importing or running stubs from the CLI.
modal/functions.py CHANGED
@@ -59,7 +59,14 @@ from .call_graph import InputInfo, _reconstruct_call_graph
59
59
  from .client import _Client
60
60
  from .cloud_bucket_mount import _CloudBucketMount, cloud_bucket_mounts_to_proto
61
61
  from .config import config
62
- from .exception import ExecutionError, FunctionTimeoutError, InvalidError, NotFoundError, OutputExpiredError
62
+ from .exception import (
63
+ ExecutionError,
64
+ FunctionTimeoutError,
65
+ InternalFailure,
66
+ InvalidError,
67
+ NotFoundError,
68
+ OutputExpiredError,
69
+ )
63
70
  from .gpu import GPU_T, parse_gpu_config
64
71
  from .image import _Image
65
72
  from .mount import _get_client_mount, _Mount, get_auto_mounts
@@ -174,7 +181,7 @@ class _Invocation:
174
181
  return _Invocation(client.stub, function_call_id, client, retry_context)
175
182
 
176
183
  async def pop_function_call_outputs(
177
- self, timeout: Optional[float], clear_on_success: bool
184
+ self, timeout: Optional[float], clear_on_success: bool, input_jwts: Optional[list[str]] = None
178
185
  ) -> api_pb2.FunctionGetOutputsResponse:
179
186
  t0 = time.time()
180
187
  if timeout is None:
@@ -190,6 +197,7 @@ class _Invocation:
190
197
  last_entry_id="0-0",
191
198
  clear_on_success=clear_on_success,
192
199
  requested_at=time.time(),
200
+ input_jwts=input_jwts,
193
201
  )
194
202
  response: api_pb2.FunctionGetOutputsResponse = await retry_transient_errors(
195
203
  self.stub.FunctionGetOutputs,
@@ -219,10 +227,14 @@ class _Invocation:
219
227
  request,
220
228
  )
221
229
 
222
- async def _get_single_output(self) -> Any:
230
+ async def _get_single_output(self, expected_jwt: Optional[str] = None) -> Any:
223
231
  # waits indefinitely for a single result for the function, and clear the outputs buffer after
224
232
  item: api_pb2.FunctionGetOutputsItem = (
225
- await self.pop_function_call_outputs(timeout=None, clear_on_success=True)
233
+ await self.pop_function_call_outputs(
234
+ timeout=None,
235
+ clear_on_success=True,
236
+ input_jwts=[expected_jwt] if expected_jwt else None,
237
+ )
226
238
  ).outputs[0]
227
239
  return await _process_result(item.result, item.data_format, self.stub, self.client)
228
240
 
@@ -242,9 +254,12 @@ class _Invocation:
242
254
 
243
255
  while True:
244
256
  try:
245
- return await self._get_single_output()
257
+ return await self._get_single_output(ctx.input_jwt)
246
258
  except (UserCodeException, FunctionTimeoutError) as exc:
247
259
  await user_retry_manager.raise_or_sleep(exc)
260
+ except InternalFailure:
261
+ # For system failures on the server, we retry immediately.
262
+ pass
248
263
  await self._retry_input()
249
264
 
250
265
  async def poll_function(self, timeout: Optional[float] = None):
modal/functions.pyi CHANGED
@@ -61,10 +61,10 @@ class _Invocation:
61
61
  function: _Function, args, kwargs, *, client: modal.client._Client, function_call_invocation_type: int
62
62
  ) -> _Invocation: ...
63
63
  async def pop_function_call_outputs(
64
- self, timeout: typing.Optional[float], clear_on_success: bool
64
+ self, timeout: typing.Optional[float], clear_on_success: bool, input_jwts: typing.Optional[list[str]] = None
65
65
  ) -> modal_proto.api_pb2.FunctionGetOutputsResponse: ...
66
66
  async def _retry_input(self) -> None: ...
67
- async def _get_single_output(self) -> typing.Any: ...
67
+ async def _get_single_output(self, expected_jwt: typing.Optional[str] = None) -> typing.Any: ...
68
68
  async def run_function(self) -> typing.Any: ...
69
69
  async def poll_function(self, timeout: typing.Optional[float] = None): ...
70
70
  def run_generator(self): ...
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.1
2
2
  Name: modal
3
- Version: 0.71.2
3
+ Version: 0.71.4
4
4
  Summary: Python client library for Modal
5
5
  Author: Modal Labs
6
6
  Author-email: support@modal.com
@@ -19,7 +19,7 @@ modal/app.py,sha256=vEE0cK5QPF6_cdW5AJvcuWxz5KmeprHwBEtlDkVRHgE,45582
19
19
  modal/app.pyi,sha256=Gx7gxjfQ70sxhbwfpx1VjvzEON-ZEMTJ_Vy8qt0oQvo,25302
20
20
  modal/call_graph.py,sha256=1g2DGcMIJvRy-xKicuf63IVE98gJSnQsr8R_NVMptNc,2581
21
21
  modal/client.py,sha256=JAnd4-GCN093BwkvOFAK5a6iy5ycxofjpUncMxlrIMw,15253
22
- modal/client.pyi,sha256=Hytz6ByaqDhEWzURBLckQhgx5lj1VGnSG5DWq6wf6O0,7278
22
+ modal/client.pyi,sha256=4tCQvE-eS0ZqCco5-2LqQ3omg76GL-q4K8prnmzVfZ4,7278
23
23
  modal/cloud_bucket_mount.py,sha256=G7T7jWLD0QkmrfKR75mSTwdUZ2xNfj7pkVqb4ipmxmI,5735
24
24
  modal/cloud_bucket_mount.pyi,sha256=CEi7vrH3kDUF4LAy4qP6tfImy2UJuFRcRbsgRNM1wo8,1403
25
25
  modal/cls.py,sha256=3hjb0JcoPjxKZNeK22f5rR43bZRBjoRI7_EMZXY7YrE,31172
@@ -31,13 +31,13 @@ modal/dict.py,sha256=ei9jsA5iTj4UFGPJxTAed6vjd49W47ezDtj0koUmVts,12497
31
31
  modal/dict.pyi,sha256=VmbzxltA2vFlIHZCxpNGtd-ieXwcUwdw3iyy3WCweqU,7115
32
32
  modal/environments.py,sha256=wbv9ttFCbzATGfwcmvYiG608PfHovx0AQmawsg-jmic,6660
33
33
  modal/environments.pyi,sha256=rF7oaaELoSNuoD6qImGnIbuGPtgWwR5SlcExyYJ61hQ,3515
34
- modal/exception.py,sha256=GEV6xMnVnkle0gsFZVLB4B7cUMyw8HzVDvAvPr34ZV4,5185
34
+ modal/exception.py,sha256=4JyO-SACaLNDe2QC48EjsK8GMkZ8AgEurZ8j1YdRu8E,5263
35
35
  modal/experimental.py,sha256=npfKbyMpI41uZZs9HW_QiB3E4ykWfDXZbACXXbw6qeA,2385
36
36
  modal/file_io.py,sha256=ZR8VBCDsDt5uB9TNN9XbEh7sniJzM_5YL47m8WP0m5c,19617
37
37
  modal/file_io.pyi,sha256=79Fg75BjmMEeCX0Lx-Z8C4XSNPCotwNdK6ZLIDFm2f4,9770
38
38
  modal/file_pattern_matcher.py,sha256=LaI7Paxg0xR9D-D7Tgc60xR0w1KZee22LjGbFie1Vms,5571
39
- modal/functions.py,sha256=aXXXr3rk7BCeh5OWMvxGksGm8FQoYCyrBDGV74FPoPE,67827
40
- modal/functions.pyi,sha256=snttn47K81lKhmrCLWNVZelZTDhNsbxtw4l1DlLDR74,25317
39
+ modal/functions.py,sha256=3uJPbrEAWhpFfLfUnoRjGmvEUC-_wVh-8yNJBx8eVeM,68249
40
+ modal/functions.pyi,sha256=LiSDgH-X7jcZ56pAoLMwo3x9Dzdp_3Sd7W5MVAJPoCg,25407
41
41
  modal/gpu.py,sha256=MTxj6ql8EpgfBg8YmZ5a1cLznyuZFssX1qXbEX4LKVM,7503
42
42
  modal/image.py,sha256=Krvcsclomp9YsqSNwFj2FoAyg10OvU47RDnsNCwjGbQ,84550
43
43
  modal/image.pyi,sha256=1fgGvsL5Rb0Sa-_2OCgIyJ_QgHcL0_9MWD_oY7cyFFM,24937
@@ -90,7 +90,7 @@ modal/_utils/blob_utils.py,sha256=N66LtZI8PpCkZ7maA7GLW5CAmYUoNJdG-GjaAUR4_NQ,14
90
90
  modal/_utils/bytes_io_segment_payload.py,sha256=uunxVJS4PE1LojF_UpURMzVK9GuvmYWRqQo_bxEj5TU,3385
91
91
  modal/_utils/deprecation.py,sha256=dycySRBxyZf3ITzEqPNM6MxXTk9-0VVLA8oCPQ5j_Os,3426
92
92
  modal/_utils/docker_utils.py,sha256=FLz1q0YicL6i_Iq-4inkgDVFfEINVG6YPT2s_P6ly0o,2264
93
- modal/_utils/function_utils.py,sha256=4LYFbNY5aHc96QitwP4Ty-dBl45SD1HjfZrvBFUF-ko,25343
93
+ modal/_utils/function_utils.py,sha256=q68HhFH16MwhHRnGD8jvIgqDjduRQVp3a_qMWXPyrgU,25518
94
94
  modal/_utils/grpc_testing.py,sha256=H1zHqthv19eGPJz2HKXDyWXWGSqO4BRsxah3L5Xaa8A,8619
95
95
  modal/_utils/grpc_utils.py,sha256=PPB5ay-vXencXNIWPVw5modr3EH7gfq2QPcO5YJ1lMU,7737
96
96
  modal/_utils/hash_utils.py,sha256=zg3J6OGxTFGSFri1qQ12giDz90lWk8bzaxCTUCRtiX4,3034
@@ -120,7 +120,7 @@ modal/cli/launch.py,sha256=44oOlGB0KYDBMfuIlkhW2uzjkWbHhDRR64UOEnGwsJ4,2989
120
120
  modal/cli/network_file_system.py,sha256=o6VLTgN4xn5XUiNPBfxYec-5uWCgYrDmfFFLM1ZW_eE,8180
121
121
  modal/cli/profile.py,sha256=rLXfjJObfPNjaZvNfHGIKqs7y9bGYyGe-K7V0w-Ni0M,3110
122
122
  modal/cli/queues.py,sha256=MIh2OsliNE2QeL1erubfsRsNuG4fxqcqWA2vgIfQ4Mg,4494
123
- modal/cli/run.py,sha256=9SvPmBzB8ZZRaqUJc9LmL2tfT5OMiR4Ow0dLANVwuB8,17870
123
+ modal/cli/run.py,sha256=QMs3BVSkq8jve76BqgstGt4C6jilbDD9gpCCRPuHUy0,17879
124
124
  modal/cli/secret.py,sha256=uQpwYrMY98iMCWeZOQTcktOYhPTZ8IHnyealDc2CZqo,4206
125
125
  modal/cli/token.py,sha256=mxSgOWakXG6N71hQb1ko61XAR9ZGkTMZD-Txn7gmTac,1924
126
126
  modal/cli/utils.py,sha256=hZmjyzcPjDnQSkLvycZD2LhGdcsfdZshs_rOU78EpvI,3717
@@ -166,10 +166,10 @@ modal_proto/options_pb2_grpc.pyi,sha256=CImmhxHsYnF09iENPoe8S4J-n93jtgUYD2JPAc0y
166
166
  modal_proto/py.typed,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
167
167
  modal_version/__init__.py,sha256=BEBWj9tcbFUwzEjUrqly601rauw5cYsHdcmJHs3iu0s,470
168
168
  modal_version/__main__.py,sha256=2FO0yYQQwDTh6udt1h-cBnGd1c4ZyHnHSI4BksxzVac,105
169
- modal_version/_version_generated.py,sha256=mfMCToZpTuPxzuVuuvViSp1od7EJVezkQVZIUWWSBic,148
170
- modal-0.71.2.dist-info/LICENSE,sha256=psuoW8kuDP96RQsdhzwOqi6fyWv0ct8CR6Jr7He_P_k,10173
171
- modal-0.71.2.dist-info/METADATA,sha256=pF1LUr5t33VWn4eEb59j6Is9NTrmoT9Wr-lZF4ciHf0,2328
172
- modal-0.71.2.dist-info/WHEEL,sha256=G16H4A3IeoQmnOrYV4ueZGKSjhipXx8zc8nu9FGlvMA,92
173
- modal-0.71.2.dist-info/entry_points.txt,sha256=An-wYgeEUnm6xzrAP9_NTSTSciYvvEWsMZILtYrvpAI,46
174
- modal-0.71.2.dist-info/top_level.txt,sha256=1nvYbOSIKcmU50fNrpnQnrrOpj269ei3LzgB6j9xGqg,64
175
- modal-0.71.2.dist-info/RECORD,,
169
+ modal_version/_version_generated.py,sha256=3TvSmDcXd2TJWiBGF1oNLfcsxLy3TPqMQ4BxZiXpYB0,148
170
+ modal-0.71.4.dist-info/LICENSE,sha256=psuoW8kuDP96RQsdhzwOqi6fyWv0ct8CR6Jr7He_P_k,10173
171
+ modal-0.71.4.dist-info/METADATA,sha256=km6ecKksbjllgRq-Bk0JlnTFBf-EuP3wBOh6_nf5bVc,2328
172
+ modal-0.71.4.dist-info/WHEEL,sha256=G16H4A3IeoQmnOrYV4ueZGKSjhipXx8zc8nu9FGlvMA,92
173
+ modal-0.71.4.dist-info/entry_points.txt,sha256=An-wYgeEUnm6xzrAP9_NTSTSciYvvEWsMZILtYrvpAI,46
174
+ modal-0.71.4.dist-info/top_level.txt,sha256=1nvYbOSIKcmU50fNrpnQnrrOpj269ei3LzgB6j9xGqg,64
175
+ modal-0.71.4.dist-info/RECORD,,
@@ -1,4 +1,4 @@
1
1
  # Copyright Modal Labs 2025
2
2
 
3
3
  # Note: Reset this value to -1 whenever you make a minor `0.X` release of the client.
4
- build_number = 2 # git: 23f2781
4
+ build_number = 4 # git: 07e0100
File without changes