Comparable struct as map key

This commit is contained in:
Tom Proctor 2024-09-28 20:59:49 +01:00
parent c8d3e16e1d
commit 005b2e2f22
3 changed files with 15 additions and 18 deletions

View File

@ -226,7 +226,7 @@ func updatesForCfg(svcName string, cfg egressservices.Config, status *egressserv
// If no rules for service are present yet, add them all. // If no rules for service are present yet, add them all.
if !ok { if !ok {
for _, t := range tailnetTargetIPs { for _, t := range tailnetTargetIPs {
for _, ports := range cfg.Ports { for ports := range cfg.Ports {
log.Printf("syncegressservices: svc %s adding port %v", svcName, ports) log.Printf("syncegressservices: svc %s adding port %v", svcName, ports)
rulesToAdd = append(rulesToAdd, rule{tailnetPort: ports.TargetPort, containerPort: ports.MatchPort, protocol: ports.Protocol, tailnetIP: t}) rulesToAdd = append(rulesToAdd, rule{tailnetPort: ports.TargetPort, containerPort: ports.MatchPort, protocol: ports.Protocol, tailnetIP: t})
} }
@ -238,7 +238,7 @@ func updatesForCfg(svcName string, cfg egressservices.Config, status *egressserv
if len(tailnetTargetIPs) == 0 { if len(tailnetTargetIPs) == 0 {
log.Printf("tailnet target for egress service %s does not have any backend addresses, deleting all rules", svcName) log.Printf("tailnet target for egress service %s does not have any backend addresses, deleting all rules", svcName)
for _, ip := range currentConfig.TailnetTargetIPs { for _, ip := range currentConfig.TailnetTargetIPs {
for _, ports := range currentConfig.Ports { for ports := range currentConfig.Ports {
rulesToDelete = append(rulesToAdd, rule{tailnetPort: ports.TargetPort, containerPort: ports.MatchPort, protocol: ports.Protocol, tailnetIP: ip}) rulesToDelete = append(rulesToAdd, rule{tailnetPort: ports.TargetPort, containerPort: ports.MatchPort, protocol: ports.Protocol, tailnetIP: ip})
} }
} }
@ -255,7 +255,7 @@ func updatesForCfg(svcName string, cfg egressservices.Config, status *egressserv
} }
} }
if !found { if !found {
for _, ports := range currentConfig.Ports { for ports := range currentConfig.Ports {
rulesToDelete = append(rulesToDelete, rule{tailnetPort: ports.TargetPort, containerPort: ports.MatchPort, protocol: ports.Protocol, tailnetIP: ip}) rulesToDelete = append(rulesToDelete, rule{tailnetPort: ports.TargetPort, containerPort: ports.MatchPort, protocol: ports.Protocol, tailnetIP: ip})
} }
} }
@ -273,7 +273,7 @@ func updatesForCfg(svcName string, cfg egressservices.Config, status *egressserv
} }
} }
if !found { if !found {
for _, ports := range cfg.Ports { for ports := range cfg.Ports {
rulesToAdd = append(rulesToAdd, rule{tailnetPort: ports.TargetPort, containerPort: ports.MatchPort, protocol: ports.Protocol, tailnetIP: ip}) rulesToAdd = append(rulesToAdd, rule{tailnetPort: ports.TargetPort, containerPort: ports.MatchPort, protocol: ports.Protocol, tailnetIP: ip})
} }
continue continue
@ -283,16 +283,16 @@ func updatesForCfg(svcName string, cfg egressservices.Config, status *egressserv
// currently applied rules are up to date. // currently applied rules are up to date.
// Delete any current portmappings that are no longer present in config. // Delete any current portmappings that are no longer present in config.
for portName, port := range currentConfig.Ports { for port := range currentConfig.Ports {
if _, ok := cfg.Ports[portName]; ok { if _, ok := cfg.Ports[port]; ok {
continue continue
} }
rulesToDelete = append(rulesToDelete, rule{tailnetPort: port.TargetPort, containerPort: port.MatchPort, protocol: port.Protocol, tailnetIP: ip}) rulesToDelete = append(rulesToDelete, rule{tailnetPort: port.TargetPort, containerPort: port.MatchPort, protocol: port.Protocol, tailnetIP: ip})
} }
// Add any new portmappings. // Add any new portmappings.
for portName, port := range cfg.Ports { for port := range cfg.Ports {
if _, ok := currentConfig.Ports[portName]; ok { if _, ok := currentConfig.Ports[port]; ok {
continue continue
} }
rulesToAdd = append(rulesToAdd, rule{tailnetPort: port.TargetPort, containerPort: port.MatchPort, protocol: port.Protocol, tailnetIP: ip}) rulesToAdd = append(rulesToAdd, rule{tailnetPort: port.TargetPort, containerPort: port.MatchPort, protocol: port.Protocol, tailnetIP: ip})
@ -477,7 +477,7 @@ func ensureServiceDeleted(svcName string, svc *egressservices.ServiceStatus, nfr
// Nftables group rules for a service in a chain, so there is no need to // Nftables group rules for a service in a chain, so there is no need to
// specify individual portmapping based rules. // specify individual portmapping based rules.
pms := make([]linuxfw.PortMap, 0) pms := make([]linuxfw.PortMap, 0)
for _, pm := range svc.Ports { for pm := range svc.Ports {
pms = append(pms, linuxfw.PortMap{MatchPort: pm.MatchPort, TargetPort: pm.TargetPort, Protocol: pm.Protocol}) pms = append(pms, linuxfw.PortMap{MatchPort: pm.MatchPort, TargetPort: pm.TargetPort, Protocol: pm.Protocol})
} }

View File

@ -16,10 +16,10 @@
func Test_updatesForSvc(t *testing.T) { func Test_updatesForSvc(t *testing.T) {
tailnetIPv4, tailnetIPv6 := netip.MustParseAddr("100.99.99.99"), netip.MustParseAddr("fd7a:115c:a1e0::701:b62a") tailnetIPv4, tailnetIPv6 := netip.MustParseAddr("100.99.99.99"), netip.MustParseAddr("fd7a:115c:a1e0::701:b62a")
tailnetIPv4_1, tailnetIPv6_1 := netip.MustParseAddr("100.88.88.88"), netip.MustParseAddr("fd7a:115c:a1e0::4101:512f") tailnetIPv4_1, tailnetIPv6_1 := netip.MustParseAddr("100.88.88.88"), netip.MustParseAddr("fd7a:115c:a1e0::4101:512f")
ports := map[egressservices.PortMapName]egressservices.PortMap{"tcp:4003:80": {Protocol: "tcp", MatchPort: 4003, TargetPort: 80}} ports := map[egressservices.PortMap]struct{}{{Protocol: "tcp", MatchPort: 4003, TargetPort: 80}: {}}
ports1 := map[egressservices.PortMapName]egressservices.PortMap{"udp:4004:53": {Protocol: "udp", MatchPort: 4004, TargetPort: 53}} ports1 := map[egressservices.PortMap]struct{}{{Protocol: "udp", MatchPort: 4004, TargetPort: 53}: {}}
ports2 := map[egressservices.PortMapName]egressservices.PortMap{"tcp:4003:80": {Protocol: "tcp", MatchPort: 4003, TargetPort: 80}, ports2 := map[egressservices.PortMap]struct{}{{Protocol: "tcp", MatchPort: 4003, TargetPort: 80}: {},
"tcp:4005:443": {Protocol: "tcp", MatchPort: 4005, TargetPort: 443}} {Protocol: "tcp", MatchPort: 4005, TargetPort: 443}: {}}
fqdnSpec := egressservices.Config{ fqdnSpec := egressservices.Config{
TailnetTarget: egressservices.TailnetTarget{FQDN: "test"}, TailnetTarget: egressservices.TailnetTarget{FQDN: "test"},
Ports: ports, Ports: ports,

View File

@ -28,7 +28,7 @@ type Config struct {
// Ports contains mappings for ports that can be accessed on the tailnet // Ports contains mappings for ports that can be accessed on the tailnet
// target keyed by a predictable name for easier lookup. // target keyed by a predictable name for easier lookup.
// {"tcp:80:4003":{"protocol":"tcp","src":80,"dst":4003}} // {"tcp:80:4003":{"protocol":"tcp","src":80,"dst":4003}}
Ports map[PortMapName]PortMap `json:"ports"` Ports map[PortMap]struct{} `json:"ports"`
} }
// TailnetTarget is the tailnet target to which traffic for the egress service // TailnetTarget is the tailnet target to which traffic for the egress service
@ -49,9 +49,6 @@ type PortMap struct {
TargetPort uint16 `json:"targetPort"` TargetPort uint16 `json:"targetPort"`
} }
// PortMapName is a name of a port mapping in form '<protocol>:<match port>:<target port>'.
type PortMapName string
// Status represents the currently configured firewall rules for all egress // Status represents the currently configured firewall rules for all egress
// services for a proxy identified by the PodIP. // services for a proxy identified by the PodIP.
type Status struct { type Status struct {
@ -63,7 +60,7 @@ type Status struct {
// ServiceStatus is the currently configured firewall rules for an egress // ServiceStatus is the currently configured firewall rules for an egress
// service. // service.
type ServiceStatus struct { type ServiceStatus struct {
Ports map[PortMapName]PortMap `json:"ports"` Ports map[PortMap]struct{} `json:"ports"`
// TailnetTargetIPs are the tailnet target IPs that were used to // TailnetTargetIPs are the tailnet target IPs that were used to
// configure these firewall rules. For a TailnetTarget with IP set, this // configure these firewall rules. For a TailnetTarget with IP set, this
// is the same as IP. // is the same as IP.