From 005b2e2f22db4a68df9e0bb78bf74e0de0e6e93d Mon Sep 17 00:00:00 2001 From: Tom Proctor Date: Sat, 28 Sep 2024 20:59:49 +0100 Subject: [PATCH] Comparable struct as map key --- cmd/containerboot/services.go | 18 +++++++++--------- cmd/containerboot/services_test.go | 8 ++++---- kube/egressservices/egressservices.go | 7 ++----- 3 files changed, 15 insertions(+), 18 deletions(-) diff --git a/cmd/containerboot/services.go b/cmd/containerboot/services.go index b9c2cd45f..a3d7cdad2 100644 --- a/cmd/containerboot/services.go +++ b/cmd/containerboot/services.go @@ -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 !ok { for _, t := range tailnetTargetIPs { - for _, ports := range cfg.Ports { + for ports := range cfg.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}) } @@ -238,7 +238,7 @@ func updatesForCfg(svcName string, cfg egressservices.Config, status *egressserv if len(tailnetTargetIPs) == 0 { log.Printf("tailnet target for egress service %s does not have any backend addresses, deleting all rules", svcName) 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}) } } @@ -255,7 +255,7 @@ func updatesForCfg(svcName string, cfg egressservices.Config, status *egressserv } } 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}) } } @@ -273,7 +273,7 @@ func updatesForCfg(svcName string, cfg egressservices.Config, status *egressserv } } 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}) } continue @@ -283,16 +283,16 @@ func updatesForCfg(svcName string, cfg egressservices.Config, status *egressserv // currently applied rules are up to date. // Delete any current portmappings that are no longer present in config. - for portName, port := range currentConfig.Ports { - if _, ok := cfg.Ports[portName]; ok { + for port := range currentConfig.Ports { + if _, ok := cfg.Ports[port]; ok { continue } rulesToDelete = append(rulesToDelete, rule{tailnetPort: port.TargetPort, containerPort: port.MatchPort, protocol: port.Protocol, tailnetIP: ip}) } // Add any new portmappings. - for portName, port := range cfg.Ports { - if _, ok := currentConfig.Ports[portName]; ok { + for port := range cfg.Ports { + if _, ok := currentConfig.Ports[port]; ok { continue } 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 // specify individual portmapping based rules. 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}) } diff --git a/cmd/containerboot/services_test.go b/cmd/containerboot/services_test.go index e32515589..46f6db1cf 100644 --- a/cmd/containerboot/services_test.go +++ b/cmd/containerboot/services_test.go @@ -16,10 +16,10 @@ func Test_updatesForSvc(t *testing.T) { 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") - ports := map[egressservices.PortMapName]egressservices.PortMap{"tcp:4003:80": {Protocol: "tcp", MatchPort: 4003, TargetPort: 80}} - ports1 := map[egressservices.PortMapName]egressservices.PortMap{"udp:4004:53": {Protocol: "udp", MatchPort: 4004, TargetPort: 53}} - ports2 := map[egressservices.PortMapName]egressservices.PortMap{"tcp:4003:80": {Protocol: "tcp", MatchPort: 4003, TargetPort: 80}, - "tcp:4005:443": {Protocol: "tcp", MatchPort: 4005, TargetPort: 443}} + ports := map[egressservices.PortMap]struct{}{{Protocol: "tcp", MatchPort: 4003, TargetPort: 80}: {}} + ports1 := map[egressservices.PortMap]struct{}{{Protocol: "udp", MatchPort: 4004, TargetPort: 53}: {}} + ports2 := map[egressservices.PortMap]struct{}{{Protocol: "tcp", MatchPort: 4003, TargetPort: 80}: {}, + {Protocol: "tcp", MatchPort: 4005, TargetPort: 443}: {}} fqdnSpec := egressservices.Config{ TailnetTarget: egressservices.TailnetTarget{FQDN: "test"}, Ports: ports, diff --git a/kube/egressservices/egressservices.go b/kube/egressservices/egressservices.go index 90f7e43ab..1cf6e3990 100644 --- a/kube/egressservices/egressservices.go +++ b/kube/egressservices/egressservices.go @@ -28,7 +28,7 @@ type Config struct { // Ports contains mappings for ports that can be accessed on the tailnet // target keyed by a predictable name for easier lookup. // {"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 @@ -49,9 +49,6 @@ type PortMap struct { TargetPort uint16 `json:"targetPort"` } -// PortMapName is a name of a port mapping in form '::'. -type PortMapName string - // Status represents the currently configured firewall rules for all egress // services for a proxy identified by the PodIP. type Status struct { @@ -63,7 +60,7 @@ type Status struct { // ServiceStatus is the currently configured firewall rules for an egress // service. 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 // configure these firewall rules. For a TailnetTarget with IP set, this // is the same as IP.