26.3
Simplyblock is happy to release Simplyblock 26.3. The changes are grouped by the component they belong to: the simplyblock control plane and storage plane, and the Kubernetes components, meaning the Simplyblock Operator and Simplyblock CSI.
Simplyblock
The control plane and the storage plane are released together and share a version number. The changes below apply to every deployment, including a Kubernetes-based one.
New Features
- Control Plane: Added asynchronous replication between two storage clusters. Several destinations per cluster are supported, the cadence and the retention are set per replication policy, and a failover is requested for a single volume, a whole policy, or a whole destination.
- Control Plane: Added the planned cross-cluster cutover, by which a volume is handed over to another cluster under control. The remaining delta is shrunk, the source is fenced, and the client is moved to the target. The return to a recovered source runs as a delta, and the return to a fresh cluster as a full copy.
- Control Plane: Added support for failure domains. Data chunks, parity chunks, journal copies, and the secondary and tertiary nodes are spread across distinct domains, with a host-disjoint fallback and a warning where that is not possible.
- Control Plane: Added online storage node removal, which runs as a resumable background task and re-hosts the replicas and devices the node holds, and the expansion of an FTT 2 cluster by a single node. Several nodes are now added in parallel.
- Control Plane: Added cluster-wide maintenance operations. Every node of a cluster is restarted in one step, and the creation, deletion, and modification of volumes, snapshots, clones, and pools is refused and resumed for the whole cluster. Read paths and the restarts, migrations, and repairs a cluster performs on itself are unaffected.
- Control Plane: Added release-specific upgrade plug-ins, which run their preparation step before a cluster update and their completion step after it, and record the installed release on the cluster.
- Control Plane: Added batch migration of namespaced volumes, by which every volume that shares an NVMe-oF subsystem is moved as one coordinated group. What a failed migration left behind on the target is removed idempotently.
- Control Plane: Added quorum-based device exclusion. A device that draws I/O errors from a quorum of the other online nodes is excluded cluster-wide, independent of what its NVMe controller reports, which is the case a slow-but-connected device previously slipped through. A device whose latency deviates from the cluster average is reported as a warning event before it fails.
- Control Plane: Added alerting from the cluster event log, which provisions Grafana rules that read the transition an entity made rather than the state it ended in. Journal events are now collected into the event log next to the distrib events.
- Control Plane: Added a FoundationDB exporter with its own dashboard, request metrics of the management API, the device health information the storage plane holds, and a retention period of 30 days for cluster tasks and their logs.
- Control Plane: Added a rebalance operation to the cluster API, validation of the erasure coding scheme by the management API, and independent NVMe device filters for a storage node, where the device model and the size range are accepted alone as well as together.
- Storage Plane: The journal device of a node is now a RAID 0+1 stack instead of an N-way mirror across the journal partition of every drive. Write amplification is capped at two physical writes per journal record and per node, independent of the drive count, and a drive lifecycle event rebuilds the affected leg instead of the whole mirror.
- Storage Plane: Added a second generation of distrib write protection. A new cluster is created on it, and an upgraded cluster is moved over once every online node has migrated. An offline node is brought over by its next restart.
- Storage Plane: The ANA state change of a volume is now scoped to its namespace instead of the whole subsystem. A volume that shares its subsystem with other volumes is failed over, suspended, and migrated without moving their I/O to the other node.
- Storage Plane: The core allocation of a storage node gives the distrib and poller threads their share before alceml, which takes its device-scaled count from what is left. Explicit layouts are added for hosts with two to five vCPUs.
- General: Added diagnostics for a latency or crash investigation: the bdev latency histograms with a per-layer
probe, by which a tail-latency spike is localized to a layer of the bdev stack, and the host directory
/var/crashmounted into the storage plane container, so that a core dump survives the container. - General: Updated the packages inherited from the container base images and dropped
wgetfrom the image, to resolve open CVEs.
Fixes
- Control Plane: Fixed the loss of I/O during a storage node restart, where an unbounded operation inside the port fence could outlast the client keep-alive.
- Control Plane: Improved the recovery of a cluster after a full reboot. An activation that wedged is detected by a watchdog, automatic reactivation is gated on every node being online, and a suspended cluster is drained to all-offline before it is restarted.
- Control Plane: Fixed storage nodes flapping to the down state on a health probe timeout, and a node that is down no longer counts toward the suspension of the cluster. The suspension is gated on an actual loss of the data plane rather than on an unreachable management network.
- Control Plane: Fixed three ways in which a highly available volume could silently lose one of its paths, and the duplicate paths a repair left behind are now pruned. No leadership over an lvstore is granted while a restart or a recovery task owns the movement of it.
- Control Plane: Fixed the failover of a namespaced volume, which the kernel rejected with mismatching identifiers.
- Control Plane: Fixed the deletion pipeline of volumes and snapshots. A delete the cluster cannot complete is refused rather than accepted, a deferred delete completes once the node it waited for returns, and concurrent operations on one snapshot chain are mutually exclusive, which closes a corruption of the blob tree.
- Control Plane: Fixed the migration of a volume whose snapshot chain spans several nodes, of an encrypted volume, and of a volume with a tertiary node. A migration whose source node goes offline is suspended instead of being cleaned up on the target.
- Control Plane: Fixed the replication of the blob chain of a volume, which replicated only the snapshots of the volume itself. A failover only ever targets a fully replicated and live snapshot, and a replication no longer halts silently under back-pressure.
- Control Plane: Fixed the addition of a storage node, which aborted on a lock timeout, on a stale in-creation record, or on an already provisioned device slot, and which did not survive the CPU topology reboot. A re-entry is idempotent now, and the status of a node, a device, a cluster, and a volume is written through a compare-and-set operation, so that a crashed writer cannot leave a stale status behind.
- Control Plane: Fixed the capacity reporting, which mixed raw with effective capacity, and the cluster admission check, which did not count the utilization of snapshots. On a storage pool, the capacity check of a resize no longer counts the volume being resized twice.
- Control Plane: Fixed the cloning of an encrypted volume, for which the crypto layer was missing from the recorded bdev stack, the key management of the local KMS, and the rendering of secrets in the management API.
- Control Plane: Fixed a forced storage node shutdown that could block indefinitely, a cluster that grew by being reactivated, a cluster expansion that did not reattach the sibling failover of its donor node, and the leases of long-running tasks, which expired while the task was still running.
- Control Plane: Improved the throughput of the snapshot and volume monitors, which process chains and nodes in parallel, and the logging to Graylog, which is written non-blocking, so that a slow log target no longer holds up the control plane.
- Storage Plane: Improved the reliability of the graceful startup and the graceful shutdown of the storage plane. A storage plane whose RPC endpoint hangs on a live process is aborted instead of being waited for, and the wait for the journal replication of a peer is bounded, so that it cannot defer a restart indefinitely.
- Storage Plane: Fixed the roles of the hub volumes, which are active on both sides within a node and passive between nodes, and the hub volume subsystem, which was lost across a restart.
- Storage Plane: Fixed the re-admission of the devices of a node recovering from an outage, which was silently refused while the node had not yet reached the online state. The memory footprint of a node improved as well, since the small I/O buffers are sized from the subsystem count of the cluster.
Kubernetes
The changes below apply to Kubernetes-based deployments only. They are delivered by the Simplyblock Operator and by Simplyblock CSI.
New Features
- Operator: Added support for failure domains, by which erasure coding chunks and failover paths are spread
across racks or availability zones. Workers are assigned to a domain through the
StorageNodeSet, and the effective domain of a worker is reflected in the status of theStorageNode. - Operator: Added support for several
StorageNodeSetresources per storage cluster, by which workers with different hardware or a different role are enrolled with their own configuration, and for the parallel addition of storage nodes. - Operator: Added live volume migration through the new
VolumeMigrationresource, by which the backing logical volume is moved between storage nodes while the volume stays online. The new NVMe-oF paths on the target node are validated on every consuming worker before the migration is continued. - Operator: Added the storage node drain, removal, and host migration workflows, requested with a
StorageNodeOpsresource. A removal suspends the node, migrates its volumes to the remaining nodes, verifies the result, and removes the node, and a migration relocates the identity of a storage node to a different worker. - Operator: Added support for asynchronous replication between two storage clusters, declared with the new
ReplicationPair,ReplicationPolicy, andReplicationSlotresources. Failover and failback are requested with aReplicationOpsresource, scoped to a replication target, a policy, or a single volume, and a PVC is enrolled into a policy through an annotation. - Operator: Added automatic, latency-based volume rebalancing and back storage data realignment, which are configured per cluster and triggered independently of each other.
- Operator: Added support for topology-aware provisioning across several storage clusters, by which a volume is provisioned in the cluster that matches the topology of the consuming workload, the option to skip the creation of the FoundationDB cluster, and the adoption of an existing Helm-deployed storage cluster, storage pool, and storage nodes into the operator resources.
- Operator: Added configuration of the image pull policy, the resource limits, and the SPDK system memory of
the storage node workloads, and of a custom OpenShift
MachineConfigPool, so that storage nodes are rebooted through a pool that is separate from the remaining workers. Every image reference is validated against the trusted registries, and a field that cannot be changed after creation is rejected instead of being ignored silently. - Operator: The Thanos data of the monitoring stack is now stored in MinIO instead of a filesystem-backed object store, and Prometheus can be deployed with more than one replica.
- CSI Driver: Added support for co-locating the primary storage node of a volume with the worker that runs the consuming pod, and for the migration of namespaced volumes together with the coordinated restart of all pods that share an NVMe subsystem.
- CSI Driver: Added the detection and the repair of stale NVMe-oF subsystems and controllers on a worker.
- CSI Driver: The presence of a device is registered when the volume is connected, instead of only by polling, and the host NQN and the DH-CHAP secrets are forwarded at that point.
Fixes
- Operator: Fixed the release of the NVMe target paths of a migration that never reaches its cutover, and the rebuild of the storage node configuration after an operator restart with an in-flight storage node migration.
- Operator: Fixed the
StoragePoolresource remaining inTerminatingwhen its backend UUID was never set, and the PVC validator, which did not accept all of the volume placement annotations. - CSI Driver: Fixed incompatibilities when formatting and mounting ext4 and XFS volumes, and the connection of a volume in a cluster with more than one storage pool.
- CSI Driver: Fixed the loss of the kernel module configuration on the host, which was written into the ephemeral filesystem of the storage node container and was gone after the CPU topology reboot during a node addition.
- CSI Driver: Fixed the restart loop of the CSI controller container, caused by dangling snapshots and volumes of a removed cluster. A gRPC keepalive and a connection timeout now detect a broken connection to a control plane instead of blocking a request.
- Operator and CSI Driver: Updated the container base images and the Go dependencies to resolve open CVEs.
Important Changes
- The storage plane sizing of a node moves to the cluster. The flags
--max-subsys,--hugepages-mem, and--vcpu-countare set onsbctl cluster createandsbctl cluster add, and a node adopts them when it is added and on every restart.--max-subsys,--max-size, and--cores-percentageare removed fromsbctl storage-node configure, and--max-subsysand--max-sizefromsbctl storage-node restart. The flag--max-lvolis renamed to--max-subsys, which is what it has always limited. - The core budget of the storage plane is an absolute vCPU count instead of a percentage. A node that cannot satisfy
the count of its cluster, plus one core for the system, is refused instead of running on fewer cores than
requested.
sbctl cluster update --vcpu-countdoes not exist, because rewriting the core mask of every node belongs to a deliberate redeployment. - A configured subsystem limit above 75 per storage node is rejected, where it was accepted and then clamped silently before, so a node reserved huge pages for subsystems it could never serve. An lvstore serves at most 6000 objects, counting volumes, clones, and snapshots, and a create beyond that limit is refused.
- Failure domains are a deploy-time feature. A cluster cannot be upgraded into them, and
--enable-failure-domainhas to be set at creation time. Once it is set,--failure-domainis mandatory on everysbctl storage-node add-nodeand rejected on a cluster without the feature. sbctl storage-node removeno longer migrates the data of the node. The node has to host no volumes and no snapshots, and those are migrated beforehand. The flag--force-removeno longer removes volumes and snapshots, it cancels the active tasks of the node before the removal starts.- The commands
sbctl storage-node resume,sbctl storage-node get-bdevs, andsbctl storage-node unloadare removed. Instead ofresume,sbctl storage-node restarthas to be used. - The command
sbctl cluster add-replicationis deprecated. Instead, the commandssbctl cluster replication-target-addandsbctl cluster replication-policy-addhave to be used, which support more than one destination per cluster. sbctl volume migrateonly pre-creates the target subsystem and returns the migration id and the NVMe connect strings. The flags--deadlineand--max-retriesmove tosbctl volume migrate-continue, which advances the migration once the client is connected.- After
sbctl cluster update, two commands have to be run.sbctl cluster upgrade-completereleases the journal compression hold the update took across its rolling restart and records the installed release, andsbctl cluster switch-write-protectionmoves the cluster to the second generation of distrib write protection, on which it does not land by itself. - The flag
--allis removed fromsbctl snapshot list, which gained--lvol-id,--node-id, and--json. The flag--cluster-idis removed fromsbctl backup restore, whose cluster is derived from the backup. - The
Poolresource is renamed toStoragePool, and the resource enrolling a group of workers is renamed fromStorageNodetoStorageNodeSet. The nameStorageNodeis now used for the per-worker resource that is created by the operator. - The field
maxLogicalVolumeCountis renamed tomaxSubsystemCount, and the fieldcorePercentageis removed. Storage node sizing is moved from theStorageNodeSetto the cluster scope, and the fieldpartitionsis replaced byenableJournalDevice. - The deprecated
StorageClusterfieldsblockSize,qpairCount,pageSizeInBlocks,maxQueueSize,inflightIOThreshold,strictNodeAntiAffinity,haType,isSingleNode, andclientQpairCountare removed. - The
StorageClusterspec fieldmaxFaultToleranceis replaced bymaxConcurrentWorkerRestarts, which is capped at the fault tolerance of the cluster. The backend-reportedmaxFaultToleranceremains part of the status. - The field
unpinBeforeDrainis removed. A pinned volume has to be unpinned manually before its storage node is drained. - The volume placement annotations are unified into
simplyblock.io/selected-storage-node. On a new PVC, a host id supplied throughsimplyblock.io/host-idorsimplybk/host-idis rewritten into that annotation and treated as a pin. On a pre-existing PVC, both legacy annotations are still honored as the lowest-priority source of the primary storage node.
Upgrade Considerations
- The CSI driver added an extended check to prevent an accidental filesystem format onto an existing pre-formatted volume in one of the upstream CSI libraries. To ensure all existing volumes work as expected, users are highly encouraged to run this script after upgrading to 26.3.0. Annotate existing PVCs Script ⧉
- An upgrade from the previous R25 Helm chart to the R26 Operator installation requires a maintenance window and additional steps. See the Upgrade Procedure R25 to R26 for details.
Known Issues
- At the moment it is only possible to define one erasure coding schema per cluster.
-
When deleting pods with simplyblock-backed PVCs, it is important to delete the pod first, before deleting the PVC.
Deleting a pod before its persistent volume claimkubectl delete pod <pod-name> --wait=true kubectl delete pvc <pvc-name> --wait=true -
A full FTT 1 or FTT 2 network outage can create a situation where surviving nodes lose access to the last journal records. This can cause loss of I/O availability until at least one node is restarted.
- Node Removal currently only works with online nodes.
Features to Expect with Next Major Release
- The ability to use different erasure coding schemas within the same cluster.
- Inline data integrity validation to prevent silent data corruption.