From da0ed14a5cc5a1b21db67aea79b59488fae5bd0d Mon Sep 17 00:00:00 2001 From: Sameer Shaikh <79081767+sameshai@users.noreply.github.com> Date: Thu, 30 Jan 2025 11:09:23 +0530 Subject: [PATCH] Support for update Volume tags via RIAAS (#211) * Support for update Volume tags via RIAAS * Support for update Volume tags via RIAAS * Support for update Volume tags via RIAAS * Support for update Volume tags via RIAAS * Support for update Volume tags via RIAAS * Support for update Volume tags via RIAAS * Support for update Volume tags via RIAAS * Support for update Volume tags via RIAAS * Support for update Volume tags via RIAAS * Support for update Volume tags via RIAAS * Support for update Volume tags via RIAAS * Support for update Volume tags via RIAAS * Support for update Volume tags via RIAAS * Support for update Volume tags via RIAAS * Support for update Volume tags via RIAAS * Support for update Volume tags via RIAAS * Support for update Volume tags via RIAAS * Support for update Volume tags via RIAAS * Support for update Volume tags via RIAAS * Support for update Volume tags via RIAAS * Support for update Volume tags via RIAAS * Support for update Volume tags via RIAAS * Support for update Volume tags via RIAAS * Support for update Volume tags via RIAAS * Support for update Volume tags via RIAAS --- cmd/main.go | 2 +- go.mod | 4 +- go.sum | 8 +- pkg/ibmcsidriver/controller.go | 2 +- pkg/ibmcsidriver/controller_helper_test.go | 32 ++--- pkg/ibmcsidriver/controller_test.go | 2 +- pkg/ibmcsidriver/fileOps_test.go | 2 +- pkg/ibmcsidriver/ibm_csi_driver.go | 2 +- pkg/ibmcsidriver/ibm_csi_driver_test.go | 2 +- pkg/ibmcsidriver/node_helper_test.go | 2 +- pkg/ibmcsidriver/server_test.go | 2 +- tests/sanity/sanity_test.go | 2 +- .../lib/provider/vpc_data_types.go | 3 +- .../block/provider/update_volume.go | 73 +++++++++- .../block/provider/util.go | 39 ++++++ .../common/vpcclient/client/request.go | 6 + .../common/vpcclient/vpcvolume/get_volume.go | 1 + .../vpcclient/vpcvolume/get_volume_etag.go | 56 ++++++++ .../vpcclient/vpcvolume/update_volume.go | 2 +- .../vpcvolume/update_volume_with_etag.go | 56 ++++++++ .../vpcclient/vpcvolume/volume_service.go | 9 ++ .../iks/provider/session.go | 18 +-- .../iks/provider/update_volume.go | 2 +- .../ibmcloudprovider/fake_volume_provider.go | 34 ++--- .../ibmcloudprovider/ibm_volume_provider.go | 2 +- .../pkg/ibmcloudprovider/volume_provider.go | 3 +- .../pkg/watcher/pv_watcher.go | 128 +++++++++++++++--- vendor/modules.txt | 7 +- 28 files changed, 411 insertions(+), 90 deletions(-) create mode 100644 vendor/github.com/IBM/ibmcloud-volume-vpc/common/vpcclient/vpcvolume/get_volume_etag.go create mode 100644 vendor/github.com/IBM/ibmcloud-volume-vpc/common/vpcclient/vpcvolume/update_volume_with_etag.go rename vendor/github.com/IBM/{ibm-csi-common => ibmcloud-volume-vpc}/pkg/ibmcloudprovider/fake_volume_provider.go (96%) rename vendor/github.com/IBM/{ibm-csi-common => ibmcloud-volume-vpc}/pkg/ibmcloudprovider/ibm_volume_provider.go (97%) rename vendor/github.com/IBM/{ibm-csi-common => ibmcloud-volume-vpc}/pkg/watcher/pv_watcher.go (63%) diff --git a/cmd/main.go b/cmd/main.go index 28920718..8d9ce6dc 100644 --- a/cmd/main.go +++ b/cmd/main.go @@ -35,7 +35,7 @@ import ( "github.com/IBM/ibm-csi-common/pkg/metrics" mountManager "github.com/IBM/ibm-csi-common/pkg/mountmanager" "github.com/IBM/ibm-csi-common/pkg/utils" - "github.com/IBM/ibm-csi-common/pkg/watcher" + "github.com/IBM/ibmcloud-volume-vpc/pkg/watcher" csiConfig "github.com/kubernetes-sigs/ibm-vpc-block-csi-driver/config" driver "github.com/kubernetes-sigs/ibm-vpc-block-csi-driver/pkg/ibmcsidriver" "go.uber.org/zap" diff --git a/go.mod b/go.mod index 8722f6c7..c0b8050f 100644 --- a/go.mod +++ b/go.mod @@ -4,8 +4,8 @@ go 1.22.0 require ( github.com/IBM/ibm-csi-common v1.1.18 - github.com/IBM/ibmcloud-volume-interface v1.2.6 - github.com/IBM/ibmcloud-volume-vpc v1.1.12 + github.com/IBM/ibmcloud-volume-interface v1.2.9 + github.com/IBM/ibmcloud-volume-vpc v1.1.14 github.com/IBM/secret-utils-lib v1.1.11 github.com/container-storage-interface/spec v1.9.0 github.com/golang/glog v1.2.1 diff --git a/go.sum b/go.sum index c1b46d03..8744de4b 100644 --- a/go.sum +++ b/go.sum @@ -8,10 +8,10 @@ github.com/IBM/go-sdk-core/v5 v5.17.4 h1:VGb9+mRrnS2HpHZFM5hy4J6ppIWnwNrw0G+tLSg github.com/IBM/go-sdk-core/v5 v5.17.4/go.mod h1:KsAAI7eStAWwQa4F96MLy+whYSh39JzNjklZRbN/8ns= github.com/IBM/ibm-csi-common v1.1.18 h1:CbzoONFN6vdmPLoXGxygiq3sbr2xtAcVUb0Vqj3/HNI= github.com/IBM/ibm-csi-common v1.1.18/go.mod h1:bDs9CLfr09kFpSMcR35e9AmyR2pSydx8goHjagFPrHs= -github.com/IBM/ibmcloud-volume-interface v1.2.6 h1:OLumrSQ0XTOp6gW+k0z2X53uTYOIt1wWSkTCXzK/vAM= -github.com/IBM/ibmcloud-volume-interface v1.2.6/go.mod h1:sDeQiPuN8k9yTRl9FbE2GZCXPNg4cV3oldUfL8wwGNA= -github.com/IBM/ibmcloud-volume-vpc v1.1.12 h1:DSC+YfddhegnixdX3stOgsIqyKlbc5wF5ofWomyMIsI= -github.com/IBM/ibmcloud-volume-vpc v1.1.12/go.mod h1:bdVgIWQmiq4ehs4buHpMYwFh6nlIaKBOxRGJoTh6bwY= +github.com/IBM/ibmcloud-volume-interface v1.2.9 h1:ug55V2mzK/IaFkfuKDOt74yzhLapSR/+qVgfQblfAjw= +github.com/IBM/ibmcloud-volume-interface v1.2.9/go.mod h1:sDeQiPuN8k9yTRl9FbE2GZCXPNg4cV3oldUfL8wwGNA= +github.com/IBM/ibmcloud-volume-vpc v1.1.14 h1:rs8f4OO+lP3jOIi5tpgiWVyVEL6g4lazGfMEsLpsfUI= +github.com/IBM/ibmcloud-volume-vpc v1.1.14/go.mod h1:CSAsBgEXN6WL8y/EpEj9GA+w+vs3fVLoRadtuCWUAz8= github.com/IBM/secret-common-lib v1.1.11 h1:EpfEe1gT1bnFQ3bxQPrh6bzTPeGjUo1NReVkCCP+TOc= github.com/IBM/secret-common-lib v1.1.11/go.mod h1:7YJF0ipT979nHIPkiCpvjFboFoIhrmYnIliE1vjCjZM= github.com/IBM/secret-utils-lib v1.1.11 h1:w87BzkddoFFlhRuWRteuGj3/561lEUg6Oo0RajVC87A= diff --git a/pkg/ibmcsidriver/controller.go b/pkg/ibmcsidriver/controller.go index 9ef9e596..85cb972c 100644 --- a/pkg/ibmcsidriver/controller.go +++ b/pkg/ibmcsidriver/controller.go @@ -22,7 +22,6 @@ import ( "strings" "time" - cloudProvider "github.com/IBM/ibm-csi-common/pkg/ibmcloudprovider" commonError "github.com/IBM/ibm-csi-common/pkg/messages" "github.com/IBM/ibm-csi-common/pkg/metrics" "github.com/IBM/ibm-csi-common/pkg/utils" @@ -30,6 +29,7 @@ import ( providerError "github.com/IBM/ibmcloud-volume-interface/lib/utils" utilReasonCode "github.com/IBM/ibmcloud-volume-interface/lib/utils/reasoncode" userError "github.com/IBM/ibmcloud-volume-vpc/common/messages" + cloudProvider "github.com/IBM/ibmcloud-volume-vpc/pkg/ibmcloudprovider" csi "github.com/container-storage-interface/spec/lib/go/csi" "go.uber.org/zap" diff --git a/pkg/ibmcsidriver/controller_helper_test.go b/pkg/ibmcsidriver/controller_helper_test.go index e158b2b0..ca2c90ec 100644 --- a/pkg/ibmcsidriver/controller_helper_test.go +++ b/pkg/ibmcsidriver/controller_helper_test.go @@ -21,10 +21,10 @@ import ( "fmt" "testing" - cloudProvider "github.com/IBM/ibm-csi-common/pkg/ibmcloudprovider" "github.com/IBM/ibm-csi-common/pkg/utils" "github.com/IBM/ibmcloud-volume-interface/config" "github.com/IBM/ibmcloud-volume-interface/lib/provider" + cloudProvider "github.com/IBM/ibmcloud-volume-vpc/pkg/ibmcloudprovider" csi "github.com/container-storage-interface/spec/lib/go/csi" "github.com/stretchr/testify/assert" ) @@ -198,9 +198,8 @@ func TestGetVolumeParameters(t *testing.T) { }, expectedVolume: &provider.Volume{Name: &volumeName, Capacity: &volumeSize, - VPCVolume: provider.VPCVolume{VPCBlockVolume: provider.VPCBlockVolume{ - Tags: []string{createdByIBM}, - }, + VPCVolume: provider.VPCVolume{ + Tags: []string{createdByIBM}, Profile: &provider.Profile{Name: "general-purpose"}, ResourceGroup: &provider.ResourceGroup{ID: "myresourcegroups"}, }, @@ -333,9 +332,8 @@ func TestGetVolumeParameters(t *testing.T) { }, expectedVolume: &provider.Volume{Name: &volumeName, Capacity: &volumeSize, - VPCVolume: provider.VPCVolume{VPCBlockVolume: provider.VPCBlockVolume{ - Tags: []string{createdByIBM}, - }, + VPCVolume: provider.VPCVolume{ + Tags: []string{createdByIBM}, Profile: &provider.Profile{Name: "general-purpose"}, ResourceGroup: &provider.ResourceGroup{ID: "myresourcegroups"}, }, @@ -421,9 +419,8 @@ func TestOverrideParams(t *testing.T) { }, expectedVolume: &provider.Volume{Name: &volumeName, Capacity: &volumeSize, - VPCVolume: provider.VPCVolume{VPCBlockVolume: provider.VPCBlockVolume{ - Tags: []string{createdByIBM}, - }, + VPCVolume: provider.VPCVolume{ + Tags: []string{createdByIBM}, Profile: &provider.Profile{Name: "general-purpose"}, ResourceGroup: &provider.ResourceGroup{ID: "secret-rg"}, }, @@ -507,9 +504,8 @@ func TestOverrideParams(t *testing.T) { }, expectedVolume: &provider.Volume{Name: &volumeName, Capacity: &volumeSize, - VPCVolume: provider.VPCVolume{VPCBlockVolume: provider.VPCBlockVolume{ - Tags: []string{createdByIBM}, - }, + VPCVolume: provider.VPCVolume{ + Tags: []string{createdByIBM}, Profile: &provider.Profile{Name: "custom"}, ResourceGroup: &provider.ResourceGroup{ID: "myresourcegroups"}, }, @@ -604,9 +600,8 @@ func TestCreateCSIVolumeResponse(t *testing.T) { { testCaseName: "Valid volume response", requestVol: provider.Volume{VolumeID: volumeID, - VPCVolume: provider.VPCVolume{VPCBlockVolume: provider.VPCBlockVolume{ - Tags: []string{createdByIBM}, - }, + VPCVolume: provider.VPCVolume{ + Tags: []string{createdByIBM}, Profile: &provider.Profile{Name: "general-purpose"}, ResourceGroup: &provider.ResourceGroup{ID: "myresourcegroups"}, }, @@ -636,9 +631,8 @@ func TestCreateCSIVolumeResponse(t *testing.T) { { testCaseName: "Valid volume response with region in vol request empty", requestVol: provider.Volume{VolumeID: volumeID, - VPCVolume: provider.VPCVolume{VPCBlockVolume: provider.VPCBlockVolume{ - Tags: []string{createdByIBM}, - }, + VPCVolume: provider.VPCVolume{ + Tags: []string{createdByIBM}, Profile: &provider.Profile{Name: "general-purpose"}, ResourceGroup: &provider.ResourceGroup{ID: "myresourcegroups"}, }, diff --git a/pkg/ibmcsidriver/controller_test.go b/pkg/ibmcsidriver/controller_test.go index 91c00691..333f4f47 100644 --- a/pkg/ibmcsidriver/controller_test.go +++ b/pkg/ibmcsidriver/controller_test.go @@ -33,8 +33,8 @@ import ( csi "github.com/container-storage-interface/spec/lib/go/csi" "github.com/stretchr/testify/assert" - cloudProvider "github.com/IBM/ibm-csi-common/pkg/ibmcloudprovider" "github.com/IBM/ibmcloud-volume-interface/lib/provider/fake" + cloudProvider "github.com/IBM/ibmcloud-volume-vpc/pkg/ibmcloudprovider" "golang.org/x/net/context" "google.golang.org/grpc/codes" "google.golang.org/grpc/status" diff --git a/pkg/ibmcsidriver/fileOps_test.go b/pkg/ibmcsidriver/fileOps_test.go index b264bc8e..6e92b06a 100644 --- a/pkg/ibmcsidriver/fileOps_test.go +++ b/pkg/ibmcsidriver/fileOps_test.go @@ -21,7 +21,7 @@ import ( "os" "testing" - cloudProvider "github.com/IBM/ibm-csi-common/pkg/ibmcloudprovider" + cloudProvider "github.com/IBM/ibmcloud-volume-vpc/pkg/ibmcloudprovider" "github.com/kubernetes-sigs/ibm-vpc-block-csi-driver/pkg/ibmcsidriver/ibmcsidriverfakes" "github.com/stretchr/testify/assert" ) diff --git a/pkg/ibmcsidriver/ibm_csi_driver.go b/pkg/ibmcsidriver/ibm_csi_driver.go index 2416d971..326cbd04 100644 --- a/pkg/ibmcsidriver/ibm_csi_driver.go +++ b/pkg/ibmcsidriver/ibm_csi_driver.go @@ -20,11 +20,11 @@ package ibmcsidriver import ( "fmt" - cloudProvider "github.com/IBM/ibm-csi-common/pkg/ibmcloudprovider" commonError "github.com/IBM/ibm-csi-common/pkg/messages" nodeMetadata "github.com/IBM/ibm-csi-common/pkg/metadata" mountManager "github.com/IBM/ibm-csi-common/pkg/mountmanager" "github.com/IBM/ibm-csi-common/pkg/utils" + cloudProvider "github.com/IBM/ibmcloud-volume-vpc/pkg/ibmcloudprovider" csi "github.com/container-storage-interface/spec/lib/go/csi" "go.uber.org/zap" ) diff --git a/pkg/ibmcsidriver/ibm_csi_driver_test.go b/pkg/ibmcsidriver/ibm_csi_driver_test.go index e810f335..004d4c89 100644 --- a/pkg/ibmcsidriver/ibm_csi_driver_test.go +++ b/pkg/ibmcsidriver/ibm_csi_driver_test.go @@ -22,10 +22,10 @@ import ( testingexec "k8s.io/utils/exec/testing" - cloudProvider "github.com/IBM/ibm-csi-common/pkg/ibmcloudprovider" nodeMetadata "github.com/IBM/ibm-csi-common/pkg/metadata" nodeInfo "github.com/IBM/ibm-csi-common/pkg/metadata/fake" mountManager "github.com/IBM/ibm-csi-common/pkg/mountmanager" + cloudProvider "github.com/IBM/ibmcloud-volume-vpc/pkg/ibmcloudprovider" "github.com/stretchr/testify/assert" ) diff --git a/pkg/ibmcsidriver/node_helper_test.go b/pkg/ibmcsidriver/node_helper_test.go index 61403a09..c3f00627 100644 --- a/pkg/ibmcsidriver/node_helper_test.go +++ b/pkg/ibmcsidriver/node_helper_test.go @@ -19,7 +19,7 @@ package ibmcsidriver import ( "testing" - cloudProvider "github.com/IBM/ibm-csi-common/pkg/ibmcloudprovider" + cloudProvider "github.com/IBM/ibmcloud-volume-vpc/pkg/ibmcloudprovider" "github.com/stretchr/testify/assert" ) diff --git a/pkg/ibmcsidriver/server_test.go b/pkg/ibmcsidriver/server_test.go index 62dead26..1f651eec 100644 --- a/pkg/ibmcsidriver/server_test.go +++ b/pkg/ibmcsidriver/server_test.go @@ -21,7 +21,7 @@ import ( "flag" "testing" - cloudProvider "github.com/IBM/ibm-csi-common/pkg/ibmcloudprovider" + cloudProvider "github.com/IBM/ibmcloud-volume-vpc/pkg/ibmcloudprovider" "github.com/stretchr/testify/assert" ) diff --git a/tests/sanity/sanity_test.go b/tests/sanity/sanity_test.go index 3e767eb5..08140c72 100644 --- a/tests/sanity/sanity_test.go +++ b/tests/sanity/sanity_test.go @@ -41,8 +41,8 @@ import ( "google.golang.org/grpc" "google.golang.org/grpc/credentials/insecure" - cloudProvider "github.com/IBM/ibm-csi-common/pkg/ibmcloudprovider" nodeMetadata "github.com/IBM/ibm-csi-common/pkg/metadata" + cloudProvider "github.com/IBM/ibmcloud-volume-vpc/pkg/ibmcloudprovider" mountManager "github.com/IBM/ibm-csi-common/pkg/mountmanager" diff --git a/vendor/github.com/IBM/ibmcloud-volume-interface/lib/provider/vpc_data_types.go b/vendor/github.com/IBM/ibmcloud-volume-interface/lib/provider/vpc_data_types.go index caa396ad..92e1e600 100644 --- a/vendor/github.com/IBM/ibmcloud-volume-interface/lib/provider/vpc_data_types.go +++ b/vendor/github.com/IBM/ibmcloud-volume-interface/lib/provider/vpc_data_types.go @@ -26,13 +26,14 @@ type VPCVolume struct { VolumeEncryptionKey *VolumeEncryptionKey `json:"encryption_key,omitempty"` Profile *Profile `json:"profile,omitempty"` CRN string `json:"crn,omitempty"` + Status string `json:"status,omitempty"` + Tags []string `json:"volume_tags,omitempty"` VPCBlockVolume VPCFileVolume } // VPCBlockVolume specific parameters type VPCBlockVolume struct { - Tags []string `json:"volume_tags,omitempty"` VolumeAttachments *[]VolumeAttachment `json:"volume_attachments,omitempty"` } diff --git a/vendor/github.com/IBM/ibmcloud-volume-vpc/block/provider/update_volume.go b/vendor/github.com/IBM/ibmcloud-volume-vpc/block/provider/update_volume.go index 5f4c00d4..c766290b 100644 --- a/vendor/github.com/IBM/ibmcloud-volume-vpc/block/provider/update_volume.go +++ b/vendor/github.com/IBM/ibmcloud-volume-vpc/block/provider/update_volume.go @@ -18,12 +18,77 @@ package provider import ( - "errors" + "strings" "github.com/IBM/ibmcloud-volume-interface/lib/provider" + userError "github.com/IBM/ibmcloud-volume-vpc/common/messages" + "github.com/IBM/ibmcloud-volume-vpc/common/vpcclient/models" + "go.uber.org/zap" ) -// UpdateVolume POSTs to /volumes -func (vpc *VPCSession) UpdateVolume(volumeTemplate provider.Volume) error { - return errors.New("unsupported Operation") +// UpdateVolume PATCH to /volumes +func (vpcs *VPCSession) UpdateVolume(volumeRequest provider.Volume) error { + var existVolume *models.Volume + var err error + var etag string + + //Fetch existing volume Tags + err = RetryWithMinRetries(vpcs.Logger, func() error { + // Get volume details + existVolume, etag, err = vpcs.Apiclient.VolumeService().GetVolumeEtag(volumeRequest.VolumeID, vpcs.Logger) + + if err != nil { + return err + } + if existVolume != nil && existVolume.Status == validVolumeStatus { + vpcs.Logger.Info("Volume got valid (available) state",zap.Reflect("etag", etag)) + return nil + } + return userError.GetUserError("VolumeNotInValidState", err, volumeRequest.VolumeID) + }) + + if err != nil { + return err + } + + //If tags are equal then skip the UpdateVolume RIAAS API call + if ifTagsEqual(existVolume.UserTags, volumeRequest.VPCVolume.Tags) { + vpcs.Logger.Info("There is no change in user tags for volume, skipping the updateVolume for VPC IaaS... ", zap.Reflect("existVolume", existVolume.UserTags), zap.Reflect("volumeRequest", volumeRequest.VPCVolume.Tags)) + return nil + } + + //Append the existing tags with the requested input tags + existVolume.UserTags = append(existVolume.UserTags, volumeRequest.VPCVolume.Tags...) + + volume := &models.Volume{ + UserTags: existVolume.UserTags, + } + + vpcs.Logger.Info("Calling VPC provider for volume UpdateVolumeWithTags...") + + err = RetryWithMinRetries(vpcs.Logger, func() error { + err = vpcs.Apiclient.VolumeService().UpdateVolumeWithEtag(volumeRequest.VolumeID, etag, volume, vpcs.Logger) + return err + }) + + if err != nil { + vpcs.Logger.Error("Failed to update volume tags from VPC provider", zap.Reflect("BackendError", err)) + return userError.GetUserError("FailedToUpdateVolume", err, volumeRequest.VolumeID) + } + + return err +} + +// ifTagsEqual will check if there is change to existing tags +func ifTagsEqual(existingTags []string, newTags []string) bool { + //Join slice into a string + tags := strings.ToLower(strings.Join(existingTags, ",")) + for _, v := range newTags { + if !strings.Contains(tags, strings.ToLower(v)) { + //Tags are different + return false + } + } + //Tags are equal + return true } diff --git a/vendor/github.com/IBM/ibmcloud-volume-vpc/block/provider/util.go b/vendor/github.com/IBM/ibmcloud-volume-vpc/block/provider/util.go index a8f26ed4..e1e9ca8f 100644 --- a/vendor/github.com/IBM/ibmcloud-volume-vpc/block/provider/util.go +++ b/vendor/github.com/IBM/ibmcloud-volume-vpc/block/provider/util.go @@ -31,6 +31,9 @@ import ( // maxRetryAttempt ... var maxRetryAttempt = 10 +// minRetryAttempt ... +var minRetryAttempt = 3 + // maxRetryGap ... var maxRetryGap = 60 @@ -119,6 +122,41 @@ func retry(logger *zap.Logger, retryfunc func() error) error { return err } +// retry ... +func RetryWithMinRetries(logger *zap.Logger, retryfunc func() error) error { + var err error + retryGap := 10 + for i := 0; i < minRetryAttempt; i++ { + if i > 0 { + time.Sleep(time.Duration(retryGap) * time.Second) + } + err = retryfunc() + if err != nil { + logger.Info("err object is not nil", zap.Reflect("ERR", err)) + //Skip retry for the below type of Errors + modelError, ok := err.(*models.Error) + if !ok { + continue + } + if skipRetry(modelError) { + break + } + if i >= 1 { + retryGap = 2 * retryGap + if retryGap > maxRetryGap { + retryGap = maxRetryGap + } + } + if (i + 1) < minRetryAttempt { + logger.Info("Error while executing the function. Re-attempting execution ..", zap.Int("attempt..", i+2), zap.Int("retry-gap", retryGap), zap.Int("max-retry-Attempts", minRetryAttempt), zap.Error(err)) + } + continue + } + return err + } + return err +} + // skipRetry skip retry as per listed error codes func skipRetry(err *models.Error) bool { for _, errorItem := range err.Errors { @@ -351,6 +389,7 @@ func FromProviderToLibVolume(vpcVolume *models.Volume, logger *zap.Logger) (libV } libVolume.CRN = vpcVolume.CRN libVolume.Tags = vpcVolume.UserTags + libVolume.Status = string(vpcVolume.Status) return } diff --git a/vendor/github.com/IBM/ibmcloud-volume-vpc/common/vpcclient/client/request.go b/vendor/github.com/IBM/ibmcloud-volume-vpc/common/vpcclient/client/request.go index 8ba71f20..a9674736 100644 --- a/vendor/github.com/IBM/ibmcloud-volume-vpc/common/vpcclient/client/request.go +++ b/vendor/github.com/IBM/ibmcloud-volume-vpc/common/vpcclient/client/request.go @@ -126,6 +126,12 @@ func (r *Request) SetQueryValue(key, value string) *Request { return r } +// SetHeader ... +func (r *Request) SetHeader(key, value string) *Request { + r.headers.Set(key, value) + return r +} + // JSONBody converts the supplied argument to JSON to use as the body of a request func (r *Request) JSONBody(p interface{}) *Request { if r.operation.Method == http.MethodPost && reflect.ValueOf(p).Kind() == reflect.Struct { diff --git a/vendor/github.com/IBM/ibmcloud-volume-vpc/common/vpcclient/vpcvolume/get_volume.go b/vendor/github.com/IBM/ibmcloud-volume-vpc/common/vpcclient/vpcvolume/get_volume.go index f8d43646..34d935e2 100644 --- a/vendor/github.com/IBM/ibmcloud-volume-vpc/common/vpcclient/vpcvolume/get_volume.go +++ b/vendor/github.com/IBM/ibmcloud-volume-vpc/common/vpcclient/vpcvolume/get_volume.go @@ -47,6 +47,7 @@ func (vs *VolumeService) GetVolume(volumeID string, ctxLogger *zap.Logger) (*mod req := request.PathParameter(volumeIDParam, volumeID) _, err := req.JSONSuccess(&volume).JSONError(&apiErr).Invoke() + if err != nil { return nil, err } diff --git a/vendor/github.com/IBM/ibmcloud-volume-vpc/common/vpcclient/vpcvolume/get_volume_etag.go b/vendor/github.com/IBM/ibmcloud-volume-vpc/common/vpcclient/vpcvolume/get_volume_etag.go new file mode 100644 index 00000000..6b27bf72 --- /dev/null +++ b/vendor/github.com/IBM/ibmcloud-volume-vpc/common/vpcclient/vpcvolume/get_volume_etag.go @@ -0,0 +1,56 @@ +/** + * Copyright 2025 IBM Corp. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +// Package vpcvolume ... +package vpcvolume + +import ( + "time" + + util "github.com/IBM/ibmcloud-volume-interface/lib/utils" + "github.com/IBM/ibmcloud-volume-vpc/common/vpcclient/client" + "github.com/IBM/ibmcloud-volume-vpc/common/vpcclient/models" + "go.uber.org/zap" +) + +// GetVolume POSTs to /volumes +func (vs *VolumeService) GetVolumeEtag(volumeID string, ctxLogger *zap.Logger) (*models.Volume, string, error) { + ctxLogger.Debug("Entry Backend GetVolumeEtag") + defer ctxLogger.Debug("Exit Backend GetVolumeEtag") + + defer util.TimeTracker("GetVolumeEtag", time.Now()) + + operation := &client.Operation{ + Name: "GetVolume", + Method: "GET", + PathPattern: volumeIDPath, + } + + var volume models.Volume + var apiErr models.Error + + request := vs.client.NewRequest(operation) + ctxLogger.Info("Equivalent curl command", zap.Reflect("URL", request.URL()), zap.Reflect("Operation", operation)) + + req := request.PathParameter(volumeIDParam, volumeID) + resp, err := req.JSONSuccess(&volume).JSONError(&apiErr).Invoke() + + if err != nil { + return nil, "", err + } + + return &volume, resp.Header.Get("etag"), nil +} diff --git a/vendor/github.com/IBM/ibmcloud-volume-vpc/common/vpcclient/vpcvolume/update_volume.go b/vendor/github.com/IBM/ibmcloud-volume-vpc/common/vpcclient/vpcvolume/update_volume.go index 78bfdc82..2a8f377d 100644 --- a/vendor/github.com/IBM/ibmcloud-volume-vpc/common/vpcclient/vpcvolume/update_volume.go +++ b/vendor/github.com/IBM/ibmcloud-volume-vpc/common/vpcclient/vpcvolume/update_volume.go @@ -24,7 +24,7 @@ import ( "go.uber.org/zap" ) -// UpdateVolume POSTs to /volumes. Riaas/VPC does have volume update support yet +// UpdateVolume PATCH to /volumes for updating func (vs *VolumeService) UpdateVolume(volumeTemplate *models.Volume, ctxLogger *zap.Logger) error { return errors.New("unsupported Operation") } diff --git a/vendor/github.com/IBM/ibmcloud-volume-vpc/common/vpcclient/vpcvolume/update_volume_with_etag.go b/vendor/github.com/IBM/ibmcloud-volume-vpc/common/vpcclient/vpcvolume/update_volume_with_etag.go new file mode 100644 index 00000000..69bd797a --- /dev/null +++ b/vendor/github.com/IBM/ibmcloud-volume-vpc/common/vpcclient/vpcvolume/update_volume_with_etag.go @@ -0,0 +1,56 @@ +/** + * Copyright 2025 IBM Corp. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +// Package vpcvolume ... +package vpcvolume + +import ( + "time" + + util "github.com/IBM/ibmcloud-volume-interface/lib/utils" + "github.com/IBM/ibmcloud-volume-vpc/common/vpcclient/client" + "github.com/IBM/ibmcloud-volume-vpc/common/vpcclient/models" + "go.uber.org/zap" +) + +// UpdateVolume PATCH to /volumes for updating user tags only +func (vs *VolumeService) UpdateVolumeWithEtag(volumeID string, etag string, volumeTemplate *models.Volume, ctxLogger *zap.Logger) error { + ctxLogger.Debug("Entry Backend UpdateVolumeWithEtag") + defer ctxLogger.Debug("Exit Backend UpdateVolumeWithEtag") + + defer util.TimeTracker("UpdateVolumeWithEtag", time.Now()) + + operation := &client.Operation{ + Name: "UpdateVolume", + Method: "PATCH", + PathPattern: volumeIDPath, + } + + var apiErr models.Error + + request := vs.client.NewRequest(operation) + request.SetHeader("If-Match", etag) + + req := request.PathParameter(volumeIDParam, volumeID) + ctxLogger.Info("Equivalent curl command and payload details", zap.Reflect("URL", req.URL()), zap.Reflect("Payload", volumeTemplate), zap.Reflect("Operation", operation)) + _, err := req.JSONBody(volumeTemplate).JSONError(&apiErr).Invoke() + + if err != nil { + return err + } + + return nil +} diff --git a/vendor/github.com/IBM/ibmcloud-volume-vpc/common/vpcclient/vpcvolume/volume_service.go b/vendor/github.com/IBM/ibmcloud-volume-vpc/common/vpcclient/vpcvolume/volume_service.go index 0569f566..9f4537e0 100644 --- a/vendor/github.com/IBM/ibmcloud-volume-vpc/common/vpcclient/vpcvolume/volume_service.go +++ b/vendor/github.com/IBM/ibmcloud-volume-vpc/common/vpcclient/vpcvolume/volume_service.go @@ -24,12 +24,18 @@ import ( ) // VolumeManager operations +// +//go:generate counterfeiter -o fakes/volume.go --fake-name VolumeService . VolumeManager type VolumeManager interface { // Create the volume with authorisation by passing required information in the volume object CreateVolume(volumeTemplate *models.Volume, ctxLogger *zap.Logger) (*models.Volume, error) + // UpdateVolume updates the volume with authorisation by passing required information in the volume object UpdateVolume(volumeTemplate *models.Volume, ctxLogger *zap.Logger) error + // UpdateVolumeWithEtag updates the volume with tags by passing etag in header + UpdateVolumeWithEtag(volumeID string, etag string, volumeTemplate *models.Volume, ctxLogger *zap.Logger) error + // ExpandVolume ... ExpandVolume(volumeID string, volumeTemplate *models.Volume, ctxLogger *zap.Logger) (*models.Volume, error) @@ -42,6 +48,9 @@ type VolumeManager interface { // Get the volume by using volume name GetVolumeByName(volumeName string, ctxLogger *zap.Logger) (*models.Volume, error) + // Get the volume etag by using ID + GetVolumeEtag(volumeID string, ctxLogger *zap.Logger) (*models.Volume, string, error) + // Others // Get volume lists by using snapshot tags ListVolumes(limit int, start string, filters *models.ListVolumeFilters, ctxLogger *zap.Logger) (*models.VolumeList, error) diff --git a/vendor/github.com/IBM/ibmcloud-volume-vpc/iks/provider/session.go b/vendor/github.com/IBM/ibmcloud-volume-vpc/iks/provider/session.go index ba570f1a..1948df4f 100644 --- a/vendor/github.com/IBM/ibmcloud-volume-vpc/iks/provider/session.go +++ b/vendor/github.com/IBM/ibmcloud-volume-vpc/iks/provider/session.go @@ -61,35 +61,35 @@ func (vpcIks *IksVpcSession) Type() provider.VolumeType { // AttachVolume attach volume based on given volume attachment request func (vpcIks *IksVpcSession) AttachVolume(volumeAttachmentRequest provider.VolumeAttachmentRequest) (*provider.VolumeAttachmentResponse, error) { - vpcIks.Logger.Debug("Entry of IksVpcSession.AttachVolume method...") - defer vpcIks.Logger.Debug("Exit from IksVpcSession.AttachVolume method...") + vpcIks.IksSession.Logger.Debug("Entry of IksVpcSession.AttachVolume method...") + defer vpcIks.IksSession.Logger.Debug("Exit from IksVpcSession.AttachVolume method...") return vpcIks.IksSession.AttachVolume(volumeAttachmentRequest) } // DetachVolume attach volume based on given volume attachment request func (vpcIks *IksVpcSession) DetachVolume(volumeAttachmentRequest provider.VolumeAttachmentRequest) (*http.Response, error) { vpcIks.IksSession.Logger.Debug("Entry of IksVpcSession.DetachVolume method...") - defer vpcIks.Logger.Debug("Exit from IksVpcSession.DetachVolume method...") + defer vpcIks.IksSession.Logger.Debug("Exit from IksVpcSession.DetachVolume method...") return vpcIks.IksSession.DetachVolume(volumeAttachmentRequest) } // GetVolumeAttachment attach volume based on given volume attachment request func (vpcIks *IksVpcSession) GetVolumeAttachment(volumeAttachmentRequest provider.VolumeAttachmentRequest) (*provider.VolumeAttachmentResponse, error) { - vpcIks.Logger.Debug("Entry of IksVpcSession.GetVolumeAttachment method...") - defer vpcIks.Logger.Debug("Exit from IksVpcSession.GetVolumeAttachment method...") + vpcIks.IksSession.Logger.Debug("Entry of IksVpcSession.GetVolumeAttachment method...") + defer vpcIks.IksSession.Logger.Debug("Exit from IksVpcSession.GetVolumeAttachment method...") return vpcIks.IksSession.GetVolumeAttachment(volumeAttachmentRequest) } // WaitForAttachVolume attach volume based on given volume attachment request func (vpcIks *IksVpcSession) WaitForAttachVolume(volumeAttachmentRequest provider.VolumeAttachmentRequest) (*provider.VolumeAttachmentResponse, error) { - vpcIks.Logger.Debug("Entry of IksVpcSession.WaitForAttachVolume method...") - defer vpcIks.Logger.Debug("Exit from IksVpcSession.WaitForAttachVolume method...") + vpcIks.IksSession.Logger.Debug("Entry of IksVpcSession.WaitForAttachVolume method...") + defer vpcIks.IksSession.Logger.Debug("Exit from IksVpcSession.WaitForAttachVolume method...") return vpcIks.IksSession.WaitForAttachVolume(volumeAttachmentRequest) } // WaitForDetachVolume attach volume based on given volume attachment request func (vpcIks *IksVpcSession) WaitForDetachVolume(volumeAttachmentRequest provider.VolumeAttachmentRequest) error { - vpcIks.Logger.Debug("Entry of IksVpcSession.WaitForDetachVolume method...") - defer vpcIks.Logger.Debug("Exit from IksVpcSession.WaitForDetachVolume method...") + vpcIks.IksSession.Logger.Debug("Entry of IksVpcSession.WaitForDetachVolume method...") + defer vpcIks.IksSession.Logger.Debug("Exit from IksVpcSession.WaitForDetachVolume method...") return vpcIks.IksSession.WaitForDetachVolume(volumeAttachmentRequest) } diff --git a/vendor/github.com/IBM/ibmcloud-volume-vpc/iks/provider/update_volume.go b/vendor/github.com/IBM/ibmcloud-volume-vpc/iks/provider/update_volume.go index a70dafb2..9fbda549 100644 --- a/vendor/github.com/IBM/ibmcloud-volume-vpc/iks/provider/update_volume.go +++ b/vendor/github.com/IBM/ibmcloud-volume-vpc/iks/provider/update_volume.go @@ -54,7 +54,7 @@ func (vpcIks *IksVpcSession) UpdateVolume(volumeRequest provider.Volume) (err er vpcIks.Logger.Debug("Failed to update volume", zap.Reflect("BackendError", err)) return userError.GetUserError("UpdateFailed", err) } - + vpcIks.Logger.Info("Successfully updated volume...") return err } diff --git a/vendor/github.com/IBM/ibm-csi-common/pkg/ibmcloudprovider/fake_volume_provider.go b/vendor/github.com/IBM/ibmcloud-volume-vpc/pkg/ibmcloudprovider/fake_volume_provider.go similarity index 96% rename from vendor/github.com/IBM/ibm-csi-common/pkg/ibmcloudprovider/fake_volume_provider.go rename to vendor/github.com/IBM/ibmcloud-volume-vpc/pkg/ibmcloudprovider/fake_volume_provider.go index 486752b4..817a8884 100644 --- a/vendor/github.com/IBM/ibm-csi-common/pkg/ibmcloudprovider/fake_volume_provider.go +++ b/vendor/github.com/IBM/ibmcloud-volume-vpc/pkg/ibmcloudprovider/fake_volume_provider.go @@ -1,5 +1,5 @@ /** - * Copyright 2021 IBM Corp. + * Copyright 2025 IBM Corp. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -18,15 +18,15 @@ package ibmcloudprovider import ( - "bytes" + "bytes" "testing" - "github.com/IBM/ibmcloud-volume-interface/config" "github.com/IBM/ibmcloud-volume-interface/lib/provider" "github.com/IBM/ibmcloud-volume-interface/lib/provider/fake" "go.uber.org/zap" - "go.uber.org/zap/zapcore" "golang.org/x/net/context" + "github.com/stretchr/testify/assert" + "go.uber.org/zap/zapcore" ) const ( @@ -64,7 +64,16 @@ const ( TestAPIVersion = "2019-07-02" ) -// GetTestLogger ... +// FakeIBMCloudStorageProvider Provider +type FakeIBMCloudStorageProvider struct { + ProviderName string + ProviderConfig *config.Config + ClusterID string + fakeSession *fake.FakeSession +} + +var _ CloudProviderInterface = &FakeIBMCloudStorageProvider{} + func GetTestLogger(t *testing.T) (logger *zap.Logger, teardown func()) { atom := zap.NewAtomicLevel() atom.SetLevel(zap.DebugLevel) @@ -85,24 +94,17 @@ func GetTestLogger(t *testing.T) (logger *zap.Logger, teardown func()) { ) teardown = func() { - _ = logger.Sync() + err := logger.Sync() + assert.Nil(t, err) + if t.Failed() { t.Log(buf) } } - return -} -// FakeIBMCloudStorageProvider Provider -type FakeIBMCloudStorageProvider struct { - ProviderName string - ProviderConfig *config.Config - ClusterID string - fakeSession *fake.FakeSession + return } -var _ CloudProviderInterface = &FakeIBMCloudStorageProvider{} - // NewFakeIBMCloudStorageProvider ... func NewFakeIBMCloudStorageProvider(configPath string, logger *zap.Logger) (*FakeIBMCloudStorageProvider, error) { return &FakeIBMCloudStorageProvider{ProviderName: "FakeIBMCloudStorageProvider", diff --git a/vendor/github.com/IBM/ibm-csi-common/pkg/ibmcloudprovider/ibm_volume_provider.go b/vendor/github.com/IBM/ibmcloud-volume-vpc/pkg/ibmcloudprovider/ibm_volume_provider.go similarity index 97% rename from vendor/github.com/IBM/ibm-csi-common/pkg/ibmcloudprovider/ibm_volume_provider.go rename to vendor/github.com/IBM/ibmcloud-volume-vpc/pkg/ibmcloudprovider/ibm_volume_provider.go index 98c4c5c0..7f572498 100644 --- a/vendor/github.com/IBM/ibm-csi-common/pkg/ibmcloudprovider/ibm_volume_provider.go +++ b/vendor/github.com/IBM/ibmcloud-volume-vpc/pkg/ibmcloudprovider/ibm_volume_provider.go @@ -1,5 +1,5 @@ /** - * Copyright 2021 IBM Corp. + * Copyright 2025 IBM Corp. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. diff --git a/vendor/github.com/IBM/ibmcloud-volume-vpc/pkg/ibmcloudprovider/volume_provider.go b/vendor/github.com/IBM/ibmcloud-volume-vpc/pkg/ibmcloudprovider/volume_provider.go index d24188ea..a48eb52f 100644 --- a/vendor/github.com/IBM/ibmcloud-volume-vpc/pkg/ibmcloudprovider/volume_provider.go +++ b/vendor/github.com/IBM/ibmcloud-volume-vpc/pkg/ibmcloudprovider/volume_provider.go @@ -23,7 +23,6 @@ import ( "strings" "time" - cloudProvider "github.com/IBM/ibm-csi-common/pkg/ibmcloudprovider" "github.com/IBM/ibmcloud-volume-interface/config" "github.com/IBM/ibmcloud-volume-interface/lib/provider" "github.com/IBM/ibmcloud-volume-interface/provider/local" @@ -44,7 +43,7 @@ type IBMCloudStorageProvider struct { ClusterID string } -var _ cloudProvider.CloudProviderInterface = &IBMCloudStorageProvider{} +var _ CloudProviderInterface = &IBMCloudStorageProvider{} // NewIBMCloudStorageProvider ... func NewIBMCloudStorageProvider(clusterVolumeLabel string, k8sClient *k8s_utils.KubernetesClient, logger *zap.Logger) (*IBMCloudStorageProvider, error) { diff --git a/vendor/github.com/IBM/ibm-csi-common/pkg/watcher/pv_watcher.go b/vendor/github.com/IBM/ibmcloud-volume-vpc/pkg/watcher/pv_watcher.go similarity index 63% rename from vendor/github.com/IBM/ibm-csi-common/pkg/watcher/pv_watcher.go rename to vendor/github.com/IBM/ibmcloud-volume-vpc/pkg/watcher/pv_watcher.go index 9ab79c30..f0884685 100644 --- a/vendor/github.com/IBM/ibm-csi-common/pkg/watcher/pv_watcher.go +++ b/vendor/github.com/IBM/ibmcloud-volume-vpc/pkg/watcher/pv_watcher.go @@ -1,5 +1,5 @@ /** - * Copyright 2021 IBM Corp. + * Copyright 2025 IBM Corp. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -23,12 +23,16 @@ import ( "strings" "time" + uid "github.com/gofrs/uuid" + "go.uber.org/zap/zapcore" + "github.com/golang/glog" - cloudprovider "github.com/IBM/ibm-csi-common/pkg/ibmcloudprovider" - "github.com/IBM/ibm-csi-common/pkg/utils" "github.com/IBM/ibmcloud-volume-interface/config" "github.com/IBM/ibmcloud-volume-interface/lib/provider" + iks_vpc_provider "github.com/IBM/ibmcloud-volume-vpc/iks/provider" + cloudprovider "github.com/IBM/ibmcloud-volume-vpc/pkg/ibmcloudprovider" + "go.uber.org/zap" "golang.org/x/net/context" v1 "k8s.io/api/core/v1" @@ -81,6 +85,24 @@ const ( VolumeUpdateEventReason = "VolumeMetaDataSaved" //VolumeUpdateEventSuccess ... VolumeUpdateEventSuccess = "Success" + + // VolumeIDLabel ... + VolumeIDLabel = "volumeId" + + // VolumeCRNLabel ... + VolumeCRNLabel = "volumeCRN" + + // ClusterIDLabel ... + ClusterIDLabel = "clusterID" + + // IOPSLabel ... + IOPSLabel = "iops" + + // ZoneLabel ... + ZoneLabel = "zone" + + // GiB in bytes + GiB = 1024 * 1024 * 1024 ) // VolumeTypeMap ... @@ -151,7 +173,7 @@ func (pvw *PVWatcher) Start() { func (pvw *PVWatcher) updateVolume(oldobj, obj interface{}) { // Run as non-blocking thread to allow parallel processing of volumes go func() { - ctxLogger, requestID := utils.GetContextLogger(context.Background(), false) + ctxLogger, requestID := GetContextLogger(context.Background(), false) // panic-recovery function that avoid watcher thread to stop because of unexexpected error defer func() { if r := recover(); r != nil { @@ -159,18 +181,45 @@ func (pvw *PVWatcher) updateVolume(oldobj, obj interface{}) { } }() - ctxLogger.Info("Entry updateVolume()", zap.Reflect("obj", obj)) - pv, _ := obj.(*v1.PersistentVolume) + ctxLogger.Info("Entry updateVolume()", zap.Reflect("obj", obj), zap.Reflect("oldobj", oldobj)) + newpv, _ := obj.(*v1.PersistentVolume) + //If there is no change to status , capacity or iops we can skip the updateVolume call. + if oldobj != nil { + oldpv, _ := oldobj.(*v1.PersistentVolume) + oldCapacity := oldpv.Spec.Capacity[v1.ResourceStorage] + capacity := newpv.Spec.Capacity[v1.ResourceStorage] + iops := newpv.Spec.CSI.VolumeAttributes[IOPSLabel] + oldiops := oldpv.Spec.CSI.VolumeAttributes[IOPSLabel] + + if (newpv.Status.Phase == oldpv.Status.Phase) && (oldCapacity.Value() == capacity.Value()) && (oldiops == iops) { + ctxLogger.Info("Skipping update Volume as there is no change in status , capacity and iops") + return + } + } + session, err := pvw.cloudProvider.GetProviderSession(context.Background(), ctxLogger) if session != nil { - volume := pvw.getVolume(pv, ctxLogger) - ctxLogger.Info("volume to update ", zap.Reflect("volume", volume)) - err := session.UpdateVolume(volume) + iksVpc, ok := session.(*iks_vpc_provider.IksVpcSession) + + if !ok { + ctxLogger.Error("Failed to get the IKS-VPC session, Try to restart the CSI driver controller POD") + return + } + + volume := pvw.getVolume(newpv, ctxLogger) + ctxLogger.Info("Updating metadata for the volume", zap.Reflect("volume", volume)) + err := iksVpc.UpdateVolume(volume) + if err != nil { + ctxLogger.Warn("Failed to update volume metadata", zap.Error(err)) + pvw.recorder.Event(newpv, v1.EventTypeWarning, VolumeUpdateEventReason, err.Error()) + } + ctxLogger.Info("Updating tags from VPC IaaS") + err = iksVpc.VPCSession.UpdateVolume(volume) if err != nil { - ctxLogger.Warn("Unable to update the volume", zap.Error(err)) - pvw.recorder.Event(pv, v1.EventTypeWarning, VolumeUpdateEventReason, err.Error()) + ctxLogger.Warn("Failed to update volume with tags from VPC IaaS", zap.Error(err)) + pvw.recorder.Event(newpv, v1.EventTypeWarning, VolumeUpdateEventReason, err.Error()) } else { - pvw.recorder.Event(pv, v1.EventTypeNormal, VolumeUpdateEventReason, VolumeUpdateEventSuccess) + pvw.recorder.Event(newpv, v1.EventTypeNormal, VolumeUpdateEventReason, VolumeUpdateEventSuccess) ctxLogger.Warn("Volume Metadata saved successfully") } } @@ -188,7 +237,7 @@ func (pvw *PVWatcher) getTags(pv *v1.PersistentVolume, ctxLogger *zap.Logger) (s tags = strings.Split(tagstr, ",") } // append default tags to users tag list - tags = append(tags, utils.ClusterIDLabel+":"+volAttributes[utils.ClusterIDLabel]) + tags = append(tags, ClusterIDLabel+":"+volAttributes[ClusterIDLabel]) tags = append(tags, ReclaimPolicyTag+string(pv.Spec.PersistentVolumeReclaimPolicy)) tags = append(tags, StorageClassTag+pv.Spec.StorageClassName) tags = append(tags, NameSpaceTag+pv.Spec.ClaimRef.Namespace) @@ -208,8 +257,8 @@ func (pvw *PVWatcher) getVolume(pv *v1.PersistentVolume, ctxLogger *zap.Logger) VolumeType: provider.VolumeType(VolumeTypeMap[pv.Spec.CSI.Driver]), } volume.CRN = crn - clusterID := pv.Spec.CSI.VolumeAttributes[utils.ClusterIDLabel] - volume.Attributes = map[string]string{strings.ToLower(utils.ClusterIDLabel): clusterID} + clusterID := pv.Spec.CSI.VolumeAttributes[ClusterIDLabel] + volume.Attributes = map[string]string{strings.ToLower(ClusterIDLabel): clusterID} if pv.Status.Phase == v1.VolumeReleased { // Set only status in case of delete operation volume.Attributes[VolumeStatus] = VolumeStatusDeleted @@ -217,9 +266,9 @@ func (pvw *PVWatcher) getVolume(pv *v1.PersistentVolume, ctxLogger *zap.Logger) volume.Tags = tags //Get Capacity and convert to GiB capacity := pv.Spec.Capacity[v1.ResourceStorage] - capacityGiB := utils.BytesToGiB(capacity.Value()) + capacityGiB := BytesToGiB(capacity.Value()) volume.Capacity = &capacityGiB - iops := pv.Spec.CSI.VolumeAttributes[utils.IOPSLabel] + iops := pv.Spec.CSI.VolumeAttributes[IOPSLabel] volume.Iops = &iops volume.Attributes[VolumeStatus] = VolumeStatusCreated } @@ -237,3 +286,48 @@ func (pvw *PVWatcher) filter(obj interface{}) bool { pvw.logger.Debug("Exit filter()", zap.Bool("provisoinerMatch", provisoinerMatch)) return provisoinerMatch } + +// BytesToGiB converts Bytes to GiB +func BytesToGiB(volumeSizeBytes int64) int { + return int(volumeSizeBytes / GiB) +} + +// GetContextLogger ... +func GetContextLogger(ctx context.Context, isDebug bool) (*zap.Logger, string) { + return GetContextLoggerWithRequestID(ctx, isDebug, nil) +} + +// GetContextLoggerWithRequestID adds existing requestID in the logger +// The Existing requestID might be coming from ControllerPublishVolume etc +func GetContextLoggerWithRequestID(ctx context.Context, isDebug bool, requestIDIn *string) (*zap.Logger, string) { + consoleDebugging := zapcore.Lock(os.Stdout) + consoleErrors := zapcore.Lock(os.Stderr) + encoderConfig := zap.NewProductionEncoderConfig() + encoderConfig.TimeKey = "ts" + encoderConfig.EncodeTime = zapcore.ISO8601TimeEncoder + traceLevel := zap.NewAtomicLevel() + if isDebug { + traceLevel.SetLevel(zap.DebugLevel) + } else { + traceLevel.SetLevel(zap.InfoLevel) + } + + core := zapcore.NewTee( + zapcore.NewCore(zapcore.NewJSONEncoder(encoderConfig), consoleDebugging, zap.LevelEnablerFunc(func(lvl zapcore.Level) bool { + return (lvl >= traceLevel.Level()) && (lvl < zapcore.ErrorLevel) + })), + zapcore.NewCore(zapcore.NewJSONEncoder(encoderConfig), consoleErrors, zap.LevelEnablerFunc(func(lvl zapcore.Level) bool { + return lvl >= zapcore.ErrorLevel + })), + ) + logger := zap.New(core, zap.AddCaller()) + // generating a unique request ID so that logs can be filter + if requestIDIn == nil { + // Generate New RequestID if not provided + uuid, _ := uid.NewV4() // #nosec G104: Attempt to randomly generate uuid + requestID := uuid.String() + requestIDIn = &requestID + } + logger = logger.With(zap.String("RequestID", *requestIDIn)) + return logger, *requestIDIn + " " +} diff --git a/vendor/modules.txt b/vendor/modules.txt index cca12c81..631e8f1d 100644 --- a/vendor/modules.txt +++ b/vendor/modules.txt @@ -10,15 +10,13 @@ github.com/IBM-Cloud/ibm-cloud-cli-sdk/common/rest github.com/IBM/go-sdk-core/v5/core # github.com/IBM/ibm-csi-common v1.1.18 ## explicit; go 1.22.0 -github.com/IBM/ibm-csi-common/pkg/ibmcloudprovider github.com/IBM/ibm-csi-common/pkg/messages github.com/IBM/ibm-csi-common/pkg/metadata github.com/IBM/ibm-csi-common/pkg/metadata/fake github.com/IBM/ibm-csi-common/pkg/metrics github.com/IBM/ibm-csi-common/pkg/mountmanager github.com/IBM/ibm-csi-common/pkg/utils -github.com/IBM/ibm-csi-common/pkg/watcher -# github.com/IBM/ibmcloud-volume-interface v1.2.6 +# github.com/IBM/ibmcloud-volume-interface v1.2.9 ## explicit; go 1.22.0 github.com/IBM/ibmcloud-volume-interface/config github.com/IBM/ibmcloud-volume-interface/lib/metrics @@ -29,7 +27,7 @@ github.com/IBM/ibmcloud-volume-interface/lib/utils/reasoncode github.com/IBM/ibmcloud-volume-interface/provider/auth github.com/IBM/ibmcloud-volume-interface/provider/iam github.com/IBM/ibmcloud-volume-interface/provider/local -# github.com/IBM/ibmcloud-volume-vpc v1.1.12 +# github.com/IBM/ibmcloud-volume-vpc v1.1.14 ## explicit; go 1.22.0 github.com/IBM/ibmcloud-volume-vpc/block/provider github.com/IBM/ibmcloud-volume-vpc/block/utils @@ -46,6 +44,7 @@ github.com/IBM/ibmcloud-volume-vpc/common/vpcclient/riaas github.com/IBM/ibmcloud-volume-vpc/common/vpcclient/vpcvolume github.com/IBM/ibmcloud-volume-vpc/iks/provider github.com/IBM/ibmcloud-volume-vpc/pkg/ibmcloudprovider +github.com/IBM/ibmcloud-volume-vpc/pkg/watcher # github.com/IBM/secret-common-lib v1.1.11 ## explicit; go 1.22.0 github.com/IBM/secret-common-lib/pkg/secret_provider