Skip to content

Commit

Permalink
Support other filesystem types (#77)
Browse files Browse the repository at this point in the history
  • Loading branch information
jonasasx authored Jan 23, 2023
1 parent baf8fcb commit d71f63f
Show file tree
Hide file tree
Showing 7 changed files with 108 additions and 14 deletions.
2 changes: 1 addition & 1 deletion Dockerfile
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@ FROM alpine:3.16
LABEL maintainers="Metal Authors"
LABEL description="LVM Driver"

RUN apk add lvm2 lvm2-extra e2fsprogs e2fsprogs-extra smartmontools nvme-cli util-linux device-mapper
RUN apk add lvm2 lvm2-extra e2fsprogs e2fsprogs-extra smartmontools nvme-cli util-linux device-mapper xfsprogs xfsprogs-extra
COPY --from=builder /work/bin/lvmplugin /lvmplugin
USER root
ENTRYPOINT ["/lvmplugin"]
11 changes: 11 additions & 0 deletions examples/csi-pvc-xfs.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
apiVersion: v1
kind: PersistentVolumeClaim
metadata:
name: csi-pvc-xfs
spec:
accessModes:
- ReadWriteOnce
resources:
requests:
storage: 100Mi
storageClassName: csi-lvm-sc-linear-xfs
11 changes: 11 additions & 0 deletions examples/csi-storageclass-linear-xfs.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
apiVersion: storage.k8s.io/v1
kind: StorageClass
metadata:
name: csi-lvm-sc-linear-xfs
provisioner: lvm.csi.metal-stack.io
reclaimPolicy: Delete
volumeBindingMode: WaitForFirstConsumer
allowVolumeExpansion: true
parameters:
type: "linear"
fsType: xfs
49 changes: 37 additions & 12 deletions pkg/lvm/lvm.go
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@ import (
"os"
"os/exec"
"path/filepath"
"regexp"
"strconv"
"strings"
"time"
Expand Down Expand Up @@ -78,12 +79,17 @@ type volumeAction struct {
}

const (
linearType = "linear"
stripedType = "striped"
mirrorType = "mirror"
actionTypeCreate = "create"
actionTypeDelete = "delete"
pullIfNotPresent = "ifnotpresent"
linearType = "linear"
stripedType = "striped"
mirrorType = "mirror"
actionTypeCreate = "create"
actionTypeDelete = "delete"
pullIfNotPresent = "ifnotpresent"
fsTypeRegexpString = `TYPE="(\w+)"`
)

var (
fsTypeRegexp = regexp.MustCompile(fsTypeRegexpString)
)

// NewLvmDriver creates the driver
Expand Down Expand Up @@ -143,23 +149,42 @@ func (lvm *Lvm) Run() error {
return nil
}

func mountLV(lvname, mountPath string, vgName string) (string, error) {
func mountLV(lvname, mountPath string, vgName string, fsType string) (string, error) {
lvPath := fmt.Sprintf("/dev/%s/%s", vgName, lvname)

formatted := false
forceFormat := false
if fsType == "" {
fsType = "ext4"
}
// check for already formatted
cmd := exec.Command("blkid", lvPath)
out, err := cmd.CombinedOutput()
if err != nil {
klog.Infof("unable to check if %s is already formatted:%v", lvPath, err)
}
if strings.Contains(string(out), "ext4") {
formatted = true
matches := fsTypeRegexp.FindStringSubmatch(string(out))
if len(matches) > 1 {
if matches[1] == "xfs_external_log" { // If old xfs signature was found
forceFormat = true
} else {
if matches[1] != fsType {
return string(out), fmt.Errorf("target fsType is %s but %s found", fsType, matches[1])
}

formatted = true
}
}

if !formatted {
klog.Infof("formatting with mkfs.ext4 %s", lvPath)
cmd = exec.Command("mkfs.ext4", lvPath)
formatArgs := []string{}
if forceFormat {
formatArgs = append(formatArgs, "-f")
}
formatArgs = append(formatArgs, lvPath)

klog.Infof("formatting with mkfs.%s %s", fsType, strings.Join(formatArgs, " "))
cmd = exec.Command(fmt.Sprintf("mkfs.%s", fsType), formatArgs...) //nolint:gosec
out, err = cmd.CombinedOutput()
if err != nil {
return string(out), fmt.Errorf("unable to format lv:%s err:%w", lvname, err)
Expand All @@ -172,7 +197,7 @@ func mountLV(lvname, mountPath string, vgName string) (string, error) {
}

// --make-shared is required that this mount is visible outside this container.
mountArgs := []string{"--make-shared", "-t", "ext4", lvPath, mountPath}
mountArgs := []string{"--make-shared", "-t", fsType, lvPath, mountPath}
klog.Infof("mountlv command: mount %s", mountArgs)
cmd = exec.Command("mount", mountArgs...)
out, err = cmd.CombinedOutput()
Expand Down
2 changes: 1 addition & 1 deletion pkg/lvm/nodeserver.go
Original file line number Diff line number Diff line change
Expand Up @@ -143,7 +143,7 @@ func (ns *nodeServer) NodePublishVolume(ctx context.Context, req *csi.NodePublis

} else if req.GetVolumeCapability().GetMount() != nil {

output, err := mountLV(req.GetVolumeId(), targetPath, ns.vgName)
output, err := mountLV(req.GetVolumeId(), targetPath, ns.vgName, req.GetVolumeCapability().GetMount().GetFsType())
if err != nil {
return nil, fmt.Errorf("unable to mount lv: %w output:%s", err, output)
}
Expand Down
27 changes: 27 additions & 0 deletions tests/bats/test.bats
Original file line number Diff line number Diff line change
Expand Up @@ -108,6 +108,33 @@
[ "${lines[0]}" = "persistentvolumeclaim \"lvm-pvc-block\" deleted" ]
[ "${lines[1]}" = "persistentvolumeclaim \"lvm-pvc-linear\" deleted" ]
}

@test "deploy inline xfs pod with ephemeral volume" {
run sleep 10
run kubectl apply -f files/xfs.yaml
[ "$status" -eq 0 ]
[ "${lines[0]}" = "pod/volume-test-inline-xfs created" ]
}

@test "inline xfs pod running" {
run kubectl wait --for=condition=ready pod/volume-test-inline-xfs --timeout=180s
run kubectl get pods volume-test-inline-xfs -o jsonpath="{.metadata.name},{.status.phase}"
[ "$status" -eq 0 ]
[ "$output" = "volume-test-inline-xfs,Running" ]
}

@test "check fsType" {
run kubectl exec -it volume-test-inline-xfs -c inline -- sh -c "mount | grep /data"
[ "$status" -eq 0 ]
[[ "$output" == *"xfs"* ]]
}

@test "delete inline xfs linear pod" {
run kubectl delete -f files/xfs.yaml
[ "$status" -eq 0 ]
[ "${lines[0]}" = "pod \"volume-test-inline-xfs\" deleted" ]
}

@test "clean up " {
run sleep 60
run helm uninstall csi-driver-lvm
Expand Down
20 changes: 20 additions & 0 deletions tests/files/xfs.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
kind: Pod
apiVersion: v1
metadata:
name: volume-test-inline-xfs
spec:
containers:
- name: inline
image: nginx:stable-alpine
imagePullPolicy: IfNotPresent
volumeMounts:
- mountPath: "/data"
name: lvm-pvc-inline-xfs
volumes:
- name: lvm-pvc-inline-xfs
csi:
driver: lvm.csi.metal-stack.io
volumeAttributes:
size: "20MB"
type: "linear"
fsType: xfs

0 comments on commit d71f63f

Please sign in to comment.