Pods are ephemeral and stateless.
Volumes bring persistence to pods.
Volumes provide external storage for pods and thier Containers and allow data to be shared between all containers with in a pod.
Containers has access to volume with in a same pod.
If node stops working, the pod can be rescheduled on another node and the volume can be attached to the new node.
It support many types of Storages.

[Volumes]
✤ awsElasticBlockStore
An awsElasticBlockStore volume mounts an Amazon Web Services (AWS) EBS volume into pod.
It is erased when a pod is removed, the contents of an EBS volume are persisted and the volume is unmounted.
The EBS volume can be pre-populated with data, and that data can be shared between pods.
It must create an EBS volume by using an command (aws ec2 create-volume) OR the AWS API before can use it.
There are some restrictions when using an awsElasticBlockStore volume:-
● The nodes on which pods are running must be AWS EC2 instances.
● Those instances need to be in the same region and availability zone as the EBS volume.
● EBS only supports a single EC2 instance mounting a volume.

✤ emptyDir
It creates empty directory first created when a Pod is assigned to a node.
It stays as long as pod is running.
Once pod is removed from a node, emptyDir is deleted forever. (OR) When a Pod is removed from a node for any reason, the data in the emptyDir is deleted permanently.
It's an temporary space.   
The emptyDir volume is initially empty. 
All containers in the Pod can read and write the same files in the emptyDir volume, though that volume can be mounted at the same or different paths in each container.
An emptyDir volume recreates when containers restart or crash. The data in this volume is deleted and lost when the pod is removed from the node, crashes, or dies.

✤ hostPath
A hostPath volume mounts a file or directory from the host node's filesystem into Pod.
The data is persistence even after the pod is terminated.
● "type: Directory" 
A directory must exist in the specified path.
● "type: DirectoryOrCreate" 
If no content is found in the specified path, an empty directory is created on demand.
The permission on the created directory is set to 0755.
The directory has the same group and ownership with kubelet.
● "type: File" 
A file must exist in the given specified path.
● "type: FileOrCreate" 
If no content is found in the specified path, an empty file is created.
The permission of the created file is set to 0644.
The file has the same group and ownership with kubelet.

✤ gitRepo
A gitRepo volume is an example of a volume plugin.
This plugin mounts an empty directory and clones a git repository into this directory for Pod to use.

[Ephemeral Volumes]
Ephemeral Volumes is a temporary space.
Ephemeral Volumes in the sense that it is cleaned up when the workload is deleted or the container crashes.
There are many types of Ephemeral Volumes.
● emptyDir
The emptyDir are provided as local ephemeral storage. They are managed by kubelet on each node.
● configMap, downwardAPI, secret
It inject different kinds of Kubernetes data into a Pod.
The configMap, downwardAPI, secret are provided as local ephemeral storage. They are managed by kubelet on each node.
● CSI ephemeral volumes
It provided by special CSI drivers.
CSI ephemeral volumes must be provided by third-party CSI storage drivers.
● generic ephemeral volumes
It can be provided by all storage drivers that also support persistent volumes.
Generic ephemeral volumes can be provided by third-party CSI storage drivers, but also by any other storage driver that supports dynamic provisioning.
Some CSI drivers are written specifically for CSI ephemeral volumes and do not support dynamic provisioning: those then cannot be used for generic ephemeral volumes.

