@@ -19,18 +19,19 @@ package controller
1919
2020import (
2121 "context"
22+ "errors"
2223 "fmt"
2324 "time"
2425
26+ "github.com/gophercloud/gophercloud"
27+ "github.com/gophercloud/gophercloud/openstack"
28+ "github.com/gophercloud/gophercloud/openstack/imageservice/v2/imageimport"
29+ "github.com/gophercloud/gophercloud/openstack/imageservice/v2/images"
2530 apiv1alpha1 "github.com/sovereignCloudStack/cluster-stack-provider-openstack/api/v1alpha1"
2631 "k8s.io/apimachinery/pkg/runtime"
2732 ctrl "sigs.k8s.io/controller-runtime"
2833 "sigs.k8s.io/controller-runtime/pkg/client"
2934 "sigs.k8s.io/controller-runtime/pkg/log"
30- "github.com/gophercloud/gophercloud"
31- "github.com/gophercloud/gophercloud/openstack"
32- "github.com/gophercloud/gophercloud/openstack/imageservice/v2/images"
33- "github.com/gophercloud/gophercloud/openstack/imageservice/v2/imageimport"
3435)
3536
3637// OpenStackNodeImageReleaseReconciler reconciles a OpenStackNodeImageRelease object.
@@ -63,24 +64,39 @@ func findImageByName(imagesClient *gophercloud.ServiceClient, imageName string)
6364}
6465
6566func waitForImageActive (client * gophercloud.ServiceClient , imageID string , interval time.Duration , timeout time.Duration ) (bool , error ) {
66- startTime := time .Now ()
67-
68- for {
69- image , err := images .Get (client , imageID ).Extract ()
70- if err != nil {
71- return false , err
72- }
73-
74- if image .Status == "active" {
75- return true , nil
76- }
67+ type result struct {
68+ IsAvailable bool
69+ Err error
70+ }
7771
78- if time .Since (startTime ) > timeout {
79- return false , fmt .Errorf ("Timeout waiting for image to become active" )
72+ ticker := time .Tick (interval )
73+ waiter := time .Tick (timeout )
74+
75+ resultChannel := make (chan result )
76+
77+ go func () {
78+ for {
79+ select {
80+ case _ = <- waiter :
81+ resultChannel <- result {IsAvailable : false , Err : errors .New ("Timeout waiting for image to become active" )}
82+ return
83+ case _ = <- ticker :
84+ image , err := images .Get (client , imageID ).Extract ()
85+ if err != nil {
86+ resultChannel <- result {IsAvailable : false , Err : err }
87+ return
88+ }
89+
90+ if image .Status == "active" {
91+ resultChannel <- result {IsAvailable : true , Err : nil }
92+ return
93+ }
94+ }
8095 }
96+ }()
8197
82- time . Sleep ( interval )
83- }
98+ resultStruct := <- resultChannel
99+ return resultStruct . IsAvailable , resultStruct . Err
84100}
85101
86102func createImage (imageClient * gophercloud.ServiceClient , createOpts images.CreateOpts ) (* images.Image , error ) {
@@ -170,25 +186,25 @@ func (r *OpenStackNodeImageReleaseReconciler) Reconcile(ctx context.Context, req
170186 } else {
171187 if imageID == "" {
172188 visibility := images .ImageVisibilityShared
173-
189+
174190 createOptsImage := images.CreateOpts {
175191 Name : imageName ,
176- ContainerFormat : "bare" ,
192+ ContainerFormat : "bare" ,
177193 DiskFormat : "iso" ,
178- Visibility : & visibility ,
194+ Visibility : & visibility ,
179195 }
180-
196+
181197 image , err := createImage (imageClient , createOptsImage )
182198 if err != nil {
183199 return ctrl.Result {}, err
184200 }
185-
201+
186202 createOpts := imageimport.CreateOpts {
187203 Name : imageimport .WebDownloadMethod ,
188204 URI : imageURL ,
189205 }
190206 imageID = image .ID
191-
207+
192208 // Handle error during image import
193209 err = importImage (imageClient , image .ID , createOpts )
194210 if err != nil {
0 commit comments