Skip to content

Commit 944b265

Browse files
authored
Merge pull request #1200 from apricote/loadbalancer-pending-update-fails-cluster
🐛 always wait for active Loadbalancer after getOrCreate
2 parents 8890189 + 912eafe commit 944b265

File tree

2 files changed

+58
-23
lines changed

2 files changed

+58
-23
lines changed

pkg/cloud/services/loadbalancer/loadbalancer.go

Lines changed: 2 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -58,8 +58,8 @@ func (s *Service) ReconcileLoadBalancer(openStackCluster *infrav1.OpenStackClust
5858
if err != nil {
5959
return err
6060
}
61-
if lb.ProvisioningStatus != loadBalancerProvisioningStatusActive {
62-
return fmt.Errorf("load balancer %q is not in expected state %s, current state is %s", lb.ID, loadBalancerProvisioningStatusActive, lb.ProvisioningStatus)
61+
if err := s.waitForLoadBalancerActive(lb.ID); err != nil {
62+
return fmt.Errorf("load balancer %q with id %s is not active after timeout: %v", loadBalancerName, lb.ID, err)
6363
}
6464

6565
var lbFloatingIP string
@@ -133,11 +133,6 @@ func (s *Service) getOrCreateLoadBalancer(openStackCluster *infrav1.OpenStackClu
133133
return nil, err
134134
}
135135

136-
if err := s.waitForLoadBalancerActive(lb.ID); err != nil {
137-
record.Warnf(openStackCluster, "FailedCreateLoadBalancer", "Failed to create load balancer %s with id %s: wait for load balancer active: %v", loadBalancerName, lb.ID, err)
138-
return nil, err
139-
}
140-
141136
record.Eventf(openStackCluster, "SuccessfulCreateLoadBalancer", "Created load balancer %s with id %s", loadBalancerName, lb.ID)
142137
return lb, nil
143138
}

pkg/cloud/services/loadbalancer/loadbalancer_test.go

Lines changed: 56 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -17,12 +17,14 @@ limitations under the License.
1717
package loadbalancer
1818

1919
import (
20-
"fmt"
2120
"testing"
2221

2322
"github.com/go-logr/logr"
2423
"github.com/golang/mock/gomock"
24+
"github.com/gophercloud/gophercloud/openstack/loadbalancer/v2/listeners"
2525
"github.com/gophercloud/gophercloud/openstack/loadbalancer/v2/loadbalancers"
26+
"github.com/gophercloud/gophercloud/openstack/loadbalancer/v2/monitors"
27+
"github.com/gophercloud/gophercloud/openstack/loadbalancer/v2/pools"
2628
. "github.com/onsi/gomega"
2729

2830
infrav1 "sigs.k8s.io/cluster-api-provider-openstack/api/v1alpha5"
@@ -35,16 +37,21 @@ func Test_ReconcileLoadBalancer(t *testing.T) {
3537
mockCtrl := gomock.NewController(t)
3638
defer mockCtrl.Finish()
3739

38-
openStackCluster := &infrav1.OpenStackCluster{Status: infrav1.OpenStackClusterStatus{
39-
ExternalNetwork: &infrav1.Network{
40-
ID: "aaaaaaaa-bbbb-cccc-dddd-111111111111",
40+
openStackCluster := &infrav1.OpenStackCluster{
41+
Spec: infrav1.OpenStackClusterSpec{
42+
DisableAPIServerFloatingIP: true,
4143
},
42-
Network: &infrav1.Network{
43-
Subnet: &infrav1.Subnet{
44-
ID: "aaaaaaaa-bbbb-cccc-dddd-222222222222",
44+
Status: infrav1.OpenStackClusterStatus{
45+
ExternalNetwork: &infrav1.Network{
46+
ID: "aaaaaaaa-bbbb-cccc-dddd-111111111111",
47+
},
48+
Network: &infrav1.Network{
49+
Subnet: &infrav1.Subnet{
50+
ID: "aaaaaaaa-bbbb-cccc-dddd-222222222222",
51+
},
4552
},
4653
},
47-
}}
54+
}
4855
type serviceFields struct {
4956
projectID string
5057
networkingClient *mock_networking.MockNetworkClient
@@ -59,7 +66,7 @@ func Test_ReconcileLoadBalancer(t *testing.T) {
5966
wantError error
6067
}{
6168
{
62-
name: "reconcile loadbalancer in non active state should should cause error",
69+
name: "reconcile loadbalancer in non active state should wait for active state",
6370
prepareServiceMock: func(sf *serviceFields) {
6471
sf.networkingClient = mock_networking.NewMockNetworkClient(mockCtrl)
6572
sf.loadbalancerClient = mock_loadbalancer.NewMockLbClient(mockCtrl)
@@ -68,17 +75,46 @@ func Test_ReconcileLoadBalancer(t *testing.T) {
6875
// add network api call results here
6976
},
7077
expectLoadBalancer: func(m *mock_loadbalancer.MockLbClientMockRecorder) {
78+
pendingLB := loadbalancers.LoadBalancer{
79+
ID: "aaaaaaaa-bbbb-cccc-dddd-333333333333",
80+
Name: "k8s-clusterapi-cluster-AAAAA-kubeapi",
81+
ProvisioningStatus: "PENDING_CREATE",
82+
}
83+
activeLB := pendingLB
84+
activeLB.ProvisioningStatus = "ACTIVE"
85+
7186
// return existing loadbalancer in non-active state
72-
lbList := []loadbalancers.LoadBalancer{
87+
lbList := []loadbalancers.LoadBalancer{pendingLB}
88+
m.ListLoadBalancers(loadbalancers.ListOpts{Name: pendingLB.Name}).Return(lbList, nil)
89+
90+
// wait for active loadbalancer by returning active loadbalancer on second call
91+
m.GetLoadBalancer("aaaaaaaa-bbbb-cccc-dddd-333333333333").Return(&pendingLB, nil).Return(&activeLB, nil)
92+
93+
listenerList := []listeners.Listener{
94+
{
95+
ID: "aaaaaaaa-bbbb-cccc-dddd-444444444444",
96+
Name: "k8s-clusterapi-cluster-AAAAA-kubeapi-0",
97+
},
98+
}
99+
m.ListListeners(listeners.ListOpts{Name: listenerList[0].Name}).Return(listenerList, nil)
100+
101+
poolList := []pools.Pool{
102+
{
103+
ID: "aaaaaaaa-bbbb-cccc-dddd-555555555555",
104+
Name: "k8s-clusterapi-cluster-AAAAA-kubeapi-0",
105+
},
106+
}
107+
m.ListPools(pools.ListOpts{Name: poolList[0].Name}).Return(poolList, nil)
108+
109+
monitorList := []monitors.Monitor{
73110
{
74-
ID: "aaaaaaaa-bbbb-cccc-dddd-333333333333",
75-
Name: "k8s-clusterapi-cluster-AAAAA-kubeapi",
76-
ProvisioningStatus: "PENDING_CREATE",
111+
ID: "aaaaaaaa-bbbb-cccc-dddd-666666666666",
112+
Name: "k8s-clusterapi-cluster-AAAAA-kubeapi-0",
77113
},
78114
}
79-
m.ListLoadBalancers(loadbalancers.ListOpts{Name: "k8s-clusterapi-cluster-AAAAA-kubeapi"}).Return(lbList, nil)
115+
m.ListMonitors(monitors.ListOpts{Name: monitorList[0].Name}).Return(monitorList, nil)
80116
},
81-
wantError: fmt.Errorf("load balancer %q is not in expected state %s, current state is %s", "aaaaaaaa-bbbb-cccc-dddd-333333333333", "ACTIVE", "PENDING_CREATE"),
117+
wantError: nil,
82118
},
83119
}
84120
for _, tt := range lbtests {
@@ -90,7 +126,11 @@ func Test_ReconcileLoadBalancer(t *testing.T) {
90126
tt.expectNetwork(tt.fields.networkingClient.EXPECT())
91127
tt.expectLoadBalancer(tt.fields.loadbalancerClient.EXPECT())
92128
err := lbs.ReconcileLoadBalancer(openStackCluster, "AAAAA", 0)
93-
g.Expect(err).To(MatchError(tt.wantError))
129+
if tt.wantError != nil {
130+
g.Expect(err).To(MatchError(tt.wantError))
131+
} else {
132+
g.Expect(err).NotTo(HaveOccurred())
133+
}
94134
})
95135
}
96136
}

0 commit comments

Comments
 (0)