Skip to content

Commit

Permalink
Added Python API server client (#1561) (#1616)
Browse files Browse the repository at this point in the history
  • Loading branch information
kevin85421 authored Nov 2, 2023
1 parent 1cddad3 commit 0725be3
Show file tree
Hide file tree
Showing 28 changed files with 2,266 additions and 348 deletions.
48 changes: 25 additions & 23 deletions apiserver/Volumes.md
Original file line number Diff line number Diff line change
@@ -1,19 +1,18 @@
# Volumes support for Ray cluster by the API server

API server allows to specify multiple types of volumes mounted to the Ray pods (nodes). These include:

* [hostPath](https://kubernetes.io/docs/concepts/storage/volumes/#hostpath)
* [PVC](https://kubernetes.io/docs/concepts/storage/persistent-volumes/)
* [ephemeral](https://kubernetes.io/docs/concepts/storage/ephemeral-volumes/)
* [config maps](https://kubernetes.io/docs/concepts/storage/volumes/#configmap)
* [secrets](https://kubernetes.io/docs/concepts/storage/volumes/#secret)
* [empty dir](https://kubernetes.io/docs/concepts/storage/volumes/#emptydir)

Multiple volumes of different type can be mounted to both head and worker nodes, by defining a array of volumes
[hostPath](https://kubernetes.io/docs/concepts/storage/volumes/#hostpath),
[PVC](https://kubernetes.io/docs/concepts/storage/persistent-volumes/),
[ephemeral](https://kubernetes.io/docs/concepts/storage/ephemeral-volumes/),
[config maps](https://kubernetes.io/docs/concepts/storage/volumes/#configmap),
[secrets](https://kubernetes.io/docs/concepts/storage/volumes/#secret),
and [empty dir](https://kubernetes.io/docs/concepts/storage/volumes/#emptydir).
Multiple volumes of different type can be mounted to both head and worker nodes, by defining a volume array for them

## HostPath volumes

A hostPath volume mounts a file or directory from the host node's filesystem into your Pod. This is not something that most Pods will need, but it offers a powerful escape hatch for some applications.
A hostPath volume mounts a file or directory from the host node's filesystem into your Pod. This is not something that
most Pods will need, but it offers a powerful escape hatch for some applications.

For example, some uses for a hostPath are:

Expand All @@ -23,7 +22,7 @@ For example, some uses for a hostPath are:

The code below gives an example of hostPath volume definition:

```shell
```json
{
"name": "hostPath", # unique name
"source": "/tmp", # data location on host
Expand All @@ -36,27 +35,30 @@ The code below gives an example of hostPath volume definition:

## PVC volumes

A Persistent Volume Claim (PVC) is a request for storage by a user. It is similar to a Pod. Pods consume node resources and PVCs consume PV resources. Pods can request specific levels of resources (CPU and Memory). Claims can request specific size and access modes (e.g., they can be mounted `ReadWriteOnce`, `ReadOnlyMany` or `ReadWriteMany`).
A Persistent Volume Claim (PVC) is a request for storage by a user. It is similar to a Pod. Pods consume node resources and PVCs consume PV resources. Pods can request specific levels of resources (CPU and Memory). Claims can request
specific size and access modes (e.g., they can be mounted `ReadWriteOnce`, `ReadOnlyMany` or `ReadWriteMany`).

The caveat of using PVC volumes is that the same PVC is mounted to all nodes. As a result only PVCs with access
mode `ReadOnlyMany` can be used in this case.

The code below gives an example of PVC volume definition:

```shell
```json
{
"name": "pvc", # unique name
"mountPath": "/tmp/pvc", # mounting path
"source": "claim", # claim name
"volumeType": 0, # volume type - PVC
"source": "myclaim" # Claim name
"mountPropagationMode": 2, # mount propagation mode - bidirectional
"readOnly": false # read only
}
```

## Ephemeral volumes

Some application need additional storage but don't care whether that data is stored persistently across restarts. For example, caching services are often limited by memory size and can move infrequently used data into storage that is slower than memory with little impact on overall performance. Ephemeral volumes are designed for these use cases. Because volumes follow the Pod's lifetime and get created and deleted along with the Pod, Pods can be stopped and restarted without being limited to where some persistent volume is available.
Some application need additional storage but don't care whether that data is stored persistently across restarts. For example, caching services are often limited by memory size and can move infrequently used data into storage that is slower than memory with little impact on overall performance. Ephemeral volumes are designed for these use cases.

Because volumes follow the Pod's lifetime and get created and deleted along with the Pod, Pods can be stopped and restarted without being limited to where some persistent volume is available.

Although there are several option of ephemeral volumes, here we are using generic ephemeral volumes, which can be provided by all storage drivers that also support persistent volumes. Generic ephemeral volumes are similar to emptyDir volumes in the sense that they provide a per-pod directory for scratch data that is usually empty after provisioning. But they may also have additional features:

Expand All @@ -65,14 +67,14 @@ Although there are several option of ephemeral volumes, here we are using generi

The code below gives an example of ephemeral volume definition:

```shell
```json
{
"name": "ephemeral", # unique name
"mountPath": "/tmp/ephemeral" # mounting path,
"mountPropagationMode": 0, # mount propagation mode - None
"volumeType": 2, # volume type - ephemeral
"storage": "5Gi", # disk size
"storageClass": "default" # storage class - optional
"storageClass": "default", # storage class - optional
"accessMode": 0 # access mode RWO - optional
}
```
Expand All @@ -85,7 +87,7 @@ When referencing a ConfigMap, you provide the name of the ConfigMap in the volum

The code below gives an example of config map volume definition:

```shell
```json
{
"name":"code-sample", # Unique name
"mountPath":"/home/ray/samples", # mounting path
Expand All @@ -103,7 +105,7 @@ A secret volume is used to pass sensitive information, such as passwords, to Pod

The code below gives an example of secret volume definition:

```shell
```json
{
"name":"important-secret", # Unique name
"mountPath":"/home/ray/sensitive", # mounting path
Expand All @@ -121,11 +123,11 @@ An emptyDir volume is first created when a Pod is assigned to a node, and exists

The code below gives an example of empydir volume definition:

```shell
```json
{
"name": "emptyDir", # unique name
"mountPath": "/tmp/emptydir" # mounting path,
"volumeType": 5, # volume type - ephemeral
"storage": "5Gi", # max storage size - optional
"volumeType": 5, # vlume type - ephemeral
"storage": "5Gi", # max storage size - optional
}
```
````
1 change: 1 addition & 0 deletions apiserver/pkg/model/volumes.go
Original file line number Diff line number Diff line change
Expand Up @@ -78,6 +78,7 @@ func PopulateVolumes(podTemplate *v1.PodTemplateSpec) []*api.Volume {
MountPath: mount.MountPath,
MountPropagationMode: GetVolumeMountPropagation(mount),
VolumeType: api.Volume_PERSISTENT_VOLUME_CLAIM,
Source: vol.VolumeSource.PersistentVolumeClaim.ClaimName,
ReadOnly: vol.VolumeSource.PersistentVolumeClaim.ReadOnly,
})
continue
Expand Down
3 changes: 2 additions & 1 deletion apiserver/pkg/model/volumes_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -67,7 +67,7 @@ var podTemplateTest = v1.PodTemplateSpec{
Name: "pvc",
VolumeSource: v1.VolumeSource{
PersistentVolumeClaim: &v1.PersistentVolumeClaimVolumeSource{
ClaimName: "pvc",
ClaimName: "pvcclaim",
ReadOnly: false,
},
},
Expand Down Expand Up @@ -145,6 +145,7 @@ var expectedVolumes = []*api.Volume{
{
Name: "pvc",
MountPath: "/tmp/pvc",
Source: "pvcclaim",
VolumeType: api.Volume_PERSISTENT_VOLUME_CLAIM,
MountPropagationMode: api.Volume_BIDIRECTIONAL,
ReadOnly: false,
Expand Down
2 changes: 1 addition & 1 deletion apiserver/pkg/util/cluster.go
Original file line number Diff line number Diff line change
Expand Up @@ -673,7 +673,7 @@ func buildVols(apiVolumes []*api.Volume) ([]v1.Volume, error) {
Name: rayVol.Name,
VolumeSource: v1.VolumeSource{
PersistentVolumeClaim: &v1.PersistentVolumeClaimVolumeSource{
ClaimName: rayVol.Name,
ClaimName: rayVol.Source,
ReadOnly: rayVol.ReadOnly,
},
},
Expand Down
3 changes: 2 additions & 1 deletion apiserver/pkg/util/cluster_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,7 @@ var testFileVolume = &api.Volume{
var testPVCVolume = &api.Volume{
Name: "test-pvc",
VolumeType: api.Volume_PERSISTENT_VOLUME_CLAIM,
Source: "my-pvc",
MountPath: "/pvc/dir",
ReadOnly: true,
}
Expand Down Expand Up @@ -261,7 +262,7 @@ func TestBuildVolumes(t *testing.T) {
Name: testPVCVolume.Name,
VolumeSource: v1.VolumeSource{
PersistentVolumeClaim: &v1.PersistentVolumeClaimVolumeSource{
ClaimName: testPVCVolume.Name,
ClaimName: testPVCVolume.Source,
ReadOnly: testPVCVolume.ReadOnly,
},
},
Expand Down
4 changes: 2 additions & 2 deletions apiserver/test/cluster/cluster/cluster
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@ curl -X POST 'localhost:8888/apis/v1/namespaces/default/clusters' \
"clusterSpec": {
"headGroupSpec": {
"computeTemplate": "default-template",
"image": "rayproject/ray:2.6.3-py310",
"image": "rayproject/ray:2.7.0-py310",
"serviceType": "NodePort",
"rayStartParams": {
"dashboard-host": "0.0.0.0",
Expand All @@ -27,7 +27,7 @@ curl -X POST 'localhost:8888/apis/v1/namespaces/default/clusters' \
{
"groupName": "small-wg",
"computeTemplate": "default-template",
"image": "rayproject/ray:2.6.3-py310",
"image": "rayproject/ray:2.7.0-py310",
"replicas": 1,
"minReplicas": 0,
"maxReplicas": 5,
Expand Down
35 changes: 35 additions & 0 deletions clients/python-apiserver-client/.gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,35 @@



# Byte-compiled / optimized / DLL files
__pycache__/
*.py[cod]
*$py.class


# Distribution / packaging
bin/
build/
develop-eggs/
dist/
eggs/
lib/
lib64/
parts/
sdist/
var/
*.egg-info/
.installed.cfg
*.egg

# Installer logs
pip-log.txt
pip-delete-this-directory.txt

# Unit test / coverage reports
.tox/
htmlcov
.coverage
.cache
nosetests.xml
coverage.xml
Loading

0 comments on commit 0725be3

Please sign in to comment.