Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 5 additions & 0 deletions pkg/ingress/config/config.go
Original file line number Diff line number Diff line change
Expand Up @@ -62,4 +62,9 @@ type octaviaConfig struct {
// the load balancer instead of the bulk update API call.
// Default is false.
ProviderRequiresSerialAPICalls bool `mapstructure:"provider-requires-serial-api-calls"`

// (Optional) If the provider requires nodeports for accessing the nodes or allows usage
// of `allocateLoadBalancerNodePorts=false`
// Default is true.
ProviderRequiresNodeports bool `mapstructure:"provider-requires-nodeports"`
}
15 changes: 13 additions & 2 deletions pkg/openstack/loadbalancer.go
Original file line number Diff line number Diff line change
Expand Up @@ -1033,10 +1033,21 @@ func (lbaas *LbaasV2) buildBatchUpdateMemberOpts(ctx context.Context, port corev
memberSubnetID = nil
}

if port.NodePort != 0 { // It's 0 when AllocateLoadBalancerNodePorts=False
var protoPort int32
if !lbaas.opts.ProviderRequiresNodeports {
protoPort = port.Port
} else {
if port.NodePort != 0 { // It's 0 when AllocateLoadBalancerNodePorts=False
protoPort = port.NodePort
}
}

// protoPort set when provider doesn't require nodePorts (and e.g. AllocateLoadBalancerNodePorts=false)
// or when NodePort is set
if protoPort > 0 {
member := v2pools.BatchUpdateMemberOpts{
Address: addr,
ProtocolPort: int(port.NodePort),
ProtocolPort: int(protoPort),
Name: &node.Name,
SubnetID: memberSubnetID,
}
Expand Down
34 changes: 32 additions & 2 deletions pkg/openstack/loadbalancer_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -3,11 +3,12 @@ package openstack
import (
"context"
"fmt"
"k8s.io/utils/ptr"
"reflect"
"sort"
"testing"

"k8s.io/utils/ptr"

"github.com/gophercloud/gophercloud/v2"
"github.com/gophercloud/gophercloud/v2/openstack/loadbalancer/v2/listeners"
v2monitors "github.com/gophercloud/gophercloud/v2/openstack/loadbalancer/v2/monitors"
Expand Down Expand Up @@ -1905,11 +1906,17 @@ func TestBuildBatchUpdateMemberOpts(t *testing.T) {
},
},
}

defaultLBaasOpts := LoadBalancerOpts{
ProviderRequiresNodeports: true,
}

testCases := []struct {
name string
nodes []*corev1.Node
port corev1.ServicePort
svcConf *serviceConfig
lbOpts *LoadBalancerOpts
expectedLen int
expectedNewMembersCount int
}{
Expand All @@ -1925,6 +1932,21 @@ func TestBuildBatchUpdateMemberOpts(t *testing.T) {
expectedLen: 0,
expectedNewMembersCount: 0,
},
{
name: "NodesPortequalszero, providerRequiresNodeports=false",
nodes: []*corev1.Node{node1, node2},
port: corev1.ServicePort{NodePort: 0, Port: 80},
svcConf: &serviceConfig{
preferredIPFamily: corev1.IPv4Protocol,
lbMemberSubnetID: "subnet-12345-test",
healthCheckNodePort: 8081,
},
lbOpts: &LoadBalancerOpts{
ProviderRequiresNodeports: false,
},
expectedLen: 2,
expectedNewMembersCount: 2,
},
{
name: "Valid nodes, canUseHTTPMonitor=false",
nodes: []*corev1.Node{node1, node2},
Expand Down Expand Up @@ -1987,7 +2009,15 @@ func TestBuildBatchUpdateMemberOpts(t *testing.T) {

for _, tc := range testCases {
t.Run(tc.name, func(t *testing.T) {
lbaas := &LbaasV2{}
lbaas := &LbaasV2{
LoadBalancer: LoadBalancer{
opts: defaultLBaasOpts,
},
}
// overwrite default options
if tc.lbOpts != nil {
lbaas.opts = *tc.lbOpts
}
members, newMembers, err := lbaas.buildBatchUpdateMemberOpts(context.TODO(), tc.port, tc.nodes, tc.svcConf)
assert.Len(t, members, tc.expectedLen)
assert.NoError(t, err)
Expand Down
2 changes: 2 additions & 0 deletions pkg/openstack/openstack.go
Original file line number Diff line number Diff line change
Expand Up @@ -120,6 +120,7 @@ type LoadBalancerOpts struct {
MaxSharedLB int `gcfg:"max-shared-lb"` // Number of Services in maximum can share a single load balancer. Default 2
ContainerStore string `gcfg:"container-store"` // Used to specify the store of the tls-container-ref
ProviderRequiresSerialAPICalls bool `gcfg:"provider-requires-serial-api-calls"` // default false, the provider supports the "bulk update" API call
ProviderRequiresNodeports bool `gcfg:"provider-requires-nodeports"` // default true, the provider requires nodeports for accessing nodes
// revive:disable:var-naming
TlsContainerRef string `gcfg:"default-tls-container-ref"` // reference to a tls container
// revive:enable:var-naming
Expand Down Expand Up @@ -227,6 +228,7 @@ func ReadConfig(config io.Reader) (Config, error) {
cfg.LoadBalancer.ContainerStore = "barbican"
cfg.LoadBalancer.MaxSharedLB = 2
cfg.LoadBalancer.ProviderRequiresSerialAPICalls = false
cfg.LoadBalancer.ProviderRequiresNodeports = true

err := gcfg.FatalOnly(gcfg.ReadInto(&cfg, config))
if err != nil {
Expand Down