syntax = "proto3"; package csi.v0; option go_package = "csi"; service Identity { rpc GetPluginInfo(GetPluginInfoRequest) returns (GetPluginInfoResponse) {} rpc GetPluginCapabilities(GetPluginCapabilitiesRequest) returns (GetPluginCapabilitiesResponse) {} rpc Probe (ProbeRequest) returns (ProbeResponse) {} } service Controller { rpc CreateVolume (CreateVolumeRequest) returns (CreateVolumeResponse) {} rpc DeleteVolume (DeleteVolumeRequest) returns (DeleteVolumeResponse) {} rpc ControllerPublishVolume (ControllerPublishVolumeRequest) returns (ControllerPublishVolumeResponse) {} rpc ControllerUnpublishVolume (ControllerUnpublishVolumeRequest) returns (ControllerUnpublishVolumeResponse) {} rpc ValidateVolumeCapabilities (ValidateVolumeCapabilitiesRequest) returns (ValidateVolumeCapabilitiesResponse) {} rpc ListVolumes (ListVolumesRequest) returns (ListVolumesResponse) {} rpc GetCapacity (GetCapacityRequest) returns (GetCapacityResponse) {} rpc ControllerGetCapabilities (ControllerGetCapabilitiesRequest) returns (ControllerGetCapabilitiesResponse) {} } service Node { rpc NodeStageVolume (NodeStageVolumeRequest) returns (NodeStageVolumeResponse) {} rpc NodeUnstageVolume (NodeUnstageVolumeRequest) returns (NodeUnstageVolumeResponse) {} rpc NodePublishVolume (NodePublishVolumeRequest) returns (NodePublishVolumeResponse) {} rpc NodeUnpublishVolume (NodeUnpublishVolumeRequest) returns (NodeUnpublishVolumeResponse) {} rpc NodeGetId (NodeGetIdRequest) returns (NodeGetIdResponse) {} rpc NodeGetCapabilities (NodeGetCapabilitiesRequest) returns (NodeGetCapabilitiesResponse) {} } message GetPluginInfoRequest { } message GetPluginInfoResponse { // The name MUST follow reverse domain name notation format // (https://en.wikipedia.org/wiki/Reverse_domain_name_notation). // It SHOULD include the plugin's host company name and the plugin // name, to minimize the possibility of collisions. It MUST be 63 // characters or less, beginning and ending with an alphanumeric // character ([a-z0-9A-Z]) with dashes (-), underscores (_), // dots (.), and alphanumerics between. This field is REQUIRED. string name = 1; // This field is REQUIRED. Value of this field is opaque to the CO. string vendor_version = 2; // This field is OPTIONAL. Values are opaque to the CO. map manifest = 3; } message GetPluginCapabilitiesRequest { } message GetPluginCapabilitiesResponse { // All the capabilities that the controller service supports. This // field is OPTIONAL. repeated PluginCapability capabilities = 2; } // Specifies a capability of the plugin. message PluginCapability { message Service { enum Type { UNKNOWN = 0; // CONTROLLER_SERVICE indicates that the Plugin provides RPCs for // the ControllerService. Plugins SHOULD provide this capability. // In rare cases certain plugins may wish to omit the // ControllerService entirely from their implementation, but such // SHOULD NOT be the common case. // The presence of this capability determines whether the CO will // attempt to invoke the REQUIRED ControllerService RPCs, as well // as specific RPCs as indicated by ControllerGetCapabilities. CONTROLLER_SERVICE = 1; } Type type = 1; } oneof type { // Service that the plugin supports. Service service = 1; } } message ProbeRequest { } message ProbeResponse { // Intentionally empty. } message CreateVolumeRequest { // The suggested name for the storage space. This field is REQUIRED. // It serves two purposes: // 1) Idempotency - This name is generated by the CO to achieve // idempotency. If `CreateVolume` fails, the volume may or may not // be provisioned. In this case, the CO may call `CreateVolume` // again, with the same name, to ensure the volume exists. The // Plugin should ensure that multiple `CreateVolume` calls for the // same name do not result in more than one piece of storage // provisioned corresponding to that name. If a Plugin is unable to // enforce idempotency, the CO's error recovery logic could result // in multiple (unused) volumes being provisioned. // 2) Suggested name - Some storage systems allow callers to specify // an identifier by which to refer to the newly provisioned // storage. If a storage system supports this, it can optionally // use this name as the identifier for the new volume. string name = 1; // This field is OPTIONAL. This allows the CO to specify the capacity // requirement of the volume to be provisioned. If not specified, the // Plugin MAY choose an implementation-defined capacity range. CapacityRange capacity_range = 2; // The capabilities that the provisioned volume MUST have: the Plugin // MUST provision a volume that could satisfy ALL of the // capabilities specified in this list. The Plugin MUST assume that // the CO MAY use the provisioned volume later with ANY of the // capabilities specified in this list. This also enables the CO to do // early validation: if ANY of the specified volume capabilities are // not supported by the Plugin, the call SHALL fail. This field is // REQUIRED. repeated VolumeCapability volume_capabilities = 3; // Plugin specific parameters passed in as opaque key-value pairs. // This field is OPTIONAL. The Plugin is responsible for parsing and // validating these parameters. COs will treat these as opaque. map parameters = 4; // Secrets required by plugin to complete volume creation request. // A secret is a string to string map where the key identifies the // name of the secret (e.g. "username" or "password"), and the value // contains the secret data (e.g. "bob" or "abc123"). // Each key MUST consist of alphanumeric characters, '-', '_' or '.'. // Each value MUST contain a valid string. An SP MAY choose to accept // binary (non-string) data by using a binary-to-text encoding scheme, // like base64. // An SP SHALL advertise the requirements for required secret keys and // values in documentation. // CO SHALL permit passing through the required secrets. // A CO MAY pass the same secrets to all RPCs, therefore the keys for // all unique secrets that an SP expects must be unique across all CSI // operations. // This information is sensitive and MUST be treated as such (not // logged, etc.) by the CO. // This field is OPTIONAL. map controller_create_secrets = 5; } message CreateVolumeResponse { // Contains all attributes of the newly created volume that are // relevant to the CO along with information required by the Plugin // to uniquely identify the volume. This field is REQUIRED. Volume volume = 1; } // Specify a capability of a volume. message VolumeCapability { // Indicate that the volume will be accessed via the block device API. message BlockVolume { // Intentionally empty, for now. } // Indicate that the volume will be accessed via the filesystem API. message MountVolume { // The filesystem type. This field is OPTIONAL. // An empty string is equal to an unspecified field value. string fs_type = 1; // The mount options that can be used for the volume. This field is // OPTIONAL. `mount_flags` MAY contain sensitive information. // Therefore, the CO and the Plugin MUST NOT leak this information // to untrusted entities. The total size of this repeated field // SHALL NOT exceed 4 KiB. repeated string mount_flags = 2; } // Specify how a volume can be accessed. message AccessMode { enum Mode { UNKNOWN = 0; // Can only be published once as read/write on a single node, at // any given time. SINGLE_NODE_WRITER = 1; // Can only be published once as readonly on a single node, at // any given time. SINGLE_NODE_READER_ONLY = 2; // Can be published as readonly at multiple nodes simultaneously. MULTI_NODE_READER_ONLY = 3; // Can be published at multiple nodes simultaneously. Only one of // the node can be used as read/write. The rest will be readonly. MULTI_NODE_SINGLE_WRITER = 4; // Can be published as read/write at multiple nodes // simultaneously. MULTI_NODE_MULTI_WRITER = 5; } // This field is REQUIRED. Mode mode = 1; } // Specifies what API the volume will be accessed using. One of the // following fields MUST be specified. oneof access_type { BlockVolume block = 1; MountVolume mount = 2; } // This is a REQUIRED field. AccessMode access_mode = 3; } // The capacity of the storage space in bytes. To specify an exact size, // `required_bytes` and `limit_bytes` can be set to the same value. At // least one of the these fields MUST be specified. message CapacityRange { // Volume must be at least this big. This field is OPTIONAL. // A value of 0 is equal to an unspecified field value. // The value of this field MUST NOT be negative. int64 required_bytes = 1; // Volume must not be bigger than this. This field is OPTIONAL. // A value of 0 is equal to an unspecified field value. // The value of this field MUST NOT be negative. int64 limit_bytes = 2; } // The information about a provisioned volume. message Volume { // The capacity of the volume in bytes. This field is OPTIONAL. If not // set (value of 0), it indicates that the capacity of the volume is // unknown (e.g., NFS share). // The value of this field MUST NOT be negative. int64 capacity_bytes = 1; // Contains identity information for the created volume. This field is // REQUIRED. The identity information will be used by the CO in // subsequent calls to refer to the provisioned volume. string id = 2; // Attributes reflect static properties of a volume and MUST be passed // to volume validation and publishing calls. // Attributes SHALL be opaque to a CO. Attributes SHALL NOT be mutable // and SHALL be safe for the CO to cache. Attributes SHOULD NOT // contain sensitive information. Attributes MAY NOT uniquely identify // a volume. A volume uniquely identified by `id` SHALL always report // the same attributes. This field is OPTIONAL and when present MUST // be passed to volume validation and publishing calls. map attributes = 3; } message DeleteVolumeRequest { // The ID of the volume to be deprovisioned. // This field is REQUIRED. string volume_id = 1; // Secrets required by plugin to complete volume deletion request. // A secret is a string to string map where the key identifies the // name of the secret (e.g. "username" or "password"), and the value // contains the secret data (e.g. "bob" or "abc123"). // Each key MUST consist of alphanumeric characters, '-', '_' or '.'. // Each value MUST contain a valid string. An SP MAY choose to accept // binary (non-string) data by using a binary-to-text encoding scheme, // like base64. // An SP SHALL advertise the requirements for required secret keys and // values in documentation. // CO SHALL permit passing through the required secrets. // A CO MAY pass the same secrets to all RPCs, therefore the keys for // all unique secrets that an SP expects must be unique across all CSI // operations. // This information is sensitive and MUST be treated as such (not // logged, etc.) by the CO. // This field is OPTIONAL. map controller_delete_secrets = 2; } message DeleteVolumeResponse { } message ControllerPublishVolumeRequest { // The ID of the volume to be used on a node. // This field is REQUIRED. string volume_id = 1; // The ID of the node. This field is REQUIRED. The CO SHALL set this // field to match the node ID returned by `NodeGetId`. string node_id = 2; // The capability of the volume the CO expects the volume to have. // This is a REQUIRED field. VolumeCapability volume_capability = 3; // Whether to publish the volume in readonly mode. This field is // REQUIRED. bool readonly = 4; // Secrets required by plugin to complete controller publish volume // request. // A secret is a string to string map where the key identifies the // name of the secret (e.g. "username" or "password"), and the value // contains the secret data (e.g. "bob" or "abc123"). // Each key MUST consist of alphanumeric characters, '-', '_' or '.'. // Each value MUST contain a valid string. An SP MAY choose to accept // binary (non-string) data by using a binary-to-text encoding scheme, // like base64. // An SP SHALL advertise the requirements for required secret keys and // values in documentation. // CO SHALL permit passing through the required secrets. // A CO MAY pass the same secrets to all RPCs, therefore the keys for // all unique secrets that an SP expects must be unique across all CSI // operations. // This information is sensitive and MUST be treated as such (not // logged, etc.) by the CO. // This field is OPTIONAL. map controller_publish_secrets = 5; // Attributes of the volume to be used on a node. This field is // OPTIONAL and MUST match the attributes of the Volume identified // by `volume_id`. map volume_attributes = 6; } message ControllerPublishVolumeResponse { // The SP specific information that will be passed to the Plugin in // the subsequent `NodeStageVolume` or `NodePublishVolume` calls // for the given volume. // This information is opaque to the CO. This field is OPTIONAL. map publish_info = 1; } message ControllerUnpublishVolumeRequest { // The ID of the volume. This field is REQUIRED. string volume_id = 1; // The ID of the node. This field is OPTIONAL. The CO SHOULD set this // field to match the node ID returned by `NodeGetId` or leave it // unset. If the value is set, the SP MUST unpublish the volume from // the specified node. If the value is unset, the SP MUST unpublish // the volume from all nodes it is published to. string node_id = 2; // Secrets required by plugin to complete controller unpublish volume // request. This SHOULD be the same secrets passed to the // ControllerPublishVolume. // call for the specified volume. // A secret is a string to string map where the key identifies the // name of the secret (e.g. "username" or "password"), and the value // contains the secret data (e.g. "bob" or "abc123"). // Each key MUST consist of alphanumeric characters, '-', '_' or '.'. // Each value MUST contain a valid string. An SP MAY choose to accept // binary (non-string) data by using a binary-to-text encoding scheme, // like base64. // An SP SHALL advertise the requirements for required secret keys and // values in documentation. // CO SHALL permit passing through the required secrets. // A CO MAY pass the same secrets to all RPCs, therefore the keys for // all unique secrets that an SP expects must be unique across all CSI // operations. // This information is sensitive and MUST be treated as such (not // logged, etc.) by the CO. // This field is OPTIONAL. map controller_unpublish_secrets = 3; } message ControllerUnpublishVolumeResponse { } message ValidateVolumeCapabilitiesRequest { // The ID of the volume to check. This field is REQUIRED. string volume_id = 1; // The capabilities that the CO wants to check for the volume. This // call SHALL return "supported" only if all the volume capabilities // specified below are supported. This field is REQUIRED. repeated VolumeCapability volume_capabilities = 2; // Attributes of the volume to check. This field is OPTIONAL and MUST // match the attributes of the Volume identified by `volume_id`. map volume_attributes = 3; } message ValidateVolumeCapabilitiesResponse { // True if the Plugin supports the specified capabilities for the // given volume. This field is REQUIRED. bool supported = 1; // Message to the CO if `supported` above is false. This field is // OPTIONAL. // An empty string is equal to an unspecified field value. string message = 2; } message ListVolumesRequest { // If specified (non-zero value), the Plugin MUST NOT return more // entries than this number in the response. If the actual number of // entries is more than this number, the Plugin MUST set `next_token` // in the response which can be used to get the next page of entries // in the subsequent `ListVolumes` call. This field is OPTIONAL. If // not specified (zero value), it means there is no restriction on the // number of entries that can be returned. // The value of this field MUST NOT be negative. int32 max_entries = 1; // A token to specify where to start paginating. Set this field to // `next_token` returned by a previous `ListVolumes` call to get the // next page of entries. This field is OPTIONAL. // An empty string is equal to an unspecified field value. string starting_token = 2; } message ListVolumesResponse { message Entry { Volume volume = 1; } repeated Entry entries = 1; // This token allows you to get the next page of entries for // `ListVolumes` request. If the number of entries is larger than // `max_entries`, use the `next_token` as a value for the // `starting_token` field in the next `ListVolumes` request. This // field is OPTIONAL. // An empty string is equal to an unspecified field value. string next_token = 2; } message GetCapacityRequest { // If specified, the Plugin SHALL report the capacity of the storage // that can be used to provision volumes that satisfy ALL of the // specified `volume_capabilities`. These are the same // `volume_capabilities` the CO will use in `CreateVolumeRequest`. // This field is OPTIONAL. repeated VolumeCapability volume_capabilities = 1; // If specified, the Plugin SHALL report the capacity of the storage // that can be used to provision volumes with the given Plugin // specific `parameters`. These are the same `parameters` the CO will // use in `CreateVolumeRequest`. This field is OPTIONAL. map parameters = 2; } message GetCapacityResponse { // The available capacity of the storage that can be used to // provision volumes. If `volume_capabilities` or `parameters` is // specified in the request, the Plugin SHALL take those into // consideration when calculating the available capacity of the // storage. This field is REQUIRED. // The value of this field MUST NOT be negative. int64 available_capacity = 1; } message ControllerGetCapabilitiesRequest { } message ControllerGetCapabilitiesResponse { // All the capabilities that the controller service supports. This // field is OPTIONAL. repeated ControllerServiceCapability capabilities = 2; } // Specifies a capability of the controller service. message ControllerServiceCapability { message RPC { enum Type { UNKNOWN = 0; CREATE_DELETE_VOLUME = 1; PUBLISH_UNPUBLISH_VOLUME = 2; LIST_VOLUMES = 3; GET_CAPACITY = 4; } Type type = 1; } oneof type { // RPC that the controller supports. RPC rpc = 1; } } message NodeStageVolumeRequest { // The ID of the volume to publish. This field is REQUIRED. string volume_id = 1; // The CO SHALL set this field to the value returned by // `ControllerPublishVolume` if the corresponding Controller Plugin // has `PUBLISH_UNPUBLISH_VOLUME` controller capability, and SHALL be // left unset if the corresponding Controller Plugin does not have // this capability. This is an OPTIONAL field. map publish_info = 2; // The path to which the volume will be published. It MUST be an // absolute path in the root filesystem of the process serving this // request. The CO SHALL ensure that there is only one // staging_target_path per volume. // This is a REQUIRED field. string staging_target_path = 3; // The capability of the volume the CO expects the volume to have. // This is a REQUIRED field. VolumeCapability volume_capability = 4; // Secrets required by plugin to complete node stage volume request. // A secret is a string to string map where the key identifies the // name of the secret (e.g. "username" or "password"), and the value // contains the secret data (e.g. "bob" or "abc123"). // Each key MUST consist of alphanumeric characters, '-', '_' or '.'. // Each value MUST contain a valid string. An SP MAY choose to accept // binary (non-string) data by using a binary-to-text encoding scheme, // like base64. // An SP SHALL advertise the requirements for required secret keys and // values in documentation. // CO SHALL permit passing through the required secrets. // A CO MAY pass the same secrets to all RPCs, therefore the keys for // all unique secrets that an SP expects must be unique across all CSI // operations. // This information is sensitive and MUST be treated as such (not // logged, etc.) by the CO. // This field is OPTIONAL. map node_stage_secrets = 5; // Attributes of the volume to publish. This field is OPTIONAL and // MUST match the attributes of the VolumeInfo identified by // `volume_id`. map volume_attributes = 6; } message NodeStageVolumeResponse { } message NodeUnstageVolumeRequest { // The ID of the volume. This field is REQUIRED. string volume_id = 1; // The path at which the volume was published. It MUST be an absolute // path in the root filesystem of the process serving this request. // This is a REQUIRED field. string staging_target_path = 2; } message NodeUnstageVolumeResponse { } message NodePublishVolumeRequest { // The ID of the volume to publish. This field is REQUIRED. string volume_id = 1; // The CO SHALL set this field to the value returned by // `ControllerPublishVolume` if the corresponding Controller Plugin // has `PUBLISH_UNPUBLISH_VOLUME` controller capability, and SHALL be // left unset if the corresponding Controller Plugin does not have // this capability. This is an OPTIONAL field. map publish_info = 2; // The path to which the device was mounted by `NodeStageVolume`. // It MUST be an absolute path in the root filesystem of the process // serving this request. // It MUST be set if the Node Plugin implements the // `STAGE_UNSTAGE_VOLUME` node capability. // This is an OPTIONAL field. string staging_target_path = 3; // The path to which the volume will be published. It MUST be an // absolute path in the root filesystem of the process serving this // request. The CO SHALL ensure uniqueness of target_path per volume. // The CO SHALL ensure that the path exists, and that the process // serving the request has `read` and `write` permissions to the path. // This is a REQUIRED field. string target_path = 4; // The capability of the volume the CO expects the volume to have. // This is a REQUIRED field. VolumeCapability volume_capability = 5; // Whether to publish the volume in readonly mode. This field is // REQUIRED. bool readonly = 6; // Secrets required by plugin to complete node publish volume request. // A secret is a string to string map where the key identifies the // name of the secret (e.g. "username" or "password"), and the value // contains the secret data (e.g. "bob" or "abc123"). // Each key MUST consist of alphanumeric characters, '-', '_' or '.'. // Each value MUST contain a valid string. An SP MAY choose to accept // binary (non-string) data by using a binary-to-text encoding scheme, // like base64. // An SP SHALL advertise the requirements for required secret keys and // values in documentation. // CO SHALL permit passing through the required secrets. // A CO MAY pass the same secrets to all RPCs, therefore the keys for // all unique secrets that an SP expects must be unique across all CSI // operations. // This information is sensitive and MUST be treated as such (not // logged, etc.) by the CO. // This field is OPTIONAL. map node_publish_secrets = 7; // Attributes of the volume to publish. This field is OPTIONAL and // MUST match the attributes of the Volume identified by // `volume_id`. map volume_attributes = 8; } message NodePublishVolumeResponse { } message NodeUnpublishVolumeRequest { // The ID of the volume. This field is REQUIRED. string volume_id = 1; // The path at which the volume was published. It MUST be an absolute // path in the root filesystem of the process serving this request. // This is a REQUIRED field. string target_path = 2; } message NodeUnpublishVolumeResponse { } message NodeGetIdRequest { } message NodeGetIdResponse { // The ID of the node as understood by the SP which SHALL be used by // CO in subsequent `ControllerPublishVolume`. // This is a REQUIRED field. string node_id = 1; } message NodeGetCapabilitiesRequest { } message NodeGetCapabilitiesResponse { // All the capabilities that the node service supports. This field // is OPTIONAL. repeated NodeServiceCapability capabilities = 1; } // Specifies a capability of the node service. message NodeServiceCapability { message RPC { enum Type { UNKNOWN = 0; STAGE_UNSTAGE_VOLUME = 1; } Type type = 1; } oneof type { // RPC that the controller supports. RPC rpc = 1; } }