Skip to content

Commit

Permalink
feat(occm): load balancing algorithm via annotation (#2684)
Browse files Browse the repository at this point in the history
  • Loading branch information
Lucasgranet authored Nov 20, 2024
1 parent 88f6478 commit b461771
Show file tree
Hide file tree
Showing 4 changed files with 65 additions and 2 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -152,6 +152,14 @@ Request Body:

Not supported when `lb-provider=ovn` is configured in openstack-cloud-controller-manager.

- `loadbalancer.openstack.org/lb-method`

Load balancing algorithm to use when distributed to members. [OpenStack Pool Creation | lb_algorithm](https://docs.openstack.org/api-ref/load-balancer/v2/#create-pool)

Default value: defined in your OCCM configuration

Possible values: `ROUND_ROBIN`, `LEAST_CONNECTIONS`, `SOURCE_IP`, `SOURCE_IP_PORT`

- `loadbalancer.openstack.org/timeout-client-data`

Frontend client inactivity timeout in milliseconds for the load balancer.
Expand Down
1 change: 1 addition & 0 deletions pkg/openstack/events.go
Original file line number Diff line number Diff line change
Expand Up @@ -23,4 +23,5 @@ const (
eventLBAZIgnored = "LoadBalancerAvailabilityZonesIgnored"
eventLBFloatingIPSkipped = "LoadBalancerFloatingIPSkipped"
eventLBRename = "LoadBalancerRename"
eventLBLbMethodUnknown = "LoadBalancerLbMethodUnknown"
)
35 changes: 33 additions & 2 deletions pkg/openstack/loadbalancer.go
Original file line number Diff line number Diff line change
Expand Up @@ -68,6 +68,7 @@ const (
ServiceAnnotationLoadBalancerClass = "loadbalancer.openstack.org/class"
ServiceAnnotationLoadBalancerKeepFloatingIP = "loadbalancer.openstack.org/keep-floatingip"
ServiceAnnotationLoadBalancerPortID = "loadbalancer.openstack.org/port-id"
ServiceAnnotationLoadBalancerLbMethod = "loadbalancer.openstack.org/lb-method"
ServiceAnnotationLoadBalancerProxyEnabled = "loadbalancer.openstack.org/proxy-protocol"
ServiceAnnotationLoadBalancerSubnetID = "loadbalancer.openstack.org/subnet-id"
ServiceAnnotationLoadBalancerNetworkID = "loadbalancer.openstack.org/network-id"
Expand Down Expand Up @@ -125,6 +126,7 @@ type serviceConfig struct {
lbPublicSubnetSpec *floatingSubnetSpec
nodeSelectors map[string]string
keepClientIP bool
poolLbMethod string
proxyProtocolVersion *v2pools.Protocol
timeoutClientData int
timeoutMemberConnect int
Expand Down Expand Up @@ -900,6 +902,27 @@ func (lbaas *LbaasV2) ensureOctaviaPool(lbID string, name string, listener *list
pool = nil
}

// If LBMethod changes, update the Pool with the new value
var poolLbMethod string
if svcConf.poolLbMethod != "" {
poolLbMethod = svcConf.poolLbMethod
} else {
// if LBMethod is not defined, fallback on default OCCM's default method
poolLbMethod = lbaas.opts.LBMethod
}
if pool != nil && pool.LBMethod != poolLbMethod {
klog.InfoS("Updating LoadBalancer LBMethod", "poolID", pool.ID, "listenerID", listener.ID, "lbID", lbID)
err = openstackutil.UpdatePool(lbaas.lb, lbID, pool.ID, v2pools.UpdateOpts{LBMethod: v2pools.LBMethod(poolLbMethod)})
if err != nil {
err = PreserveGopherError(err)
msg := fmt.Sprintf("Error updating LB method for LoadBalancer: %v", err)
klog.Errorf(msg, "poolID", pool.ID, "listenerID", listener.ID, "lbID", lbID)
lbaas.eventRecorder.Eventf(service, corev1.EventTypeWarning, eventLBLbMethodUnknown, msg)
} else {
pool.LBMethod = poolLbMethod
}
}

if pool == nil {
createOpt := lbaas.buildPoolCreateOpt(listener.Protocol, service, svcConf, name)
createOpt.ListenerID = listener.ID
Expand Down Expand Up @@ -972,11 +995,18 @@ func (lbaas *LbaasV2) buildPoolCreateOpt(listenerProtocol string, service *corev
persistence = &v2pools.SessionPersistence{Type: "SOURCE_IP"}
}

lbmethod := v2pools.LBMethod(lbaas.opts.LBMethod)
var lbMethod v2pools.LBMethod
if svcConf.poolLbMethod != "" {
lbMethod = v2pools.LBMethod(svcConf.poolLbMethod)
} else {
// if LBMethod is not defined, fallback on default OCCM's default method
lbMethod = v2pools.LBMethod(lbaas.opts.LBMethod)
}

return v2pools.CreateOpts{
Name: name,
Protocol: poolProto,
LBMethod: lbmethod,
LBMethod: lbMethod,
Persistence: persistence,
}
}
Expand Down Expand Up @@ -1509,6 +1539,7 @@ func (lbaas *LbaasV2) checkService(ctx context.Context, service *corev1.Service,
func (lbaas *LbaasV2) makeSvcConf(serviceName string, service *corev1.Service, svcConf *serviceConfig) error {
svcConf.connLimit = getIntFromServiceAnnotation(service, ServiceAnnotationLoadBalancerConnLimit, -1)
svcConf.lbID = getStringFromServiceAnnotation(service, ServiceAnnotationLoadBalancerID, "")
svcConf.poolLbMethod = getStringFromServiceAnnotation(service, ServiceAnnotationLoadBalancerLbMethod, "")
svcConf.supportLBTags = openstackutil.IsOctaviaFeatureSupported(lbaas.lb, openstackutil.OctaviaFeatureTags, lbaas.opts.LBProvider)

// Get service node-selector annotations
Expand Down
23 changes: 23 additions & 0 deletions pkg/openstack/loadbalancer_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -1155,6 +1155,29 @@ func Test_buildPoolCreateOpt(t *testing.T) {
Persistence: &pools.SessionPersistence{Type: "SOURCE_IP"},
},
},
{
name: "test for loadbalancing method",
args: args{
protocol: "TCP",
svcConf: &serviceConfig{
poolLbMethod: "ROUND_ROBIN",
},
lbaasV2: &LbaasV2{
LoadBalancer{
opts: LoadBalancerOpts{
LBProvider: "ovn",
LBMethod: "SOURCE_IP_PORT",
},
},
},
service: &corev1.Service{},
},
want: pools.CreateOpts{
Name: "test for loadbalancing method",
Protocol: pools.ProtocolTCP,
LBMethod: "ROUND_ROBIN",
},
},
}

for _, tt := range tests {
Expand Down

0 comments on commit b461771

Please sign in to comment.