anyscale 0.26.30__py3-none-any.whl → 0.26.32__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.
- anyscale/_private/anyscale_client/anyscale_client.py +22 -60
- anyscale/_private/anyscale_client/common.py +12 -1
- anyscale/_private/anyscale_client/fake_anyscale_client.py +24 -0
- anyscale/_private/docgen/__main__.py +2 -0
- anyscale/_private/docgen/models.md +2 -2
- anyscale/client/README.md +9 -0
- anyscale/client/openapi_client/__init__.py +7 -0
- anyscale/client/openapi_client/api/default_api.py +232 -0
- anyscale/client/openapi_client/models/__init__.py +7 -0
- anyscale/client/openapi_client/models/baseimagesenum.py +135 -1
- anyscale/client/openapi_client/models/cluster_operation.py +266 -0
- anyscale/client/openapi_client/models/cluster_operation_type.py +101 -0
- anyscale/client/openapi_client/models/clusteroperation_response.py +121 -0
- anyscale/client/openapi_client/models/get_or_create_build_from_image_uri_request.py +207 -0
- anyscale/client/openapi_client/models/operation_error.py +123 -0
- anyscale/client/openapi_client/models/operation_progress.py +123 -0
- anyscale/client/openapi_client/models/operation_result.py +150 -0
- anyscale/client/openapi_client/models/supportedbaseimagesenum.py +135 -1
- anyscale/cloud/__init__.py +16 -0
- anyscale/cloud/_private/cloud_sdk.py +33 -0
- anyscale/cloud/commands.py +35 -0
- anyscale/cluster_compute.py +3 -8
- anyscale/commands/cloud_commands.py +35 -0
- anyscale/commands/command_examples.py +6 -0
- anyscale/controllers/compute_config_controller.py +3 -19
- anyscale/sdk/anyscale_client/models/baseimagesenum.py +135 -1
- anyscale/sdk/anyscale_client/models/supportedbaseimagesenum.py +135 -1
- anyscale/shared_anyscale_utils/latest_ray_version.py +1 -1
- anyscale/version.py +1 -1
- {anyscale-0.26.30.dist-info → anyscale-0.26.32.dist-info}/METADATA +1 -1
- {anyscale-0.26.30.dist-info → anyscale-0.26.32.dist-info}/RECORD +36 -29
- {anyscale-0.26.30.dist-info → anyscale-0.26.32.dist-info}/LICENSE +0 -0
- {anyscale-0.26.30.dist-info → anyscale-0.26.32.dist-info}/NOTICE +0 -0
- {anyscale-0.26.30.dist-info → anyscale-0.26.32.dist-info}/WHEEL +0 -0
- {anyscale-0.26.30.dist-info → anyscale-0.26.32.dist-info}/entry_points.txt +0 -0
- {anyscale-0.26.30.dist-info → anyscale-0.26.32.dist-info}/top_level.txt +0 -0
@@ -46,6 +46,7 @@ from anyscale.client.openapi_client.models import (
|
|
46
46
|
CloudDataBucketPresignedUrlResponse,
|
47
47
|
CloudDataBucketPresignedUrlScheme,
|
48
48
|
CloudNameOptions,
|
49
|
+
ClusteroperationResponse,
|
49
50
|
ComputeTemplate,
|
50
51
|
ComputeTemplateConfig,
|
51
52
|
ComputeTemplateQuery,
|
@@ -68,6 +69,7 @@ from anyscale.client.openapi_client.models import (
|
|
68
69
|
ExperimentalWorkspace,
|
69
70
|
FineTunedModel,
|
70
71
|
FinetunedmodelListResponse,
|
72
|
+
GetOrCreateBuildFromImageUriRequest,
|
71
73
|
InternalProductionJob,
|
72
74
|
JobQueueSortDirective,
|
73
75
|
JobQueuesQuery,
|
@@ -81,6 +83,7 @@ from anyscale.client.openapi_client.models import (
|
|
81
83
|
SessionState,
|
82
84
|
StartSessionOptions,
|
83
85
|
StopSessionOptions,
|
86
|
+
SystemWorkloadName,
|
84
87
|
WorkspaceDataplaneProxiedArtifacts,
|
85
88
|
)
|
86
89
|
from anyscale.client.openapi_client.models.create_schedule import CreateSchedule
|
@@ -595,6 +598,19 @@ class AnyscaleClient(AnyscaleClientInterface):
|
|
595
598
|
cloud_id, collaborators
|
596
599
|
)
|
597
600
|
|
601
|
+
@handle_api_exceptions
|
602
|
+
def terminate_system_cluster(self, cloud_id: str) -> ClusteroperationResponse:
|
603
|
+
return self._internal_api_client.terminate_system_cluster_api_v2_system_workload_cloud_id_terminate_post(
|
604
|
+
cloud_id
|
605
|
+
)
|
606
|
+
|
607
|
+
@handle_api_exceptions
|
608
|
+
def describe_system_workload_get_status(self, cloud_id: str) -> str:
|
609
|
+
res = self._internal_api_client.describe_system_workload_api_v2_system_workload_cloud_id_describe_post(
|
610
|
+
cloud_id, SystemWorkloadName.RAY_OBS_EVENTS_API_SERVICE, start_cluster=False
|
611
|
+
).result
|
612
|
+
return res.status
|
613
|
+
|
598
614
|
@handle_api_exceptions
|
599
615
|
def create_compute_config(
|
600
616
|
self, config: ComputeTemplateConfig, *, name: Optional[str] = None
|
@@ -946,69 +962,15 @@ class AnyscaleClient(AnyscaleClientInterface):
|
|
946
962
|
ray_version: Optional[str] = None,
|
947
963
|
name: Optional[str] = None,
|
948
964
|
) -> str:
|
949
|
-
|
950
|
-
|
951
|
-
|
952
|
-
build = self._external_api_client.find_cluster_environment_build_by_identifier(
|
953
|
-
identifier=identifier
|
954
|
-
).result
|
955
|
-
if build.status == ClusterEnvironmentBuildStatus.SUCCEEDED:
|
956
|
-
return build.id
|
957
|
-
else:
|
958
|
-
raise RuntimeError(
|
959
|
-
f"Legacy cluster environment build '{identifier}' is not a successful build."
|
960
|
-
)
|
961
|
-
except ExternalApiException as e:
|
962
|
-
if e.status == 404:
|
963
|
-
raise RuntimeError(
|
964
|
-
f"Legacy cluster environment '{identifier}' is not found."
|
965
|
-
)
|
966
|
-
elif image_uri.is_default_image():
|
967
|
-
# Default image
|
968
|
-
cluster_envs = self._internal_api_client.list_application_templates_api_v2_application_templates_get(
|
969
|
-
image_name_contains=image_uri.image_uri
|
970
|
-
).results
|
971
|
-
for cluster_env in cluster_envs:
|
972
|
-
if (
|
973
|
-
cluster_env.latest_build is not None
|
974
|
-
and cluster_env.latest_build.docker_image_name
|
975
|
-
== image_uri.image_uri
|
976
|
-
):
|
977
|
-
return cluster_env.latest_build.id
|
978
|
-
raise RuntimeError(f"Default image '{image_uri.image_uri}' is not found.")
|
979
|
-
|
980
|
-
# BYOD image
|
981
|
-
cluster_env_name = name if name else image_uri.to_cluster_env_name()
|
982
|
-
image_uri_str = str(image_uri)
|
983
|
-
cluster_env = self._find_or_create_cluster_env(
|
984
|
-
cluster_env_name,
|
985
|
-
anonymous=not name,
|
986
|
-
image_uri=image_uri_str,
|
987
|
-
registry_login_secret=registry_login_secret,
|
988
|
-
ray_version=ray_version,
|
989
|
-
)
|
990
|
-
for build in self.list_cluster_env_builds(cluster_env.id):
|
991
|
-
if (
|
992
|
-
# NOTE: Ignore ray version mismatch for now. We plan to eventually remove ray version from the API model.
|
993
|
-
build.docker_image_name == image_uri_str
|
994
|
-
and build.registry_login_secret == registry_login_secret
|
995
|
-
and build.status == ClusterEnvironmentBuildStatus.SUCCEEDED
|
996
|
-
):
|
997
|
-
return build.id
|
998
|
-
|
999
|
-
# Still create a new build if the cluster env already exists but the build does not match the image_uri.
|
1000
|
-
result = self._external_api_client.create_cluster_environment_build(
|
1001
|
-
CreateClusterEnvironmentBuild(
|
1002
|
-
# For historical reasons, we have to use docker_image_name instead of image_uri; but it is just a URI to the image.
|
1003
|
-
cluster_environment_id=cluster_env.id,
|
1004
|
-
docker_image_name=image_uri_str,
|
965
|
+
build = self._internal_api_client.get_or_create_build_from_image_uri_api_v2_builds_get_or_create_build_from_image_uri_post(
|
966
|
+
GetOrCreateBuildFromImageUriRequest(
|
967
|
+
image_uri=str(image_uri),
|
1005
968
|
registry_login_secret=registry_login_secret,
|
1006
|
-
ray_version=ray_version
|
969
|
+
ray_version=ray_version,
|
970
|
+
cluster_env_name=name,
|
1007
971
|
)
|
1008
972
|
).result
|
1009
|
-
|
1010
|
-
assert result.completed
|
1011
|
-
return result.cluster_environment_build_id
|
973
|
+
return build.id
|
1012
974
|
|
1013
975
|
@handle_api_exceptions
|
1014
976
|
def send_workspace_notification(
|
@@ -8,6 +8,7 @@ from anyscale.client.openapi_client.models import (
|
|
8
8
|
AdminCreateUser,
|
9
9
|
AnyscaleServiceAccount,
|
10
10
|
Cloud,
|
11
|
+
ClusteroperationResponse,
|
11
12
|
ComputeTemplateConfig,
|
12
13
|
CreateCloudCollaborator,
|
13
14
|
CreateExperimentalWorkspace,
|
@@ -54,7 +55,7 @@ from anyscale.utils.workspace_notification import WorkspaceNotification
|
|
54
55
|
# Maybe just make it part of the release process to update it, or fetch the
|
55
56
|
# default builds and get the latest one. The best thing to do is probably
|
56
57
|
# to populate this in the backend.
|
57
|
-
DEFAULT_RAY_VERSION = "2.
|
58
|
+
DEFAULT_RAY_VERSION = "2.47.1" # RAY_RELEASE_UPDATE: update to latest version.
|
58
59
|
DEFAULT_PYTHON_VERSION = "py311"
|
59
60
|
RUNTIME_ENV_PACKAGE_FORMAT = "pkg_{content_hash}.zip"
|
60
61
|
|
@@ -175,6 +176,16 @@ class AnyscaleClientInterface(ABC):
|
|
175
176
|
"""Batch add collaborators to a cloud."""
|
176
177
|
raise NotImplementedError
|
177
178
|
|
179
|
+
@abstractmethod
|
180
|
+
def terminate_system_cluster(self, cloud_id: str) -> ClusteroperationResponse:
|
181
|
+
"""Terminate the system cluster for the provided cloud ID."""
|
182
|
+
raise NotImplementedError
|
183
|
+
|
184
|
+
@abstractmethod
|
185
|
+
def describe_system_workload_get_status(self, cloud_id: str) -> str:
|
186
|
+
"""Get the status of the system cluster for the provided cloud ID."""
|
187
|
+
raise NotImplementedError
|
188
|
+
|
178
189
|
@abstractmethod
|
179
190
|
def create_compute_config(
|
180
191
|
self, config: ComputeTemplateConfig, *, name: Optional[str] = None
|
@@ -19,6 +19,9 @@ from anyscale.client.openapi_client.models import (
|
|
19
19
|
AnyscaleServiceAccount,
|
20
20
|
Cloud,
|
21
21
|
CloudProviders,
|
22
|
+
ClusterOperation,
|
23
|
+
ClusteroperationResponse,
|
24
|
+
ClusterState,
|
22
25
|
ComputeTemplateConfig,
|
23
26
|
CreateCloudCollaborator,
|
24
27
|
CreateExperimentalWorkspace,
|
@@ -177,6 +180,7 @@ class FakeAnyscaleClient(AnyscaleClientInterface):
|
|
177
180
|
self._organization_collaborators: List[OrganizationCollaborator] = []
|
178
181
|
self._organization_invitations: Dict[str, OrganizationInvitation] = {}
|
179
182
|
self._resource_quotas: Dict[str, ResourceQuota] = {}
|
183
|
+
self._system_cluster_status: Dict[str, str] = {}
|
180
184
|
|
181
185
|
# Cloud ID -> Cloud.
|
182
186
|
self._clouds: Dict[str, Cloud] = {
|
@@ -369,6 +373,7 @@ class FakeAnyscaleClient(AnyscaleClientInterface):
|
|
369
373
|
|
370
374
|
def add_cloud(self, cloud: Cloud):
|
371
375
|
self._clouds[cloud.id] = cloud
|
376
|
+
self._system_cluster_status[cloud.id] = ClusterState.RUNNING
|
372
377
|
|
373
378
|
def get_cloud(self, *, cloud_id: str) -> Optional[Cloud]:
|
374
379
|
return self._clouds.get(cloud_id, None)
|
@@ -401,6 +406,25 @@ class FakeAnyscaleClient(AnyscaleClientInterface):
|
|
401
406
|
else:
|
402
407
|
self._cloud_collaborators[cloud_id].extend(collaborators)
|
403
408
|
|
409
|
+
def terminate_system_cluster(
|
410
|
+
self, cloud_id: str
|
411
|
+
) -> Optional[ClusteroperationResponse]:
|
412
|
+
self._system_cluster_status[cloud_id] = ClusterState.TERMINATING
|
413
|
+
return ClusteroperationResponse(
|
414
|
+
result=ClusterOperation(
|
415
|
+
id="sop_123",
|
416
|
+
completed=False,
|
417
|
+
progress=None,
|
418
|
+
result=None,
|
419
|
+
cluster_id="fake-system-cluster-id",
|
420
|
+
cluster_operation_type="terminate",
|
421
|
+
)
|
422
|
+
)
|
423
|
+
|
424
|
+
def describe_system_workload_get_status(self, cloud_id: str) -> str:
|
425
|
+
self._system_cluster_status[cloud_id] = ClusterState.TERMINATED
|
426
|
+
return self._system_cluster_status[cloud_id]
|
427
|
+
|
404
428
|
def add_compute_config(self, compute_config: DecoratedComputeTemplate) -> int:
|
405
429
|
compute_config.version = (
|
406
430
|
len(self._compute_config_name_to_ids[compute_config.name]) + 1
|
@@ -436,12 +436,14 @@ ALL_MODULES = [
|
|
436
436
|
cloud_commands.add_collaborators,
|
437
437
|
cloud_commands.get_cloud,
|
438
438
|
cloud_commands.get_default_cloud,
|
439
|
+
cloud_commands.terminate_system_cluster,
|
439
440
|
],
|
440
441
|
sdk_prefix="anyscale.cloud",
|
441
442
|
sdk_commands=[
|
442
443
|
anyscale.cloud.add_collaborators,
|
443
444
|
anyscale.cloud.get,
|
444
445
|
anyscale.cloud.get_default,
|
446
|
+
anyscale.cloud.terminate_system_cluster,
|
445
447
|
],
|
446
448
|
models=[
|
447
449
|
CloudPermissionLevel,
|