[Storage Classes (SC)]
Storage Classes is automatically to manage the PersistentVolume (PV) also known as Dynamic Provisioning.
First create the StorageClass (SC) and then create PersistentVolumeClaim (PVC) that reference to StorageClass (SC), the Kubernetes use StorageClass (SC) provisioner to provision a PersistentVolume (PV) when the PersistentVolumeClaim (PVC) is referenced in a Pod volume and applied, so storage is provisioned the PersistentVolume (PV) is automatically created and get bound to PVC.
First the StorageClass is created, then the PersistentVolumeClaim and finally the Pod.
When a PVC is created, Kubernetes creates a PersistentVolume and binds it to the PVC automatically, depending on the VolumeBindingMode used in the StorageClass configuration.
It allows dynamic provisioning of Persistent Volumes, when PVC claims it.
StorageClass is used with PVC that allow Pods to dynamically request a new storage.
For each and every Storage Classes thier will be a Persistent Volume Claim (PVC).
StorageClass use provisioners that are specific to the storage platform or cloud provider to give Kubernetes access to the physical storage.
Each storage backend has own provisioner. Storage Backend is defined in the StorageClass component via provisioner attribute.
If using a provisioner, usually don't create the PV. Just create a PVC requiring that created StorageClass.
Components of Storage Classes in YAML file.
● provisioner
It is a type of volume plug-in that handles the creation and management of storage within Kubernetes.
Some provisioners are built in and shipped with Kubernetes and some are third-party provisioners, which is helpful when internal provisioners don’t support use case.
Third-party provisioners are not shipped with Kubernetes, but are developed and maintained by third-party vendors.
● volumeBindingMode
There are two volume binding modes that can be used:
* Immediate 
It is the default.
This mode involves the automatic volume binding of PV to PVC with a StorageClass once a PVC is created.
In this mode, the volume and storage binding are created immediately after the PVC is created.
So whenever a new PVC with the standard storage StorageClass is created, can see it in the bound state.
It indicates that volume binding and dynamic provisioning occurs once the PVC is created.
This mode is universally supported.
* WaitForFirstConsumer 
This mode will delay the binding and dynamic provisioning of PV, until a Pod that will use it is created.
In this mode, volume is not created until a pod that consumes the PVC is created.
Most plug-ins don’t support this mode, but only "Amazon Elastic Block Store", "Google Compute Engine Persistent Disk" and "Azure Disk" support it.
The binding will be delayed and provisioning of a PV will only happen when a Pod starts using the PVC.
● allowVolumeExpansion
It can expand the Persistent Volume if required.
In this field there will be two options.
* true 
The StorageClass will allow support for volume expansion.
When the request come from PVC with storage size change, then StorageClass will accept the request and it allow to expansion the volume.
* false 
The StorageClass will not allow support for volume expansion.
When the request come from PVC with storage size change, then StorageClass will not accept the request and it not allow to expansion the volume.
● type
There are several type of Volume types in each cloud platform.
* provisioner: kubernetes.io/aws-ebs
By default it is gp2.
But can choose other types in AWS EBS like General Purpose SSD (gp2 and gp3), Provisioned IOPS SSD (io1 and io2), Throughput Optimized HDD (st1), Cold HDD (sc1), Magnetic (standard).
* provisioner: kubernetes.io/gce-pd
By default it is pd-standard.
But can choose other types in GCE PD like pd-standard, pd-ssd.

[Persistent Volumes (PV)]
Persistent Volumes is also known as Static Provisioning.
First need to create a volume in external storage like AWS, Azure, GCP with required storage size (eg: 10GB) later then create a PersistentVolume (PV) in Kubernetes that links back to volume in external storage, so after that can claim created PersistentVolume (PV) using a request called PersistentVolumeClaim (PVC) from a Pod and application can use it. 
It is an abstraction for the physical storage device that attached to the cluster.
PV is not Namespaced it is available to whole cluster. PV is accessible to all Namespaces.
PV can be mounted into a pod through a PVC.
It no need to create StorageClass for PV.
● volumeMode
* Filesystem 
It is the default.
The volume mounted into Pod into a directory.
When the Persistent Volume (PV) is mounted in a container, it is mounted to a directory in the file tree of the container.
If the underlying storage is an unformatted block device, Kubernetes formats the device using the filesystem specified in the volume definition before it is mounted in the container.
* Block 
It is uses a volume as a raw block device.
The block device (/dev/xvdf, /dev/xvdf1, /dev/xvdf2) is empty and it create a filesystem on the device before mounting it for the first time.
When a pod uses a Persistent Volume with this mode, the volume is made available to the application in the container as a raw block device (without a filesystem).
This allows the application to read and write data without any filesystem overhead. This mode is typically used by special types of applications, such as database systems.

