mirror of
https://github.com/k3s-io/kubernetes.git
synced 2025-08-05 10:19:50 +00:00
refector iscsi volume to seperate builder and cleaner
This commit is contained in:
parent
788012ae7b
commit
ce52ae782d
@ -27,14 +27,14 @@ import (
|
|||||||
type diskManager interface {
|
type diskManager interface {
|
||||||
MakeGlobalPDName(disk iscsiDisk) string
|
MakeGlobalPDName(disk iscsiDisk) string
|
||||||
// Attaches the disk to the kubelet's host machine.
|
// Attaches the disk to the kubelet's host machine.
|
||||||
AttachDisk(disk iscsiDisk) error
|
AttachDisk(b iscsiDiskBuilder) error
|
||||||
// Detaches the disk from the kubelet's host machine.
|
// Detaches the disk from the kubelet's host machine.
|
||||||
DetachDisk(disk iscsiDisk, mntPath string) error
|
DetachDisk(disk iscsiDiskCleaner, mntPath string) error
|
||||||
}
|
}
|
||||||
|
|
||||||
// utility to mount a disk based filesystem
|
// utility to mount a disk based filesystem
|
||||||
func diskSetUp(manager diskManager, disk iscsiDisk, volPath string, mounter mount.Interface) error {
|
func diskSetUp(manager diskManager, b iscsiDiskBuilder, volPath string, mounter mount.Interface) error {
|
||||||
globalPDPath := manager.MakeGlobalPDName(disk)
|
globalPDPath := manager.MakeGlobalPDName(*b.iscsiDisk)
|
||||||
// TODO: handle failed mounts here.
|
// TODO: handle failed mounts here.
|
||||||
mountpoint, err := mounter.IsMountPoint(volPath)
|
mountpoint, err := mounter.IsMountPoint(volPath)
|
||||||
|
|
||||||
@ -45,7 +45,7 @@ func diskSetUp(manager diskManager, disk iscsiDisk, volPath string, mounter moun
|
|||||||
if mountpoint {
|
if mountpoint {
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
if err := manager.AttachDisk(disk); err != nil {
|
if err := manager.AttachDisk(b); err != nil {
|
||||||
glog.Errorf("failed to attach disk")
|
glog.Errorf("failed to attach disk")
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
@ -56,7 +56,7 @@ func diskSetUp(manager diskManager, disk iscsiDisk, volPath string, mounter moun
|
|||||||
}
|
}
|
||||||
// Perform a bind mount to the full path to allow duplicate mounts of the same disk.
|
// Perform a bind mount to the full path to allow duplicate mounts of the same disk.
|
||||||
options := []string{"bind"}
|
options := []string{"bind"}
|
||||||
if disk.readOnly {
|
if b.readOnly {
|
||||||
options = append(options, "ro")
|
options = append(options, "ro")
|
||||||
}
|
}
|
||||||
err = mounter.Mount(globalPDPath, volPath, "", options)
|
err = mounter.Mount(globalPDPath, volPath, "", options)
|
||||||
@ -68,7 +68,7 @@ func diskSetUp(manager diskManager, disk iscsiDisk, volPath string, mounter moun
|
|||||||
}
|
}
|
||||||
|
|
||||||
// utility to tear down a disk based filesystem
|
// utility to tear down a disk based filesystem
|
||||||
func diskTearDown(manager diskManager, disk iscsiDisk, volPath string, mounter mount.Interface) error {
|
func diskTearDown(manager diskManager, c iscsiDiskCleaner, volPath string, mounter mount.Interface) error {
|
||||||
mountpoint, err := mounter.IsMountPoint(volPath)
|
mountpoint, err := mounter.IsMountPoint(volPath)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
glog.Errorf("cannot validate mountpoint %s", volPath)
|
glog.Errorf("cannot validate mountpoint %s", volPath)
|
||||||
@ -91,7 +91,7 @@ func diskTearDown(manager diskManager, disk iscsiDisk, volPath string, mounter m
|
|||||||
// remaining reference is the global mount. It is safe to detach.
|
// remaining reference is the global mount. It is safe to detach.
|
||||||
if len(refs) == 1 {
|
if len(refs) == 1 {
|
||||||
mntPath := refs[0]
|
mntPath := refs[0]
|
||||||
if err := manager.DetachDisk(disk, mntPath); err != nil {
|
if err := manager.DetachDisk(c, mntPath); err != nil {
|
||||||
glog.Errorf("failed to detach disk from %s", mntPath)
|
glog.Errorf("failed to detach disk from %s", mntPath)
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
@ -89,17 +89,19 @@ func (plugin *iscsiPlugin) newBuilderInternal(spec *volume.Spec, podUID types.UI
|
|||||||
|
|
||||||
lun := strconv.Itoa(iscsi.Lun)
|
lun := strconv.Itoa(iscsi.Lun)
|
||||||
|
|
||||||
return &iscsiDisk{
|
return &iscsiDiskBuilder{
|
||||||
|
iscsiDisk: &iscsiDisk{
|
||||||
podUID: podUID,
|
podUID: podUID,
|
||||||
volName: spec.Name,
|
volName: spec.Name,
|
||||||
portal: iscsi.TargetPortal,
|
portal: iscsi.TargetPortal,
|
||||||
iqn: iscsi.IQN,
|
iqn: iscsi.IQN,
|
||||||
lun: lun,
|
lun: lun,
|
||||||
fsType: iscsi.FSType,
|
|
||||||
readOnly: iscsi.ReadOnly,
|
|
||||||
manager: manager,
|
manager: manager,
|
||||||
mounter: mounter,
|
mounter: mounter,
|
||||||
plugin: plugin,
|
plugin: plugin},
|
||||||
|
|
||||||
|
fsType: iscsi.FSType,
|
||||||
|
readOnly: iscsi.ReadOnly,
|
||||||
}, nil
|
}, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -109,13 +111,13 @@ func (plugin *iscsiPlugin) NewCleaner(volName string, podUID types.UID, mounter
|
|||||||
}
|
}
|
||||||
|
|
||||||
func (plugin *iscsiPlugin) newCleanerInternal(volName string, podUID types.UID, manager diskManager, mounter mount.Interface) (volume.Cleaner, error) {
|
func (plugin *iscsiPlugin) newCleanerInternal(volName string, podUID types.UID, manager diskManager, mounter mount.Interface) (volume.Cleaner, error) {
|
||||||
return &iscsiDisk{
|
return &iscsiDiskCleaner{&iscsiDisk{
|
||||||
podUID: podUID,
|
podUID: podUID,
|
||||||
volName: volName,
|
volName: volName,
|
||||||
manager: manager,
|
manager: manager,
|
||||||
mounter: mounter,
|
mounter: mounter,
|
||||||
plugin: plugin,
|
plugin: plugin,
|
||||||
}, nil
|
}}, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (plugin *iscsiPlugin) execCommand(command string, args []string) ([]byte, error) {
|
func (plugin *iscsiPlugin) execCommand(command string, args []string) ([]byte, error) {
|
||||||
@ -128,9 +130,7 @@ type iscsiDisk struct {
|
|||||||
podUID types.UID
|
podUID types.UID
|
||||||
portal string
|
portal string
|
||||||
iqn string
|
iqn string
|
||||||
readOnly bool
|
|
||||||
lun string
|
lun string
|
||||||
fsType string
|
|
||||||
plugin *iscsiPlugin
|
plugin *iscsiPlugin
|
||||||
mounter mount.Interface
|
mounter mount.Interface
|
||||||
// Utility interface that provides API calls to the provider to attach/detach disks.
|
// Utility interface that provides API calls to the provider to attach/detach disks.
|
||||||
@ -143,33 +143,47 @@ func (iscsi *iscsiDisk) GetPath() string {
|
|||||||
return iscsi.plugin.host.GetPodVolumeDir(iscsi.podUID, util.EscapeQualifiedNameForDisk(name), iscsi.volName)
|
return iscsi.plugin.host.GetPodVolumeDir(iscsi.podUID, util.EscapeQualifiedNameForDisk(name), iscsi.volName)
|
||||||
}
|
}
|
||||||
|
|
||||||
func (iscsi *iscsiDisk) SetUp() error {
|
type iscsiDiskBuilder struct {
|
||||||
return iscsi.SetUpAt(iscsi.GetPath())
|
*iscsiDisk
|
||||||
|
readOnly bool
|
||||||
|
fsType string
|
||||||
}
|
}
|
||||||
|
|
||||||
func (iscsi *iscsiDisk) SetUpAt(dir string) error {
|
var _ volume.Builder = &iscsiDiskBuilder{}
|
||||||
|
|
||||||
|
func (b *iscsiDiskBuilder) SetUp() error {
|
||||||
|
return b.SetUpAt(b.GetPath())
|
||||||
|
}
|
||||||
|
|
||||||
|
func (b *iscsiDiskBuilder) SetUpAt(dir string) error {
|
||||||
// diskSetUp checks mountpoints and prevent repeated calls
|
// diskSetUp checks mountpoints and prevent repeated calls
|
||||||
err := diskSetUp(iscsi.manager, *iscsi, dir, iscsi.mounter)
|
err := diskSetUp(b.manager, *b, dir, b.mounter)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
glog.Errorf("iscsi: failed to setup")
|
glog.Errorf("iscsi: failed to setup")
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
globalPDPath := iscsi.manager.MakeGlobalPDName(*iscsi)
|
globalPDPath := b.manager.MakeGlobalPDName(*b.iscsiDisk)
|
||||||
var options []string
|
var options []string
|
||||||
if iscsi.readOnly {
|
if b.readOnly {
|
||||||
options = []string{"remount", "ro"}
|
options = []string{"remount", "ro"}
|
||||||
} else {
|
} else {
|
||||||
options = []string{"remount", "rw"}
|
options = []string{"remount", "rw"}
|
||||||
}
|
}
|
||||||
return iscsi.mounter.Mount(globalPDPath, dir, "", options)
|
return b.mounter.Mount(globalPDPath, dir, "", options)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
type iscsiDiskCleaner struct {
|
||||||
|
*iscsiDisk
|
||||||
|
}
|
||||||
|
|
||||||
|
var _ volume.Cleaner = &iscsiDiskCleaner{}
|
||||||
|
|
||||||
// Unmounts the bind mount, and detaches the disk only if the disk
|
// Unmounts the bind mount, and detaches the disk only if the disk
|
||||||
// resource was the last reference to that disk on the kubelet.
|
// resource was the last reference to that disk on the kubelet.
|
||||||
func (iscsi *iscsiDisk) TearDown() error {
|
func (c *iscsiDiskCleaner) TearDown() error {
|
||||||
return iscsi.TearDownAt(iscsi.GetPath())
|
return c.TearDownAt(c.GetPath())
|
||||||
}
|
}
|
||||||
|
|
||||||
func (iscsi *iscsiDisk) TearDownAt(dir string) error {
|
func (c *iscsiDiskCleaner) TearDownAt(dir string) error {
|
||||||
return diskTearDown(iscsi.manager, *iscsi, dir, iscsi.mounter)
|
return diskTearDown(c.manager, *c, dir, c.mounter)
|
||||||
}
|
}
|
||||||
|
@ -72,22 +72,22 @@ type fakeDiskManager struct {
|
|||||||
func (fake *fakeDiskManager) MakeGlobalPDName(disk iscsiDisk) string {
|
func (fake *fakeDiskManager) MakeGlobalPDName(disk iscsiDisk) string {
|
||||||
return "/tmp/fake_iscsi_path"
|
return "/tmp/fake_iscsi_path"
|
||||||
}
|
}
|
||||||
func (fake *fakeDiskManager) AttachDisk(disk iscsiDisk) error {
|
func (fake *fakeDiskManager) AttachDisk(b iscsiDiskBuilder) error {
|
||||||
globalPath := disk.manager.MakeGlobalPDName(disk)
|
globalPath := b.manager.MakeGlobalPDName(*b.iscsiDisk)
|
||||||
err := os.MkdirAll(globalPath, 0750)
|
err := os.MkdirAll(globalPath, 0750)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
// Simulate the global mount so that the fakeMounter returns the
|
// Simulate the global mount so that the fakeMounter returns the
|
||||||
// expected number of mounts for the attached disk.
|
// expected number of mounts for the attached disk.
|
||||||
disk.mounter.Mount(globalPath, globalPath, disk.fsType, nil)
|
b.mounter.Mount(globalPath, globalPath, b.fsType, nil)
|
||||||
|
|
||||||
fake.attachCalled = true
|
fake.attachCalled = true
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (fake *fakeDiskManager) DetachDisk(disk iscsiDisk, mntPath string) error {
|
func (fake *fakeDiskManager) DetachDisk(c iscsiDiskCleaner, mntPath string) error {
|
||||||
globalPath := disk.manager.MakeGlobalPDName(disk)
|
globalPath := c.manager.MakeGlobalPDName(*c.iscsiDisk)
|
||||||
err := os.RemoveAll(globalPath)
|
err := os.RemoveAll(globalPath)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
|
@ -78,18 +78,18 @@ func (util *ISCSIUtil) MakeGlobalPDName(iscsi iscsiDisk) string {
|
|||||||
return makePDNameInternal(iscsi.plugin.host, iscsi.portal, iscsi.iqn, iscsi.lun)
|
return makePDNameInternal(iscsi.plugin.host, iscsi.portal, iscsi.iqn, iscsi.lun)
|
||||||
}
|
}
|
||||||
|
|
||||||
func (util *ISCSIUtil) AttachDisk(iscsi iscsiDisk) error {
|
func (util *ISCSIUtil) AttachDisk(b iscsiDiskBuilder) error {
|
||||||
devicePath := strings.Join([]string{"/dev/disk/by-path/ip", iscsi.portal, "iscsi", iscsi.iqn, "lun", iscsi.lun}, "-")
|
devicePath := strings.Join([]string{"/dev/disk/by-path/ip", b.portal, "iscsi", b.iqn, "lun", b.lun}, "-")
|
||||||
exist := waitForPathToExist(devicePath, 1)
|
exist := waitForPathToExist(devicePath, 1)
|
||||||
if exist == false {
|
if exist == false {
|
||||||
// discover iscsi target
|
// discover iscsi target
|
||||||
out, err := iscsi.plugin.execCommand("iscsiadm", []string{"-m", "discovery", "-t", "sendtargets", "-p", iscsi.portal})
|
out, err := b.plugin.execCommand("iscsiadm", []string{"-m", "discovery", "-t", "sendtargets", "-p", b.portal})
|
||||||
if err != nil {
|
if err != nil {
|
||||||
glog.Errorf("iscsi: failed to sendtargets to portal %s error: %s", iscsi.portal, string(out))
|
glog.Errorf("iscsi: failed to sendtargets to portal %s error: %s", b.portal, string(out))
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
// login to iscsi target
|
// login to iscsi target
|
||||||
out, err = iscsi.plugin.execCommand("iscsiadm", []string{"-m", "node", "-p", iscsi.portal, "-T", iscsi.iqn, "--login"})
|
out, err = b.plugin.execCommand("iscsiadm", []string{"-m", "node", "-p", b.portal, "-T", b.iqn, "--login"})
|
||||||
if err != nil {
|
if err != nil {
|
||||||
glog.Errorf("iscsi: failed to attach disk:Error: %s (%v)", string(out), err)
|
glog.Errorf("iscsi: failed to attach disk:Error: %s (%v)", string(out), err)
|
||||||
return err
|
return err
|
||||||
@ -100,8 +100,8 @@ func (util *ISCSIUtil) AttachDisk(iscsi iscsiDisk) error {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
// mount it
|
// mount it
|
||||||
globalPDPath := iscsi.manager.MakeGlobalPDName(iscsi)
|
globalPDPath := b.manager.MakeGlobalPDName(*b.iscsiDisk)
|
||||||
mountpoint, err := iscsi.mounter.IsMountPoint(globalPDPath)
|
mountpoint, err := b.mounter.IsMountPoint(globalPDPath)
|
||||||
if mountpoint {
|
if mountpoint {
|
||||||
glog.Infof("iscsi: %s already mounted", globalPDPath)
|
glog.Infof("iscsi: %s already mounted", globalPDPath)
|
||||||
return nil
|
return nil
|
||||||
@ -112,21 +112,21 @@ func (util *ISCSIUtil) AttachDisk(iscsi iscsiDisk) error {
|
|||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
err = iscsi.mounter.Mount(devicePath, globalPDPath, iscsi.fsType, nil)
|
err = b.mounter.Mount(devicePath, globalPDPath, b.fsType, nil)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
glog.Errorf("iscsi: failed to mount iscsi volume %s [%s] to %s, error %v", devicePath, iscsi.fsType, globalPDPath, err)
|
glog.Errorf("iscsi: failed to mount iscsi volume %s [%s] to %s, error %v", devicePath, b.fsType, globalPDPath, err)
|
||||||
}
|
}
|
||||||
|
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
func (util *ISCSIUtil) DetachDisk(iscsi iscsiDisk, mntPath string) error {
|
func (util *ISCSIUtil) DetachDisk(c iscsiDiskCleaner, mntPath string) error {
|
||||||
device, cnt, err := mount.GetDeviceNameFromMount(iscsi.mounter, mntPath)
|
device, cnt, err := mount.GetDeviceNameFromMount(c.mounter, mntPath)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
glog.Errorf("iscsi detach disk: failed to get device from mnt: %s\nError: %v", mntPath, err)
|
glog.Errorf("iscsi detach disk: failed to get device from mnt: %s\nError: %v", mntPath, err)
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
if err = iscsi.mounter.Unmount(mntPath); err != nil {
|
if err = c.mounter.Unmount(mntPath); err != nil {
|
||||||
glog.Errorf("iscsi detach disk: failed to unmount: %s\nError: %v", mntPath, err)
|
glog.Errorf("iscsi detach disk: failed to unmount: %s\nError: %v", mntPath, err)
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
@ -136,7 +136,7 @@ func (util *ISCSIUtil) DetachDisk(iscsi iscsiDisk, mntPath string) error {
|
|||||||
// strip -lun- from device path
|
// strip -lun- from device path
|
||||||
ind := strings.LastIndex(device, "-lun-")
|
ind := strings.LastIndex(device, "-lun-")
|
||||||
prefix := device[:(ind - 1)]
|
prefix := device[:(ind - 1)]
|
||||||
refCount, err := getDevicePrefixRefCount(iscsi.mounter, prefix)
|
refCount, err := getDevicePrefixRefCount(c.mounter, prefix)
|
||||||
|
|
||||||
if err == nil && refCount == 0 {
|
if err == nil && refCount == 0 {
|
||||||
// this portal/iqn are no longer referenced, log out
|
// this portal/iqn are no longer referenced, log out
|
||||||
@ -146,7 +146,7 @@ func (util *ISCSIUtil) DetachDisk(iscsi iscsiDisk, mntPath string) error {
|
|||||||
iqn := device[ind1+len("-iscsi-") : ind]
|
iqn := device[ind1+len("-iscsi-") : ind]
|
||||||
|
|
||||||
glog.Infof("iscsi: log out target %s iqn %s", portal, iqn)
|
glog.Infof("iscsi: log out target %s iqn %s", portal, iqn)
|
||||||
out, err := iscsi.plugin.execCommand("iscsiadm", []string{"-m", "node", "-p", portal, "-T", iqn, "--logout"})
|
out, err := c.plugin.execCommand("iscsiadm", []string{"-m", "node", "-p", portal, "-T", iqn, "--logout"})
|
||||||
if err != nil {
|
if err != nil {
|
||||||
glog.Errorf("iscsi: failed to detach disk Error: %s", string(out))
|
glog.Errorf("iscsi: failed to detach disk Error: %s", string(out))
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user