Disks in virtual machines (VirtualDisk resources) are essential for writing and storing data. They ensure the proper functioning of applications and operating systems. The structure of these disks includes storage provided by the platform.

Depending on the storage properties, disks during creation and virtual machines during operation may exhibit different behaviors.

VolumeBindingMode properties:

Immediate — disk is created immediately after the resource is created (it is assumed that the disk will be available for attachment to a virtual machine on any cluster node).

Immediate

WaitForFirstConsumer — disk is created only after it is attached to a virtual machine and will be created on the node where the virtual machine is launched.

WaitForFirstConsumer

AccessMode:

ReadWriteOnce (RWO) — access to the disk is granted to only one instance of a virtual machine. Live migration of virtual machines with such disks is not possible.

ReadWriteMany (RWX) — multiple access to the disk is allowed. Live migration of virtual machines with such disks is possible.

When a disk is created, the controller automatically determines the most optimal parameters supported by the storage.

Warning Creating disks from ISO images is not allowed.

To find the available storage options on the platform, run the following command:

d8 k get storageclass

Example output:

NAME                          PROVISIONER                           RECLAIMPOLICY   VOLUMEBINDINGMODE      ALLOWVOLUMEEXPANSION   AGE
i-linstor-thin-r1 (default)   replicated.csi.storage.deckhouse.io   Delete          Immediate              true                   48d
i-linstor-thin-r2             replicated.csi.storage.deckhouse.io   Delete          Immediate              true                   48d
i-linstor-thin-r3             replicated.csi.storage.deckhouse.io   Delete          Immediate              true                   48d
linstor-thin-r1               replicated.csi.storage.deckhouse.io   Delete          WaitForFirstConsumer   true                   48d
linstor-thin-r2               replicated.csi.storage.deckhouse.io   Delete          WaitForFirstConsumer   true                   48d
linstor-thin-r3               replicated.csi.storage.deckhouse.io   Delete          WaitForFirstConsumer   true                   48d
nfs-4-1-wffc                  nfs.csi.k8s.io                        Delete          WaitForFirstConsumer   true                   30d

The (default) marker next to the class name indicates that this StorageClass will be used by default if the user has not explicitly specified the class name in the resource being created. If the StorageClass is missing by default in the cluster, the user must explicitly specify the required StorageClass in the resource specification. Deckhouse Virtualization Platform also allows you to set individual settings for storing disks and images.

Storage class settings for disks

The storage class settings for disks are defined in the .spec.settings.virtualDisks parameter of the module settings. Example:

spec:
...
settings:
virtualDisks:
allowedStorageClassNames:
- sc-1
- sc-2
defaultStorageClassName: sc-1
  • allowedStorageClassNames — (optional) is a list of valid StorageClass for creating a VirtualDisk, which can be explicitly specified in the resource specification.
  • defaultStorageClassName — (optional) is the StorageClass used by default when creating a VirtualDisk if the .spec.persistentVolumeClaim.storageClassName parameter is not specified.

Fine-tuning storage classes for disks

When creating a disk, the controller will automatically select the most optimal parameters supported by the storage based on the data it knows. Priorities for configuring PersistentVolumeClaim parameters when creating a disk by automatically detecting storage characteristics:

  • RWX + Block
  • RWX + FileSystem
  • RWO + Block
  • RWO + FileSystem.

If the storage is unknown and it is impossible to determine its parameters automatically, the mode is used: RWO + FileSystem

Creating an empty disk

Empty disks are typically used for installing operating systems or storing data.

To create a disk use:

d8 k apply -f - <<EOF
apiVersion: virtualization.deckhouse.io/v1alpha2
kind: VirtualDisk
metadata:
  name: blank-disk
spec:
  # Disk storage settings.
  persistentVolumeClaim:
    # Replace with your StorageClass name.
    storageClassName: i-linstor-thin-r2
    size: 100Mi
EOF

After creation, the VirtualDisk resource can be in the following states:

  • Pending: Waiting for readiness of all dependent resources required for disk creation.
  • Provisioning: The disk creation process is ongoing.
  • Resizing: The disk resizing process is ongoing.
  • WaitForFirstConsumer: The disk is waiting for a virtual machine that will use it.
  • Ready: The disk is created and ready for use.
  • Failed: An error occurred during the creation process.
  • Terminating: The disk deletion process is ongoing. This process may “hang” in this state if the disk is still attached to a virtual machine.

Until the disk reaches the Ready phase, the entire .spec block can be modified. Changing it will restart the disk creation process.

Check the disk’s status after creation:

d8 k get vd blank-disk

Example output:

NAME         PHASE     CAPACITY   AGE
blank-disk   Ready     100Mi      1m2s

Creating a disk from an image

Disks can be created and populated with data from previously created images such as ClusterVirtualImage and VirtualImage.

When creating a disk, you can specify its desired size, which must be equal to or greater than the unpacked size of the image. If the size is not specified, the disk will be created with the same size as the source disk image.

Using a previously created project image VirtualImage, here’s an example command to determine the size of the unpacked image:

d8 k get cvi ubuntu-22.04 -o wide

Example output:

NAME           PHASE   CDROM   PROGRESS   STOREDSIZE   UNPACKEDSIZE   REGISTRY URL                                                                       AGE
ubuntu-22.04   Ready   false   100%       285.9Mi      2.5Gi          dvcr.d8-virtualization.svc/cvi/ubuntu-22.04:eac95605-7e0b-4a32-bb50-cc7284fd89d0   122m

The required size is indicated in the UNPACKEDSIZE column and is 2.5Gi.

Create a disk from this image:

d8 k apply -f - <<EOF
apiVersion: virtualization.deckhouse.io/v1alpha2
kind: VirtualDisk
metadata:
  name: linux-vm-root
spec:
  # Disk storage parameters configuration.
  persistentVolumeClaim:
    # Specify a size greater than the unpacked image size.
    size: 10Gi
    # Substitute with your StorageClass name.
    storageClassName: i-linstor-thin-r2
  # The source from which the disk is created.
  dataSource:
    type: ObjectRef
    objectRef:
      kind: VirtualImage
      name: ubuntu-22.04
EOF

Now, create a disk without specifying its size:

d8 k apply -f - <<EOF
apiVersion: virtualization.deckhouse.io/v1alpha2
kind: VirtualDisk
metadata:
  name: linux-vm-root-2
spec:
  # Disk storage parameters configuration.
  persistentVolumeClaim:
    # Substitute with your StorageClass name.
    storageClassName: i-linstor-thin-r2
  # The source from which the disk is created.
  dataSource:
    type: ObjectRef
    objectRef:
      kind: VirtualImage
      name: ubuntu-22.04
EOF

Check the state of the disks after creation:

d8 k get vd

Example output:

NAME           PHASE   CAPACITY   AGE
linux-vm-root    Ready   10Gi       7m52s
linux-vm-root-2  Ready   2590Mi     7m15s

Resizing a disk

The size of disks can be increased even if they are already attached to a running virtual machine. Changes are made to the spec.persistentVolumeClaim.size field:

Check the size before the change:

d8 k get vd linux-vm-root

Example output:

NAME          PHASE   CAPACITY   AGE
linux-vm-root   Ready   10Gi       10m

Apply the changes:

kubectl patch vd linux-vm-root --type merge -p '{"spec":{"persistentVolumeClaim":{"size":"11Gi"}}}'

Check the size after the change:

d8 k get vd linux-vm-root

Example output:

NAME          PHASE   CAPACITY   AGE
linux-vm-root   Ready   11Gi       12m