[Persistent Volume Claim (PVC)]
It is binding between a Pod and PV. Pod request the Volume through the PVC.
It is the request to provision persistent storage with a specific type and configuration.
Pods consume node resources and PVC consume PV resources.
PVC describe the storage capacity and characteristics a pod requires, and the cluster attempts to match the request and provision the desired persistent volume.
PVC must be in same namespace as the Pod. For each Pod, a PVC makes a storage consumption request within a namespace.

          PVC (request) ---> StorageClass (defines Type of Disk) ---> PV (Cloud Provider like AWS, GCP, Azure)

⦿ PVC to PV binding is a one-to-one mapping. The process uses a ClaimRef, which creates a bi-directional binding between PV and PVC.
   PV that meets the criteria defined in the PVC, it matches the claim to PV then it binds the PV to that PVC.

⦿ Persistent Volume (PV) is an abstraction for the physical storage device that have attached to the cluster.
   Pods can use this storage space using Persistent Volume Claim (PVC).
   To create the PV-PVC pair for Pod is to use a StorageClass (SC) object, and then using the StorageClass to create PV-PVC pair dynamically.

{Reclaim Policy (reclaimPolicy,persistentVolumeReclaimPolicy)}
It is the policy that describes how a storage class can reclaim a PV when it is no longer needed.
If no 'reclaimPolicy' is specified when a StorageClass object is created, it will default to 'Delete'.
PV that are created manually and managed via a StorageClass will have whatever reclaim policy they were assigned at creation.
PV that are dynamically created by a StorageClass will have the reclaim policy specified in the reclaimPolicy field of the class, which can be either Delete or Retain.
When the user no longer needs a volume, they can delete the PVC. The reclaim policy for a PersistentVolume tells the cluster what to do with the volume after it has been released of its claim.
Currently, volumes can either be Retained, Recycled, or Deleted.
● Delete
It will automatically delete the data immediately.
It deletion removes the PV from Kubernetes.
It removes the storage asset from the associated external infrastructure such as AWS EBS, GCE PD, Azure Disk.
● Retain
It is the default.
It will keep the data until the user deletes it.
It allows for manual reclamation of the resource.
PVC is deleted, the PV still exists, and the volume is considered “released”.
It is not yet available for another claim because the previous claimant’s data remains on the volume.
● Recycle
It deletes the volume’s contents and makes the volume available to be a fresh claimed again.
This policy option is now deprecated and should not be used as it may not be supported.

{Access Modes (accessModes)}
There are 4 types of Access Modes.
● ReadWriteOnce(RWO)
The volume can be mounted as read-write by a single node.
Only a single node can mount the volume for reading and writing.
This access mode still can allow multiple pods to access the volume when the pods are running on the same node.
The volume can be mounted by a single node in read and write mode. While it mounted to the node then other nodes can't mount the volume.
It read and write is allowed by only one pod at a time.
● ReadOnlyMany(ROX)
The volume can be mounted read-only by many nodes.
The volume can be mounted by multiple nodes for reading.
The volume can be mounted on multiple nodes in read mode.
The multiple pods can perform read operations from the volume.
● ReadWriteMany(RWX)
The volume can be mounted as read-write by many nodes.
Multiple nodes can mount the volume for reading and writing.
The volume can be mounted in read and write mode on multiple nodes at the same time.
The multiple pods can perform read and write operations from the volume.
● ReadWriteOncePod(RWOP)
The volume can be mounted as read-write by a single Pod.
This access mode if want to ensure that only one pod across whole cluster can read that PVC or write to it. 
This is only supported for CSI volumes and Kubernetes version 1.22+.

