Skip to content

Commit

Permalink
Mount iRODS Clients on PublishVolume call
Browse files Browse the repository at this point in the history
  • Loading branch information
iychoi committed Oct 4, 2021
1 parent 14385e5 commit 5280941
Show file tree
Hide file tree
Showing 3 changed files with 98 additions and 36 deletions.
1 change: 1 addition & 0 deletions go.mod
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ require (
github.com/cyverse/go-irodsclient v0.5.5
github.com/golang/protobuf v1.4.2 // indirect
github.com/kr/pretty v0.2.0 // indirect
github.com/rs/xid v1.3.0
golang.org/x/net v0.0.0-20200707034311-ab3426394381 // indirect
golang.org/x/text v0.3.3 // indirect
google.golang.org/grpc v1.27.0
Expand Down
33 changes: 15 additions & 18 deletions pkg/driver/controller.go
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,7 @@ import (
"strings"

"github.com/container-storage-interface/spec/lib/go/csi"
"github.com/rs/xid"
"google.golang.org/grpc/codes"
"google.golang.org/grpc/status"
"k8s.io/klog"
Expand All @@ -53,7 +54,7 @@ func (driver *Driver) CreateVolume(ctx context.Context, req *csi.CreateVolumeReq
if len(volName) == 0 {
return nil, status.Error(codes.InvalidArgument, "Volume name not provided")
}
volID := generateVolumeID(volName)
volID := driver.generateVolumeID(volName)

klog.V(4).Infof("CreateVolume: volumeName(%#v)", volName)

Expand Down Expand Up @@ -102,20 +103,17 @@ func (driver *Driver) CreateVolume(ctx context.Context, req *csi.CreateVolumeReq
}

if enforceProxyAccess {
if proxyUser == irodsConn.User {
// same proxy user
// enforce clientUser
if len(irodsConn.ClientUser) == 0 {
return nil, status.Error(codes.InvalidArgument, "Argument clientUser must be given")
}
if proxyUser != irodsConn.User {
// different proxy user
return nil, status.Error(codes.InvalidArgument, "cannot use change proxy user account from pre-configued one")
}

if irodsConn.User == irodsConn.ClientUser {
return nil, status.Errorf(codes.InvalidArgument, "Argument clientUser cannot be the same as user - user %s, clientUser %s", irodsConn.User, irodsConn.ClientUser)
}
} else {
// replaced user
// static volume provisioning takes user argument from pv
// this is okay
if len(irodsConn.ClientUser) == 0 {
return nil, status.Error(codes.InvalidArgument, "Argument clientUser must be given")
}

if irodsConn.User == irodsConn.ClientUser {
return nil, status.Errorf(codes.InvalidArgument, "Argument clientUser cannot be the same as user - user %s, clientUser %s", irodsConn.User, irodsConn.ClientUser)
}
}

Expand Down Expand Up @@ -213,6 +211,7 @@ func (driver *Driver) CreateVolume(ctx context.Context, req *csi.CreateVolumeReq
}

volContext["path"] = volPath
volContext["provisioning_mode"] = "dynamic"

// create a irods volume and put it to manager
irodsVolume := NewIRODSVolume(volID, volName, volRootPath, volPath, irodsConn, volRetain)
Expand Down Expand Up @@ -347,8 +346,6 @@ func (driver *Driver) ControllerExpandVolume(ctx context.Context, req *csi.Contr
}

// generateVolumeID generates volume id from volume name
func generateVolumeID(volName string) string {
//uuid := uuid.New()
//return fmt.Sprintf("volid-%s", uuid.String())
return volName
func (driver *Driver) generateVolumeID(volName string) string {
return fmt.Sprintf("volid-%s-%s", volName, xid.New().String())
}
100 changes: 82 additions & 18 deletions pkg/driver/node.go
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,7 @@ import (
"fmt"
"net/url"
"os"
"strings"

"github.com/container-storage-interface/spec/lib/go/csi"
"google.golang.org/grpc/codes"
Expand All @@ -42,10 +43,6 @@ var (
nodeCaps = []csi.NodeServiceCapability_RPC_Type{csi.NodeServiceCapability_RPC_STAGE_UNSTAGE_VOLUME}
)

const (
sensitiveArgsRemoved = "<masked>"
)

// NodeStageVolume handles persistent volume stage event in node service
func (driver *Driver) NodeStageVolume(ctx context.Context, req *csi.NodeStageVolumeRequest) (*csi.NodeStageVolumeResponse, error) {
volID := req.GetVolumeId()
Expand All @@ -55,6 +52,12 @@ func (driver *Driver) NodeStageVolume(ctx context.Context, req *csi.NodeStageVol

klog.V(4).Infof("NodeStageVolume: volumeId (%#v)", volID)

if !driver.isDynamicVolumeProvisioningMode(req.VolumeContext) {
// static volume provisioning
return &csi.NodeStageVolumeResponse{}, nil
}

// only for dynamic volume provisioning mode
targetPath := req.GetStagingTargetPath()
if len(targetPath) == 0 {
return nil, status.Error(codes.InvalidArgument, "Staging target path not provided")
Expand Down Expand Up @@ -86,6 +89,18 @@ func (driver *Driver) NodeStageVolume(ctx context.Context, req *csi.NodeStageVol
}
}

pathExist, pathExistErr := PathExists(targetPath)
if pathExistErr != nil {
return nil, status.Error(codes.Internal, pathExistErr.Error())
}

if !pathExist {
klog.V(5).Infof("NodeStageVolume: creating dir %s", targetPath)
if err := MakeDir(targetPath); err != nil {
return nil, status.Errorf(codes.Internal, "Could not create dir %q: %v", targetPath, err)
}
}

notMountPoint, err := driver.mounter.IsLikelyNotMountPoint(targetPath)
if err != nil {
return nil, status.Error(codes.Internal, err.Error())
Expand Down Expand Up @@ -138,8 +153,6 @@ func (driver *Driver) NodeStageVolume(ctx context.Context, req *csi.NodeStageVol

// NodePublishVolume handles persistent volume publish event in node service
func (driver *Driver) NodePublishVolume(ctx context.Context, req *csi.NodePublishVolumeRequest) (*csi.NodePublishVolumeResponse, error) {
//klog.V(4).Infof("NodePublishVolume: called with args %+v", req)

volID := req.GetVolumeId()
if len(volID) == 0 {
return nil, status.Error(codes.InvalidArgument, "Volume ID not provided")
Expand Down Expand Up @@ -203,27 +216,66 @@ func (driver *Driver) NodePublishVolume(ctx context.Context, req *csi.NodePublis
return nil, status.Errorf(codes.Internal, "Staging target path %s is already mounted", targetPath)
}

// bind mount
stagingTargetPath := req.GetStagingTargetPath()
if len(stagingTargetPath) == 0 {
return nil, status.Error(codes.InvalidArgument, "Staging target path not provided")
}
if driver.isDynamicVolumeProvisioningMode(req.VolumeContext) {
// dynamic volume provisioning
// bind mount
stagingTargetPath := req.GetStagingTargetPath()
if len(stagingTargetPath) == 0 {
return nil, status.Error(codes.InvalidArgument, "Staging target path not provided")
}

klog.V(5).Infof("NodePublishVolume: mounting %s", "bind")
if err := driver.mountBind(stagingTargetPath, mountOptions, targetPath); err != nil {
os.Remove(targetPath)
return nil, err
klog.V(5).Infof("NodePublishVolume: mounting %s", "bind")
if err := driver.mountBind(stagingTargetPath, mountOptions, targetPath); err != nil {
os.Remove(targetPath)
return nil, err
}
} else {
// static volume provisioning
// mount volume
volContext := req.GetVolumeContext()
volSecrets := req.GetSecrets()

secrets := make(map[string]string)
for k, v := range driver.secrets {
secrets[k] = v
}

for k, v := range volSecrets {
secrets[k] = v
}

irodsClient := ExtractIRODSClientType(volContext, secrets, FuseType)

switch irodsClient {
case FuseType:
klog.V(5).Infof("NodePublishVolume: mounting %s", irodsClient)
if err := driver.mountFuse(volContext, secrets, mountOptions, targetPath); err != nil {
os.Remove(targetPath)
return nil, err
}
case WebdavType:
klog.V(5).Infof("NodePublishVolume: mounting %s", irodsClient)
if err := driver.mountWebdav(volContext, secrets, mountOptions, targetPath); err != nil {
os.Remove(targetPath)
return nil, err
}
case NfsType:
klog.V(5).Infof("NodePublishVolume: mounting %s", irodsClient)
if err := driver.mountNfs(volContext, secrets, mountOptions, targetPath); err != nil {
os.Remove(targetPath)
return nil, err
}
default:
return nil, status.Errorf(codes.Internal, "unknown driver type - %v", irodsClient)
}
}

klog.V(5).Infof("NodePublishVolume: %s was mounted", targetPath)

return &csi.NodePublishVolumeResponse{}, nil
}

// NodeUnpublishVolume handles persistent volume unpublish event in node service
func (driver *Driver) NodeUnpublishVolume(ctx context.Context, req *csi.NodeUnpublishVolumeRequest) (*csi.NodeUnpublishVolumeResponse, error) {
//klog.V(4).Infof("NodeUnpublishVolume: called with args %+v", req)

volID := req.GetVolumeId()
if len(volID) == 0 {
return nil, status.Error(codes.InvalidArgument, "Volume ID not provided")
Expand Down Expand Up @@ -522,3 +574,15 @@ func (driver *Driver) mountNfs(volContext map[string]string, volSecrets map[stri

return nil
}

func (driver *Driver) isDynamicVolumeProvisioningMode(volContext map[string]string) bool {
for k, v := range volContext {
if strings.ToLower(k) == "provisioning_mode" {
if strings.ToLower(v) == "dynamic" {
return true
}
}
}

return false
}

0 comments on commit 5280941

Please sign in to comment.