{fsType in Storage Classes (SC) and Persistent Volumes (PV)}
● ext4
It is the default.
● xfs

{mountOptions in Storage Classes (SC) and Persistent Volumes (PV)}
* hard
* debug
* nfsvers
It support for an NFS and need to specify the NFS version. 

[Phases/States]
● Available
A free resource that is not yet bound to a claim.
The PV is ready to be used by the PVC.
● Bound
The volume is bound to a claim.
PV has been bound to a claim.
The PV has been assigned to a PVC.
● Released
The claim has been deleted, but the resource is not yet reclaimed by the cluster.
PVC has been deleted, PV is pending reclamation.
The claim has been deleted but the cluster has not yet reclaimed the resource.
● Failed
The volume has failed its automatic reclamation.
An error has been encountered attempting to reclaim the PV.
It shows that an error has occured in the PV.

[Provisioning]
There are two ways to provision persistent storage volumes in Kubernetes.
● Static
PVs are created by Kubernetes cluster administrators and exist in the Kubernetes API.
PV is created in advance by the cluster administrator, the developer creates the PVC and the Pod, and the Pod uses the storage provided by the PV through the PVC.
The administrator has to make existing storage devices available to a cluster.
To make existing storage available to a cluster, the administrator has to manually create a persistent volume after that only user can claim the storage for the pod by creating PVCs.
● Dynamic
The static PVs created by the administrator can match the user’s PVC, the cluster will try to automatically provision a storage volume for the PVC, which is based on StorageClass.
The PVC needs to request a storage class, but this storage class must be pre-created and configured by the administrator.
The cluster administrator needs to enable the access controller for default StorageClass in the API Server.
It is based on Storage Classes (SC), the PVC must request a storage class and the administrator must have created and configured that storage class for dynamic provisioning to occur.
In order to demand storage, it must create a PVC by using an default StorageClass.

[LifeCycle of PV and PVC]
● Provisioning
PV
The creation of the PV, either directly Static OR Dynamically using StorageClass.
● Binding
PVC
It assigning the PV to the PVC.
The user creates a PVC (or has previously created one for dynamic provisioning), specifying the requested storage size and access mode.
The master has a control loop to monitor new PVCs, find matching PVs (if any), and bind the PVC and PV together.
If a PV is ever dynamically provisioned to a new PVC, the loop will always bind that PV to the PVC.
In addition, users will always get at least the storage they request, but the volume may exceed their request.
If no matching PV is found, the PVC will remain unbound indefinitely, and once the PV is available, then the PVC will become bound again.
For example, if a cluster is provisioned with many 50G PVs, it will not match the 100G PVCs requested, and the PVCs will not be bound until 100G PVs are added to the cluster.
● Using
Workloads like Pods, Deployments, ... etc.
Pods use the volume through the PVC.
The Pod uses PVC as a volume, and the Kubernetes cluster looks up the bound PV by the PVC and mounts it to the Pod.
The user can specify the access method when using PVC as a volume.
For volumes that support multiple access methods, the user specifies which mode is desired when using their claim as a volume in a Pod.
Once a user has a bound PVC, the bound PV belongs to that user.
The user can access the possessed PV through the PVC contained in the Pod’s storage volume.
● Reclaiming
Reclaim Policy (reclaimPolicy,persistentVolumeReclaimPolicy) = Retain, Delete, Recycle.
PV is reclaimed, either by keeping it for the next use OR by deleting it directly from the cloud storage.

[Syntax for YAML file]
● volumes:
Pod level config.
Volumes to be attached to the Pod.
Pod can support multiple types of Volumes.
● volumeMounts:
Container level config.
The location in the container file system where the volume is mounted to. 
Any OS allows mounting at any location of the container file system.
A volume has to be mounted to a container using volumeMount in order for the container to have access to the volume.
pod container can mount multiple volume types defined in the pod spec.
