diff --git a/internal/app/machined/pkg/controllers/k8s/control_plane_static_pod_test.go b/internal/app/machined/pkg/controllers/k8s/control_plane_static_pod_test.go index 998c4d82b..33fbf42b2 100644 --- a/internal/app/machined/pkg/controllers/k8s/control_plane_static_pod_test.go +++ b/internal/app/machined/pkg/controllers/k8s/control_plane_static_pod_test.go @@ -28,6 +28,7 @@ import ( k8sctrl "github.com/talos-systems/talos/internal/app/machined/pkg/controllers/k8s" "github.com/talos-systems/talos/pkg/logging" "github.com/talos-systems/talos/pkg/machinery/constants" + "github.com/talos-systems/talos/pkg/machinery/generic/slices" "github.com/talos-systems/talos/pkg/machinery/resources/k8s" "github.com/talos-systems/talos/pkg/machinery/resources/v1alpha1" ) @@ -85,11 +86,7 @@ func (suite *ControlPlaneStaticPodSuite) assertControlPlaneStaticPods(manifests return err } - ids := make([]string, 0, len(resources.Items)) - - for _, res := range resources.Items { - ids = append(ids, res.Metadata().ID()) - } + ids := slices.Map(resources.Items, func(r resource.Resource) string { return r.Metadata().ID() }) if !reflect.DeepEqual(manifests, ids) { return retry.ExpectedError(fmt.Errorf("expected %q, got %q", manifests, ids)) diff --git a/internal/app/machined/pkg/controllers/k8s/extra_manifest_test.go b/internal/app/machined/pkg/controllers/k8s/extra_manifest_test.go index 8171f5b0d..7b81437d2 100644 --- a/internal/app/machined/pkg/controllers/k8s/extra_manifest_test.go +++ b/internal/app/machined/pkg/controllers/k8s/extra_manifest_test.go @@ -26,6 +26,7 @@ import ( k8sadapter "github.com/talos-systems/talos/internal/app/machined/pkg/adapters/k8s" k8sctrl "github.com/talos-systems/talos/internal/app/machined/pkg/controllers/k8s" "github.com/talos-systems/talos/pkg/logging" + "github.com/talos-systems/talos/pkg/machinery/generic/slices" "github.com/talos-systems/talos/pkg/machinery/resources/k8s" "github.com/talos-systems/talos/pkg/machinery/resources/network" "github.com/talos-systems/talos/pkg/machinery/resources/v1alpha1" @@ -78,11 +79,7 @@ func (suite *ExtraManifestSuite) assertExtraManifests(manifests []string) error return err } - ids := make([]string, 0, len(resources.Items)) - - for _, res := range resources.Items { - ids = append(ids, res.Metadata().ID()) - } + ids := slices.Map(resources.Items, func(r resource.Resource) string { return r.Metadata().ID() }) if !reflect.DeepEqual(manifests, ids) { return retry.ExpectedError(fmt.Errorf("expected %q, got %q", manifests, ids)) diff --git a/internal/app/machined/pkg/controllers/k8s/manifest_apply.go b/internal/app/machined/pkg/controllers/k8s/manifest_apply.go index dd061a73e..90292af86 100644 --- a/internal/app/machined/pkg/controllers/k8s/manifest_apply.go +++ b/internal/app/machined/pkg/controllers/k8s/manifest_apply.go @@ -209,11 +209,9 @@ func (ctrl *ManifestApplyController) etcdLock(ctx context.Context, logger *zap.L //nolint:gocyclo func (ctrl *ManifestApplyController) apply(ctx context.Context, logger *zap.Logger, mapper *restmapper.DeferredDiscoveryRESTMapper, dyn dynamic.Interface, manifests resource.List) error { // flatten list of objects to be applied - objects := make([]*unstructured.Unstructured, 0, len(manifests.Items)) - - for _, manifest := range manifests.Items { - objects = append(objects, k8sadapter.Manifest(manifest.(*k8s.Manifest)).Objects()...) - } + objects := slices.FlatMap(manifests.Items, func(m resource.Resource) []*unstructured.Unstructured { + return k8sadapter.Manifest(m.(*k8s.Manifest)).Objects() + }) // sort the list so that namespaces come first, followed by CRDs and everything else after that sort.SliceStable(objects, func(i, j int) bool { diff --git a/internal/app/machined/pkg/controllers/k8s/manifest_test.go b/internal/app/machined/pkg/controllers/k8s/manifest_test.go index 673379bba..9b0b107de 100644 --- a/internal/app/machined/pkg/controllers/k8s/manifest_test.go +++ b/internal/app/machined/pkg/controllers/k8s/manifest_test.go @@ -26,6 +26,7 @@ import ( k8sctrl "github.com/talos-systems/talos/internal/app/machined/pkg/controllers/k8s" "github.com/talos-systems/talos/pkg/logging" "github.com/talos-systems/talos/pkg/machinery/constants" + "github.com/talos-systems/talos/pkg/machinery/generic/slices" "github.com/talos-systems/talos/pkg/machinery/resources/k8s" "github.com/talos-systems/talos/pkg/machinery/resources/secrets" ) @@ -77,11 +78,7 @@ func (suite *ManifestSuite) assertManifests(manifests []string) error { return err } - ids := make([]string, 0, len(resources.Items)) - - for _, res := range resources.Items { - ids = append(ids, res.Metadata().ID()) - } + ids := slices.Map(resources.Items, func(r resource.Resource) string { return r.Metadata().ID() }) if !reflect.DeepEqual(manifests, ids) { return retry.ExpectedError(fmt.Errorf("expected %q, got %q", manifests, ids)) diff --git a/internal/app/machined/pkg/controllers/kubespan/kubespan_test.go b/internal/app/machined/pkg/controllers/kubespan/kubespan_test.go index 4c6e55319..d8af3c8b3 100644 --- a/internal/app/machined/pkg/controllers/kubespan/kubespan_test.go +++ b/internal/app/machined/pkg/controllers/kubespan/kubespan_test.go @@ -22,6 +22,7 @@ import ( "github.com/talos-systems/talos/pkg/logging" "github.com/talos-systems/talos/pkg/machinery/config/types/v1alpha1" + "github.com/talos-systems/talos/pkg/machinery/generic/slices" "github.com/talos-systems/talos/pkg/machinery/resources/config" ) @@ -67,11 +68,7 @@ func (suite *KubeSpanSuite) assertResourceIDs(md resource.Metadata, expectedIDs return err } - actualIDs := make([]resource.ID, 0, len(l.Items)) - - for _, r := range l.Items { - actualIDs = append(actualIDs, r.Metadata().ID()) - } + actualIDs := slices.Map(l.Items, func(r resource.Resource) string { return r.Metadata().ID() }) sort.Strings(expectedIDs) diff --git a/internal/app/machined/pkg/controllers/kubespan/peer_spec.go b/internal/app/machined/pkg/controllers/kubespan/peer_spec.go index 28fa1be57..a81dc5ddf 100644 --- a/internal/app/machined/pkg/controllers/kubespan/peer_spec.go +++ b/internal/app/machined/pkg/controllers/kubespan/peer_spec.go @@ -15,6 +15,7 @@ import ( "go.uber.org/zap" "inet.af/netaddr" + "github.com/talos-systems/talos/pkg/machinery/generic/slices" "github.com/talos-systems/talos/pkg/machinery/resources/cluster" "github.com/talos-systems/talos/pkg/machinery/resources/config" "github.com/talos-systems/talos/pkg/machinery/resources/kubespan" @@ -178,12 +179,5 @@ func (ctrl *PeerSpecController) Run(ctx context.Context, r controller.Runtime, l // dumpSet converts IPSet to a form suitable for logging. func dumpSet(set *netaddr.IPSet) []string { - ranges := set.Ranges() - res := make([]string, len(ranges)) - - for i, p := range ranges { - res[i] = p.String() - } - - return res + return slices.Map(set.Ranges(), netaddr.IPRange.String) } diff --git a/internal/app/machined/pkg/controllers/network/link_config.go b/internal/app/machined/pkg/controllers/network/link_config.go index 98463e50c..c330b6715 100644 --- a/internal/app/machined/pkg/controllers/network/link_config.go +++ b/internal/app/machined/pkg/controllers/network/link_config.go @@ -16,6 +16,7 @@ import ( "inet.af/netaddr" talosconfig "github.com/talos-systems/talos/pkg/machinery/config" + "github.com/talos-systems/talos/pkg/machinery/generic/maps" "github.com/talos-systems/talos/pkg/machinery/nethelpers" "github.com/talos-systems/talos/pkg/machinery/ordered" "github.com/talos-systems/talos/pkg/machinery/resources/network" @@ -340,13 +341,7 @@ func (ctrl *LinkConfigController) processDevicesConfiguration(logger *zap.Logger SetBondSlave(linkMap[slaveName], bondData) } - links := make([]network.LinkSpecSpec, 0, len(linkMap)) - - for _, link := range linkMap { - links = append(links, *link) - } - - return links + return maps.ValuesFunc(linkMap, func(link *network.LinkSpecSpec) network.LinkSpecSpec { return *link }) } func vlanLink(linkName string, vlan talosconfig.Vlan) network.LinkSpecSpec { diff --git a/internal/app/machined/pkg/controllers/network/link_spec_test.go b/internal/app/machined/pkg/controllers/network/link_spec_test.go index dcd8320e0..e99cf34a4 100644 --- a/internal/app/machined/pkg/controllers/network/link_spec_test.go +++ b/internal/app/machined/pkg/controllers/network/link_spec_test.go @@ -28,6 +28,7 @@ import ( networkadapter "github.com/talos-systems/talos/internal/app/machined/pkg/adapters/network" netctrl "github.com/talos-systems/talos/internal/app/machined/pkg/controllers/network" "github.com/talos-systems/talos/pkg/logging" + "github.com/talos-systems/talos/pkg/machinery/generic/slices" "github.com/talos-systems/talos/pkg/machinery/nethelpers" "github.com/talos-systems/talos/pkg/machinery/resources/network" ) @@ -800,25 +801,18 @@ func TestSortBonds(t *testing.T) { } func toResources(slice []network.LinkSpecSpec) []resource.Resource { - result := make([]resource.Resource, 0, len(slice)) - - for _, elem := range slice { + return slices.Map(slice, func(spec network.LinkSpecSpec) resource.Resource { link := network.NewLinkSpec(network.NamespaceName, "bar") - *link.TypedSpec() = elem + *link.TypedSpec() = spec - result = append(result, link) - } - - return result + return link + }) } func toSpecs(slice []resource.Resource) []network.LinkSpecSpec { - result := make([]network.LinkSpecSpec, 0, len(slice)) + return slices.Map(slice, func(r resource.Resource) network.LinkSpecSpec { + v := r.Spec().(*network.LinkSpecSpec) //nolint:errcheck - for _, elem := range slice { - v := elem.Spec().(*network.LinkSpecSpec) //nolint:errcheck - result = append(result, *v) - } - - return result + return *v + }) } diff --git a/internal/app/machined/pkg/controllers/network/operator/dhcp4.go b/internal/app/machined/pkg/controllers/network/operator/dhcp4.go index 455a6b1b0..c5cec7455 100644 --- a/internal/app/machined/pkg/controllers/network/operator/dhcp4.go +++ b/internal/app/machined/pkg/controllers/network/operator/dhcp4.go @@ -19,6 +19,7 @@ import ( "inet.af/netaddr" "github.com/talos-systems/talos/internal/app/machined/pkg/runtime" + "github.com/talos-systems/talos/pkg/machinery/generic/slices" "github.com/talos-systems/talos/pkg/machinery/nethelpers" "github.com/talos-systems/talos/pkg/machinery/resources/network" ) @@ -246,15 +247,15 @@ func (d *DHCP4) parseAck(ack *dhcpv4.DHCPv4) { } if len(ack.DNS()) > 0 { - dns := make([]netaddr.IP, len(ack.DNS())) + convertIP := func(ip net.IP) netaddr.IP { + result, _ := netaddr.FromStdIP(ip) - for i := range dns { - dns[i], _ = netaddr.FromStdIP(ack.DNS()[i]) + return result } d.resolvers = []network.ResolverSpecSpec{ { - DNSServers: dns, + DNSServers: slices.Map(ack.DNS(), convertIP), ConfigLayer: network.ConfigOperator, }, } @@ -283,16 +284,15 @@ func (d *DHCP4) parseAck(ack *dhcpv4.DHCPv4) { } if len(ack.NTPServers()) > 0 { - ntp := make([]string, len(ack.NTPServers())) + convertIP := func(ip net.IP) string { + result, _ := netaddr.FromStdIP(ip) - for i := range ntp { - ip, _ := netaddr.FromStdIP(ack.NTPServers()[i]) - ntp[i] = ip.String() + return result.String() } d.timeservers = []network.TimeServerSpecSpec{ { - NTPServers: ntp, + NTPServers: slices.Map(ack.NTPServers(), convertIP), ConfigLayer: network.ConfigOperator, }, } diff --git a/internal/app/machined/pkg/controllers/network/operator/dhcp6.go b/internal/app/machined/pkg/controllers/network/operator/dhcp6.go index 227602d7b..1786d75c5 100644 --- a/internal/app/machined/pkg/controllers/network/operator/dhcp6.go +++ b/internal/app/machined/pkg/controllers/network/operator/dhcp6.go @@ -22,6 +22,7 @@ import ( "golang.org/x/sys/unix" "inet.af/netaddr" + "github.com/talos-systems/talos/pkg/machinery/generic/slices" "github.com/talos-systems/talos/pkg/machinery/nethelpers" "github.com/talos-systems/talos/pkg/machinery/resources/network" ) @@ -172,15 +173,15 @@ func (d *DHCP6) parseReply(reply *dhcpv6.Message) (leaseTime time.Duration) { } if len(reply.Options.DNS()) > 0 { - dns := make([]netaddr.IP, len(reply.Options.DNS())) + convertIP := func(ip net.IP) netaddr.IP { + result, _ := netaddr.FromStdIP(ip) - for i := range dns { - dns[i], _ = netaddr.FromStdIP(reply.Options.DNS()[i]) + return result } d.resolvers = []network.ResolverSpecSpec{ { - DNSServers: dns, + DNSServers: slices.Map(reply.Options.DNS(), convertIP), ConfigLayer: network.ConfigOperator, }, } @@ -201,16 +202,15 @@ func (d *DHCP6) parseReply(reply *dhcpv6.Message) (leaseTime time.Duration) { } if len(reply.Options.NTPServers()) > 0 { - ntp := make([]string, len(reply.Options.NTPServers())) + convertIP := func(ip net.IP) string { + result, _ := netaddr.FromStdIP(ip) - for i := range ntp { - ip, _ := netaddr.FromStdIP(reply.Options.NTPServers()[i]) - ntp[i] = ip.String() + return result.String() } d.timeservers = []network.TimeServerSpecSpec{ { - NTPServers: ntp, + NTPServers: slices.Map(reply.Options.NTPServers(), convertIP), ConfigLayer: network.ConfigOperator, }, } diff --git a/internal/app/machined/pkg/controllers/network/operator_config.go b/internal/app/machined/pkg/controllers/network/operator_config.go index 972368a35..c46f9ef7b 100644 --- a/internal/app/machined/pkg/controllers/network/operator_config.go +++ b/internal/app/machined/pkg/controllers/network/operator_config.go @@ -16,6 +16,7 @@ import ( "go.uber.org/zap" talosconfig "github.com/talos-systems/talos/pkg/machinery/config" + "github.com/talos-systems/talos/pkg/machinery/generic/slices" "github.com/talos-systems/talos/pkg/machinery/resources/network" ) @@ -100,13 +101,9 @@ func (ctrl *OperatorConfigController) Run(ctx context.Context, r controller.Runt specErrors *multierror.Error ) - devices := make([]talosconfig.Device, len(items.Items)) - - for i, item := range items.Items { - device := item.(*network.DeviceConfigSpec).TypedSpec().Device - - devices[i] = device - } + devices := slices.Map(items.Items, func(item resource.Resource) talosconfig.Device { + return item.(*network.DeviceConfigSpec).TypedSpec().Device + }) // operators from the config if len(devices) > 0 { diff --git a/internal/app/machined/pkg/controllers/network/operator_vip_config.go b/internal/app/machined/pkg/controllers/network/operator_vip_config.go index 73d540560..ee46eb3a8 100644 --- a/internal/app/machined/pkg/controllers/network/operator_vip_config.go +++ b/internal/app/machined/pkg/controllers/network/operator_vip_config.go @@ -18,6 +18,7 @@ import ( "github.com/talos-systems/talos/internal/app/machined/pkg/controllers/network/operator/vip" talosconfig "github.com/talos-systems/talos/pkg/machinery/config" + "github.com/talos-systems/talos/pkg/machinery/generic/slices" "github.com/talos-systems/talos/pkg/machinery/resources/network" ) @@ -72,13 +73,9 @@ func (ctrl *OperatorVIPConfigController) Run(ctx context.Context, r controller.R } } - devices := make([]talosconfig.Device, len(items.Items)) - - for i, item := range items.Items { - device := item.(*network.DeviceConfigSpec).TypedSpec().Device - - devices[i] = device - } + devices := slices.Map(items.Items, func(item resource.Resource) talosconfig.Device { + return item.(*network.DeviceConfigSpec).TypedSpec().Device + }) ignoredInterfaces := map[string]struct{}{} diff --git a/internal/app/machined/pkg/controllers/network/resolver_spec.go b/internal/app/machined/pkg/controllers/network/resolver_spec.go index 9ad89e6cb..843ffbae0 100644 --- a/internal/app/machined/pkg/controllers/network/resolver_spec.go +++ b/internal/app/machined/pkg/controllers/network/resolver_spec.go @@ -12,7 +12,9 @@ import ( "github.com/cosi-project/runtime/pkg/resource" "github.com/cosi-project/runtime/pkg/state" "go.uber.org/zap" + "inet.af/netaddr" + "github.com/talos-systems/talos/pkg/machinery/generic/slices" "github.com/talos-systems/talos/pkg/machinery/resources/network" ) @@ -87,12 +89,7 @@ func (ctrl *ResolverSpecController) Run(ctx context.Context, r controller.Runtim return fmt.Errorf("error removing finalizer: %w", err) } case resource.PhaseRunning: - resolvers := make([]string, len(spec.TypedSpec().DNSServers)) - - for i := range resolvers { - resolvers[i] = spec.TypedSpec().DNSServers[i].String() - } - + resolvers := slices.Map(spec.TypedSpec().DNSServers, netaddr.IP.String) logger.Info("setting resolvers", zap.Strings("resolvers", resolvers)) if err = r.Modify(ctx, network.NewResolverStatus(network.NamespaceName, spec.Metadata().ID()), func(r resource.Resource) error { diff --git a/internal/app/machined/pkg/runtime/v1alpha2/v1alpha2_controller.go b/internal/app/machined/pkg/runtime/v1alpha2/v1alpha2_controller.go index 258cf5b1b..39aac3c22 100644 --- a/internal/app/machined/pkg/runtime/v1alpha2/v1alpha2_controller.go +++ b/internal/app/machined/pkg/runtime/v1alpha2/v1alpha2_controller.go @@ -38,6 +38,7 @@ import ( "github.com/talos-systems/talos/pkg/logging" talosconfig "github.com/talos-systems/talos/pkg/machinery/config" "github.com/talos-systems/talos/pkg/machinery/constants" + "github.com/talos-systems/talos/pkg/machinery/generic/slices" configresource "github.com/talos-systems/talos/pkg/machinery/resources/config" ) @@ -320,10 +321,7 @@ func (ctrl *Controller) updateLoggingConfig(ctx context.Context, cfg talosconfig var prevSenders []runtime.LogSender if len(loggingEndpoints) > 0 { - senders := make([]runtime.LogSender, len(loggingEndpoints)) - for i, u := range loggingEndpoints { - senders[i] = runtimelogging.NewJSONLines(u) - } + senders := slices.Map(loggingEndpoints, runtimelogging.NewJSONLines) ctrl.logger.Info("enabling JSON logging") prevSenders = ctrl.loggingManager.SetSenders(senders) diff --git a/internal/app/machined/pkg/system/events/events.go b/internal/app/machined/pkg/system/events/events.go index c350a4677..1f2d28695 100644 --- a/internal/app/machined/pkg/system/events/events.go +++ b/internal/app/machined/pkg/system/events/events.go @@ -11,6 +11,7 @@ import ( "github.com/talos-systems/talos/internal/app/machined/pkg/system/health" machineapi "github.com/talos-systems/talos/pkg/machinery/api/machine" + "github.com/talos-systems/talos/pkg/machinery/generic/slices" ) // MaxEventsToKeep is maximum number of events to keep per service before dropping old entries. @@ -120,21 +121,19 @@ func (events *ServiceEvents) Get(count int) (result []ServiceEvent) { func (events *ServiceEvents) AsProto(count int) *machineapi.ServiceEvents { eventList := events.Get(count) - result := &machineapi.ServiceEvents{ - Events: make([]*machineapi.ServiceEvent, len(eventList)), - } + fn := func(event ServiceEvent) *machineapi.ServiceEvent { + tspb := timestamppb.New(event.Timestamp) - for i := range eventList { - tspb := timestamppb.New(eventList[i].Timestamp) - - result.Events[i] = &machineapi.ServiceEvent{ - Msg: eventList[i].Message, - State: eventList[i].State.String(), + return &machineapi.ServiceEvent{ + Msg: event.Message, + State: event.State.String(), Ts: tspb, } } - return result + return &machineapi.ServiceEvents{ + Events: slices.Map(eventList, fn), + } } // Recorder adds new event to the history of events, formatting message with args using Sprintf. diff --git a/internal/app/machined/pkg/system/events/events_test.go b/internal/app/machined/pkg/system/events/events_test.go index af4877c8c..12fb74ad9 100644 --- a/internal/app/machined/pkg/system/events/events_test.go +++ b/internal/app/machined/pkg/system/events/events_test.go @@ -11,6 +11,7 @@ import ( "github.com/stretchr/testify/suite" "github.com/talos-systems/talos/internal/app/machined/pkg/system/events" + "github.com/talos-systems/talos/pkg/machinery/generic/slices" ) type EventsSuite struct { @@ -18,12 +19,7 @@ type EventsSuite struct { } func (suite *EventsSuite) assertEvents(expectedMessages []string, evs []events.ServiceEvent) { - messages := make([]string, len(evs)) - - for i := range evs { - messages[i] = evs[i].Message - } - + messages := slices.Map(evs, func(ev events.ServiceEvent) string { return ev.Message }) suite.Assert().Equal(expectedMessages, messages) } diff --git a/internal/app/machined/pkg/system/service_runner.go b/internal/app/machined/pkg/system/service_runner.go index b0030f1b6..9a824cde8 100644 --- a/internal/app/machined/pkg/system/service_runner.go +++ b/internal/app/machined/pkg/system/service_runner.go @@ -17,6 +17,7 @@ import ( "github.com/talos-systems/talos/internal/app/machined/pkg/system/runner" "github.com/talos-systems/talos/pkg/conditions" machineapi "github.com/talos-systems/talos/pkg/machinery/api/machine" + "github.com/talos-systems/talos/pkg/machinery/generic/slices" ) // WaitConditionCheckInterval is time between checking for wait condition @@ -200,11 +201,7 @@ func (svcrunner *ServiceRunner) Start() { dependencies := svcrunner.service.DependsOn(svcrunner.runtime) if len(dependencies) > 0 { - serviceConditions := make([]conditions.Condition, len(dependencies)) - for i := range dependencies { - serviceConditions[i] = WaitForService(StateEventUp, dependencies[i]) - } - + serviceConditions := slices.Map(dependencies, func(dep string) conditions.Condition { return WaitForService(StateEventUp, dep) }) serviceDependencies := conditions.WaitForAll(serviceConditions...) if condition != nil { diff --git a/internal/app/machined/pkg/system/system.go b/internal/app/machined/pkg/system/system.go index 881eca91a..9ec938010 100644 --- a/internal/app/machined/pkg/system/system.go +++ b/internal/app/machined/pkg/system/system.go @@ -16,6 +16,8 @@ import ( "github.com/talos-systems/talos/internal/app/machined/pkg/runtime" "github.com/talos-systems/talos/pkg/conditions" + "github.com/talos-systems/talos/pkg/machinery/generic/maps" + "github.com/talos-systems/talos/pkg/machinery/generic/slices" ) // singleton the system services API interface. @@ -176,12 +178,7 @@ func (s *singleton) Start(serviceIDs ...string) error { // StartAll starts all the services. func (s *singleton) StartAll() { s.mu.Lock() - serviceIDs := make([]string, 0, len(s.state)) - - for id := range s.state { - serviceIDs = append(serviceIDs, id) - } - + serviceIDs := maps.Keys(s.state) s.mu.Unlock() //nolint:errcheck @@ -335,13 +332,9 @@ func (s *singleton) stopServices(ctx context.Context, services []string, waitFor go func(svcrunner *ServiceRunner, reverseDeps []string) { defer shutdownWg.Done() - conds := make([]conditions.Condition, len(reverseDeps)) - - for i := range reverseDeps { - conds[i] = WaitForService(StateEventDown, reverseDeps[i]) - } - + conds := slices.Map(reverseDeps, func(dep string) conditions.Condition { return WaitForService(StateEventDown, dep) }) allDeps := conditions.WaitForAll(conds...) + if err := allDeps.Wait(shutdownCtx); err != nil { log.Printf("gave up on %s while stopping %q", allDeps, svcrunner.id) } @@ -360,10 +353,7 @@ func (s *singleton) List() (result []*ServiceRunner) { s.mu.Lock() defer s.mu.Unlock() - result = make([]*ServiceRunner, 0, len(s.state)) - for _, svcrunner := range s.state { - result = append(result, svcrunner) - } + result = maps.Values(s.state) // TODO: results should be sorted properly with topological sort on dependencies // but, we don't have dependencies yet, so sort by service id for now to get stable order diff --git a/internal/app/maintenance/main.go b/internal/app/maintenance/main.go index e78ede9cc..5477557fa 100644 --- a/internal/app/maintenance/main.go +++ b/internal/app/maintenance/main.go @@ -26,6 +26,7 @@ import ( "github.com/talos-systems/talos/pkg/grpc/gen" "github.com/talos-systems/talos/pkg/grpc/middleware/authz" "github.com/talos-systems/talos/pkg/machinery/constants" + "github.com/talos-systems/talos/pkg/machinery/generic/slices" "github.com/talos-systems/talos/pkg/machinery/resources/network" ) @@ -161,11 +162,7 @@ func genTLSConfig(ips []netaddr.IP, dnsNames []string) (tlsConfig *tls.Config, p ips = append(ips, netaddr.MustParseIP("127.0.0.1"), netaddr.MustParseIP("::1")) - netIPs := make([]net.IP, len(ips)) - - for i := range netIPs { - netIPs[i] = ips[i].IPAddr().IP - } + netIPs := slices.Map(ips, func(ip netaddr.IP) net.IP { return ip.IPAddr().IP }) var generator ttls.Generator diff --git a/internal/app/resources/server.go b/internal/app/resources/server.go index dfb69306f..d5eeb1669 100644 --- a/internal/app/resources/server.go +++ b/internal/app/resources/server.go @@ -20,6 +20,7 @@ import ( "github.com/talos-systems/talos/pkg/grpc/middleware/authz" resourceapi "github.com/talos-systems/talos/pkg/machinery/api/resource" + "github.com/talos-systems/talos/pkg/machinery/generic/slices" "github.com/talos-systems/talos/pkg/machinery/role" ) @@ -110,11 +111,7 @@ func (s *Server) resolveResourceKind(ctx context.Context, kind *resourceKind) (* return matched[0], nil case len(matched) > 1: - matchedTypes := make([]string, len(matched)) - - for i := range matched { - matchedTypes[i] = matched[i].Metadata().ID() - } + matchedTypes := slices.Map(matched, func(rd *meta.ResourceDefinition) string { return rd.Metadata().ID() }) return nil, status.Errorf(codes.InvalidArgument, fmt.Sprintf("resource type %q is ambiguous: %v", kind.Type, matchedTypes)) default: diff --git a/internal/app/storaged/server.go b/internal/app/storaged/server.go index 8ca379325..f687e20a8 100644 --- a/internal/app/storaged/server.go +++ b/internal/app/storaged/server.go @@ -11,6 +11,7 @@ import ( "google.golang.org/protobuf/types/known/emptypb" "github.com/talos-systems/talos/pkg/machinery/api/storage" + "github.com/talos-systems/talos/pkg/machinery/generic/slices" ) // Server implements storage.StorageService. @@ -26,21 +27,21 @@ func (s *Server) Disks(ctx context.Context, in *emptypb.Empty) (reply *storage.D return nil, err } - diskList := make([]*storage.Disk, len(disks)) - - for i, disk := range disks { - diskList[i] = &storage.Disk{ - DeviceName: disk.DeviceName, - Model: disk.Model, - Size: disk.Size, - Name: disk.Name, - Serial: disk.Serial, - Modalias: disk.Modalias, - Type: storage.Disk_DiskType(disk.Type), - BusPath: disk.BusPath, + diskConv := func(d *disk.Disk) *storage.Disk { + return &storage.Disk{ + DeviceName: d.DeviceName, + Model: d.Model, + Size: d.Size, + Name: d.Name, + Serial: d.Serial, + Modalias: d.Modalias, + Type: storage.Disk_DiskType(d.Type), + BusPath: d.BusPath, } } + diskList := slices.Map(disks, diskConv) + reply = &storage.DisksResponse{ Messages: []*storage.Disks{ { diff --git a/internal/integration/cli/dmesg.go b/internal/integration/cli/dmesg.go index c8e33ec46..53cd6d883 100644 --- a/internal/integration/cli/dmesg.go +++ b/internal/integration/cli/dmesg.go @@ -14,6 +14,7 @@ import ( "strings" "github.com/talos-systems/talos/internal/integration/base" + "github.com/talos-systems/talos/pkg/machinery/generic/slices" ) // DmesgSuite verifies dmesg command. @@ -36,13 +37,11 @@ func (suite *DmesgSuite) TestClusterHasOutput() { nodes := suite.DiscoverNodes(context.TODO()).Nodes() suite.Require().NotEmpty(nodes) - matchers := make([]base.RunOption, 0, len(nodes)) - - for _, node := range nodes { - matchers = append(matchers, - base.StdoutShouldMatch( - regexp.MustCompile(fmt.Sprintf(`(?m)^%s:`, regexp.QuoteMeta(node))))) - } + matchers := slices.Map(nodes, func(node string) base.RunOption { + return base.StdoutShouldMatch( + regexp.MustCompile(fmt.Sprintf(`(?m)^%s:`, regexp.QuoteMeta(node))), + ) + }) suite.RunCLI([]string{"--nodes", strings.Join(nodes, ","), "dmesg"}, matchers...) diff --git a/internal/integration/provision/upgrade.go b/internal/integration/provision/upgrade.go index 14440b53a..81711bb93 100644 --- a/internal/integration/provision/upgrade.go +++ b/internal/integration/provision/upgrade.go @@ -41,6 +41,7 @@ import ( "github.com/talos-systems/talos/pkg/machinery/config/types/v1alpha1/generate" "github.com/talos-systems/talos/pkg/machinery/config/types/v1alpha1/machine" "github.com/talos-systems/talos/pkg/machinery/constants" + "github.com/talos-systems/talos/pkg/machinery/generic/slices" "github.com/talos-systems/talos/pkg/provision" "github.com/talos-systems/talos/pkg/provision/access" "github.com/talos-systems/talos/pkg/provision/providers/qemu" @@ -524,12 +525,7 @@ func (suite *UpgradeSuite) runE2E(k8sVersion string) { } func (suite *UpgradeSuite) assertSameVersionCluster(client *talosclient.Client, expectedVersion string) { - nodes := make([]string, len(suite.Cluster.Info().Nodes)) - - for i, node := range suite.Cluster.Info().Nodes { - nodes[i] = node.IPs[0].String() - } - + nodes := slices.Map(suite.Cluster.Info().Nodes, func(node provision.NodeInfo) string { return node.IPs[0].String() }) ctx := talosclient.WithNodes(suite.ctx, nodes...) var v *machineapi.VersionResponse diff --git a/internal/pkg/circular/circular.go b/internal/pkg/circular/circular.go index 1f2d65939..03c0bef8f 100644 --- a/internal/pkg/circular/circular.go +++ b/internal/pkg/circular/circular.go @@ -8,6 +8,8 @@ package circular import ( "fmt" "sync" + + "github.com/talos-systems/talos/pkg/machinery/generic/slices" ) // Buffer implements circular buffer with a thread-safe writer, @@ -76,9 +78,7 @@ func (buf *Buffer) Write(p []byte) (int, error) { size = buf.opt.MaxCapacity } - data := make([]byte, size) - copy(data, buf.data) - buf.data = data + buf.data = slices.Copy(buf.data, size) } } diff --git a/internal/pkg/configuration/configuration.go b/internal/pkg/configuration/configuration.go index 920bdc302..dee07bbcb 100644 --- a/internal/pkg/configuration/configuration.go +++ b/internal/pkg/configuration/configuration.go @@ -17,6 +17,7 @@ import ( "github.com/talos-systems/talos/pkg/machinery/config/types/v1alpha1/generate" v1alpha1machine "github.com/talos-systems/talos/pkg/machinery/config/types/v1alpha1/machine" "github.com/talos-systems/talos/pkg/machinery/constants" + "github.com/talos-systems/talos/pkg/machinery/generic/slices" ) // Generate config for GenerateConfiguration grpc. @@ -45,15 +46,19 @@ func Generate(ctx context.Context, in *machine.GenerateConfigurationRequest) (re networkConfig.NetworkInterfaces = make([]*v1alpha1.Device, len(networkInterfaces)) for i, device := range networkInterfaces { - routes := make([]*v1alpha1.Route, len(device.Routes)) - iface := &v1alpha1.Device{ DeviceInterface: device.Interface, DeviceMTU: int(device.Mtu), DeviceCIDR: device.Cidr, DeviceDHCP: device.Dhcp, DeviceIgnore: device.Ignore, - DeviceRoutes: routes, + DeviceRoutes: slices.Map(device.Routes, func(route *machine.RouteConfig) *v1alpha1.Route { + return &v1alpha1.Route{ + RouteNetwork: route.Network, + RouteGateway: route.Gateway, + RouteMetric: route.Metric, + } + }), } if device.DhcpOptions != nil { diff --git a/internal/pkg/discovery/registry/kubernetes.go b/internal/pkg/discovery/registry/kubernetes.go index a76722be6..4a262bc24 100644 --- a/internal/pkg/discovery/registry/kubernetes.go +++ b/internal/pkg/discovery/registry/kubernetes.go @@ -26,6 +26,7 @@ import ( "github.com/talos-systems/talos/pkg/kubernetes" "github.com/talos-systems/talos/pkg/machinery/config/types/v1alpha1/machine" "github.com/talos-systems/talos/pkg/machinery/constants" + "github.com/talos-systems/talos/pkg/machinery/generic/slices" "github.com/talos-systems/talos/pkg/machinery/resources/cluster" ) @@ -125,33 +126,15 @@ func AffiliateFromNode(node *v1.Node) *cluster.AffiliateSpec { } func ipsToString(in []netaddr.IP) string { - items := make([]string, len(in)) - - for i := range in { - items[i] = in[i].String() - } - - return strings.Join(items, ",") + return strings.Join(slices.Map(in, netaddr.IP.String), ",") } func ipPrefixesToString(in []netaddr.IPPrefix) string { - items := make([]string, len(in)) - - for i := range in { - items[i] = in[i].String() - } - - return strings.Join(items, ",") + return strings.Join(slices.Map(in, netaddr.IPPrefix.String), ",") } func ipPortsToString(in []netaddr.IPPort) string { - items := make([]string, len(in)) - - for i := range in { - items[i] = in[i].String() - } - - return strings.Join(items, ",") + return strings.Join(slices.Map(in, netaddr.IPPort.String), ",") } func parseIPs(in string) []netaddr.IP { diff --git a/pkg/argsbuilder/argsbuilder_args.go b/pkg/argsbuilder/argsbuilder_args.go index cba855eea..7621bbe53 100644 --- a/pkg/argsbuilder/argsbuilder_args.go +++ b/pkg/argsbuilder/argsbuilder_args.go @@ -8,6 +8,8 @@ import ( "fmt" "sort" "strings" + + "github.com/talos-systems/talos/pkg/machinery/generic/maps" ) // Key represents an arg key. @@ -88,12 +90,7 @@ func (a Args) Set(k, v Key) ArgsBuilder { // Args implements the ArgsBuilder interface. func (a Args) Args() []string { - keys := make([]string, 0, len(a)) - - for key := range a { - keys = append(keys, key) - } - + keys := maps.Keys(a) sort.Strings(keys) args := []string{} diff --git a/pkg/chunker/stream/stream.go b/pkg/chunker/stream/stream.go index 1c3ab0f84..08636b010 100644 --- a/pkg/chunker/stream/stream.go +++ b/pkg/chunker/stream/stream.go @@ -10,6 +10,7 @@ import ( "io" "github.com/talos-systems/talos/pkg/chunker" + "github.com/talos-systems/talos/pkg/machinery/generic/slices" ) // Options is the functional options struct. @@ -87,8 +88,7 @@ func (c *Stream) Read() <-chan []byte { if n != 0 { // Copy the buffer since we will modify it in the next loop. - b := make([]byte, n) - copy(b, buf[:n]) + b := slices.Copy(buf, n) select { case <-c.ctx.Done(): diff --git a/pkg/cluster/kubernetes/talos_managed.go b/pkg/cluster/kubernetes/talos_managed.go index 184a849c2..2be35bc8c 100644 --- a/pkg/cluster/kubernetes/talos_managed.go +++ b/pkg/cluster/kubernetes/talos_managed.go @@ -39,6 +39,7 @@ import ( v1alpha1config "github.com/talos-systems/talos/pkg/machinery/config/types/v1alpha1" machinetype "github.com/talos-systems/talos/pkg/machinery/config/types/v1alpha1/machine" "github.com/talos-systems/talos/pkg/machinery/constants" + "github.com/talos-systems/talos/pkg/machinery/generic/slices" "github.com/talos-systems/talos/pkg/machinery/resources/config" "github.com/talos-systems/talos/pkg/machinery/resources/k8s" ) @@ -756,11 +757,7 @@ func checkDeprecated(ctx context.Context, cluster UpgradeProvider, options Upgra probeResources := func(namespaces ...v1.Namespace) error { r := k8sClient.Resource(*gvr) - namespaceNames := make([]string, 0, len(namespaces)) - - for _, ns := range namespaces { - namespaceNames = append(namespaceNames, ns.Name) - } + namespaceNames := slices.Map(namespaces, func(ns v1.Namespace) string { return ns.Name }) if len(namespaceNames) == 0 { namespaceNames = append(namespaceNames, "default") diff --git a/pkg/conditions/files.go b/pkg/conditions/files.go index 1fc992fe8..ada85c923 100644 --- a/pkg/conditions/files.go +++ b/pkg/conditions/files.go @@ -9,6 +9,8 @@ import ( "fmt" "os" "time" + + "github.com/talos-systems/talos/pkg/machinery/generic/slices" ) type file string @@ -47,10 +49,7 @@ func WaitForFileToExist(filename string) Condition { // WaitForFilesToExist is a service condition that will wait for the existence of all the files. func WaitForFilesToExist(filenames ...string) Condition { - conditions := make([]Condition, len(filenames)) - for i := range filenames { - conditions[i] = WaitForFileToExist(filenames[i]) - } + conditions := slices.Map(filenames, WaitForFileToExist) return WaitForAll(conditions...) } diff --git a/pkg/grpc/middleware/log/log.go b/pkg/grpc/middleware/log/log.go index e15795c0f..7ca57cfe1 100644 --- a/pkg/grpc/middleware/log/log.go +++ b/pkg/grpc/middleware/log/log.go @@ -15,6 +15,8 @@ import ( "google.golang.org/grpc" metadata "google.golang.org/grpc/metadata" "google.golang.org/grpc/status" + + "github.com/talos-systems/talos/pkg/machinery/generic/maps" ) // Middleware provides grpc logging middleware. @@ -36,12 +38,7 @@ var sensitiveFields = map[string]struct{}{ // ExtractMetadata formats metadata from incoming grpc context as string for the log. func ExtractMetadata(ctx context.Context) string { md, _ := metadata.FromIncomingContext(ctx) - keys := make([]string, 0, len(md)) - - for key := range md { - keys = append(keys, key) - } - + keys := maps.Keys(md) sort.Strings(keys) pairs := make([]string, 0, len(keys)) diff --git a/pkg/machinery/config/types/v1alpha1/v1alpha1_apiserverconfig.go b/pkg/machinery/config/types/v1alpha1/v1alpha1_apiserverconfig.go index c8c6ec11e..bbebae160 100644 --- a/pkg/machinery/config/types/v1alpha1/v1alpha1_apiserverconfig.go +++ b/pkg/machinery/config/types/v1alpha1/v1alpha1_apiserverconfig.go @@ -9,6 +9,7 @@ import ( "github.com/talos-systems/talos/pkg/machinery/config" "github.com/talos-systems/talos/pkg/machinery/constants" + "github.com/talos-systems/talos/pkg/machinery/generic/slices" ) // Image implements the config.APIServer interface. @@ -29,13 +30,7 @@ func (a *APIServerConfig) ExtraArgs() map[string]string { // ExtraVolumes implements the config.APIServer interface. func (a *APIServerConfig) ExtraVolumes() []config.VolumeMount { - volumes := make([]config.VolumeMount, 0, len(a.ExtraVolumesConfig)) - - for _, volume := range a.ExtraVolumesConfig { - volumes = append(volumes, volume) - } - - return volumes + return slices.Map(a.ExtraVolumesConfig, func(v VolumeMountConfig) config.VolumeMount { return v }) } // Env implements the config.APIServer interface. @@ -50,15 +45,5 @@ func (a *APIServerConfig) DisablePodSecurityPolicy() bool { // AdmissionControl implements the config.APIServer interface. func (a *APIServerConfig) AdmissionControl() []config.AdmissionPlugin { - if a.AdmissionControlConfig == nil { - return nil - } - - res := make([]config.AdmissionPlugin, 0, len(a.AdmissionControlConfig)) - - for _, c := range a.AdmissionControlConfig { - res = append(res, c) - } - - return res + return slices.Map(a.AdmissionControlConfig, func(c *AdmissionPluginConfig) config.AdmissionPlugin { return c }) } diff --git a/pkg/machinery/config/types/v1alpha1/v1alpha1_clusterconfig.go b/pkg/machinery/config/types/v1alpha1/v1alpha1_clusterconfig.go index 857fc36ef..b390e0f76 100644 --- a/pkg/machinery/config/types/v1alpha1/v1alpha1_clusterconfig.go +++ b/pkg/machinery/config/types/v1alpha1/v1alpha1_clusterconfig.go @@ -16,6 +16,7 @@ import ( "github.com/talos-systems/talos/pkg/machinery/config" "github.com/talos-systems/talos/pkg/machinery/config/types/v1alpha1/machine" "github.com/talos-systems/talos/pkg/machinery/constants" + "github.com/talos-systems/talos/pkg/machinery/generic/slices" ) // ClusterConfig implements config.ClusterConfig, config.Token, and config.ClusterNetwork interfaces. @@ -158,13 +159,7 @@ func (c *ClusterConfig) ExtraManifestHeaderMap() map[string]string { // InlineManifests implements the config.ClusterConfig interface. func (c *ClusterConfig) InlineManifests() []config.InlineManifest { - manifests := make([]config.InlineManifest, len(c.ClusterInlineManifests)) - - for i := range manifests { - manifests[i] = c.ClusterInlineManifests[i] - } - - return manifests + return slices.Map(c.ClusterInlineManifests, func(m ClusterInlineManifest) config.InlineManifest { return m }) } // AdminKubeconfig implements the config.ClusterConfig interface. diff --git a/pkg/machinery/config/types/v1alpha1/v1alpha1_controllermanagerconfig.go b/pkg/machinery/config/types/v1alpha1/v1alpha1_controllermanagerconfig.go index 80fd55d02..6d4861b18 100644 --- a/pkg/machinery/config/types/v1alpha1/v1alpha1_controllermanagerconfig.go +++ b/pkg/machinery/config/types/v1alpha1/v1alpha1_controllermanagerconfig.go @@ -9,6 +9,7 @@ import ( "github.com/talos-systems/talos/pkg/machinery/config" "github.com/talos-systems/talos/pkg/machinery/constants" + "github.com/talos-systems/talos/pkg/machinery/generic/slices" ) // Image implements the config.ControllerManager interface. @@ -29,13 +30,7 @@ func (c *ControllerManagerConfig) ExtraArgs() map[string]string { // ExtraVolumes implements the config.ControllerManager interface. func (c *ControllerManagerConfig) ExtraVolumes() []config.VolumeMount { - volumes := make([]config.VolumeMount, 0, len(c.ExtraVolumesConfig)) - - for _, volume := range c.ExtraVolumesConfig { - volumes = append(volumes, volume) - } - - return volumes + return slices.Map(c.ExtraVolumesConfig, func(v VolumeMountConfig) config.VolumeMount { return v }) } // Env implements the config.ControllerManager interface. diff --git a/pkg/machinery/config/types/v1alpha1/v1alpha1_kernel.go b/pkg/machinery/config/types/v1alpha1/v1alpha1_kernel.go index ce8ee8e51..22ed4ae3c 100644 --- a/pkg/machinery/config/types/v1alpha1/v1alpha1_kernel.go +++ b/pkg/machinery/config/types/v1alpha1/v1alpha1_kernel.go @@ -6,20 +6,12 @@ package v1alpha1 import ( "github.com/talos-systems/talos/pkg/machinery/config" + "github.com/talos-systems/talos/pkg/machinery/generic/slices" ) // Modules implements config.Kernel interface. func (kc *KernelConfig) Modules() []config.KernelModule { - if kc.KernelModules == nil { - return nil - } - - res := make([]config.KernelModule, len(kc.KernelModules)) - for i, m := range kc.KernelModules { - res[i] = config.KernelModule(m) - } - - return res + return slices.Map(kc.KernelModules, func(kmc *KernelModuleConfig) config.KernelModule { return kmc }) } // Name implements config.KernelModule interface. diff --git a/pkg/machinery/config/types/v1alpha1/v1alpha1_logging.go b/pkg/machinery/config/types/v1alpha1/v1alpha1_logging.go index 0a569ce38..177f1e58d 100644 --- a/pkg/machinery/config/types/v1alpha1/v1alpha1_logging.go +++ b/pkg/machinery/config/types/v1alpha1/v1alpha1_logging.go @@ -12,6 +12,7 @@ import ( "github.com/talos-systems/talos/pkg/machinery/config" "github.com/talos-systems/talos/pkg/machinery/constants" + "github.com/talos-systems/talos/pkg/machinery/generic/slices" ) // Validate checks logging configuration for errors. @@ -49,12 +50,7 @@ func (lc *LoggingConfig) Validate() error { // Destinations implements config.Logging interface. func (lc *LoggingConfig) Destinations() []config.LoggingDestination { - res := make([]config.LoggingDestination, len(lc.LoggingDestinations)) - for i, ld := range lc.LoggingDestinations { - res[i] = config.LoggingDestination(ld) - } - - return res + return slices.Map(lc.LoggingDestinations, func(ld LoggingDestination) config.LoggingDestination { return ld }) } // Endpoint implements config.LoggingDestination interface. diff --git a/pkg/machinery/config/types/v1alpha1/v1alpha1_provider.go b/pkg/machinery/config/types/v1alpha1/v1alpha1_provider.go index b3c4d21ef..c0bddcd88 100644 --- a/pkg/machinery/config/types/v1alpha1/v1alpha1_provider.go +++ b/pkg/machinery/config/types/v1alpha1/v1alpha1_provider.go @@ -20,6 +20,7 @@ import ( "github.com/talos-systems/talos/pkg/machinery/config/encoder" "github.com/talos-systems/talos/pkg/machinery/config/types/v1alpha1/machine" "github.com/talos-systems/talos/pkg/machinery/constants" + "github.com/talos-systems/talos/pkg/machinery/generic/slices" ) const ( @@ -101,13 +102,7 @@ func (m *MachineConfig) Security() config.Security { // Disks implements the config.Provider interface. func (m *MachineConfig) Disks() []config.Disk { - disks := make([]config.Disk, len(m.MachineDisks)) - - for i := 0; i < len(m.MachineDisks); i++ { - disks[i] = m.MachineDisks[i] - } - - return disks + return slices.Map(m.MachineDisks, func(d *MachineDisk) config.Disk { return d }) } // Network implements the config.Provider interface. @@ -139,17 +134,7 @@ func (m *MachineConfig) Controlplane() config.MachineControlPlane { // Pods implements the config.Provider interface. func (m *MachineConfig) Pods() []map[string]interface{} { - if m.MachinePods == nil { - return nil - } - - v := make([]map[string]interface{}, len(m.MachinePods)) - - for i := range v { - v[i] = m.MachinePods[i].Object - } - - return v + return slices.Map(m.MachinePods, func(u Unstructured) map[string]interface{} { return u.Object }) } // ControllerManager implements the config.Provider interface. @@ -196,13 +181,7 @@ func (m *MachineConfig) Env() config.Env { // Files implements the config.Provider interface. func (m *MachineConfig) Files() ([]config.File, error) { - files := make([]config.File, len(m.MachineFiles)) - - for i := 0; i < len(m.MachineFiles); i++ { - files[i] = m.MachineFiles[i] - } - - return files, nil + return slices.Map(m.MachineFiles, func(f *MachineFile) config.File { return f }), nil } // Type implements the config.Provider interface. @@ -331,17 +310,7 @@ func (k *KubeletConfig) ExtraArgs() map[string]string { // ExtraMounts implements the config.Provider interface. func (k *KubeletConfig) ExtraMounts() []specs.Mount { - if k.KubeletExtraMounts == nil { - return nil - } - - out := make([]specs.Mount, len(k.KubeletExtraMounts)) - - for i := range k.KubeletExtraMounts { - out[i] = k.KubeletExtraMounts[i].Mount - } - - return out + return slices.Map(k.KubeletExtraMounts, func(m ExtraMount) specs.Mount { return m.Mount }) } // ExtraConfig implements the config.Provider interface. @@ -476,13 +445,7 @@ func (n *NetworkConfig) DisableSearchDomain() bool { // Devices implements the config.Provider interface. func (n *NetworkConfig) Devices() []config.Device { - interfaces := make([]config.Device, len(n.NetworkInterfaces)) - - for i := 0; i < len(n.NetworkInterfaces); i++ { - interfaces[i] = n.NetworkInterfaces[i] - } - - return interfaces + return slices.Map(n.NetworkInterfaces, func(d *Device) config.Device { return d }) } // getDevice adds or returns existing Device by name. @@ -511,13 +474,7 @@ func (n *NetworkConfig) Resolvers() []string { // ExtraHosts implements the config.Provider interface. func (n *NetworkConfig) ExtraHosts() []config.ExtraHost { - hosts := make([]config.ExtraHost, len(n.ExtraHostEntries)) - - for i := 0; i < len(n.ExtraHostEntries); i++ { - hosts[i] = n.ExtraHostEntries[i] - } - - return hosts + return slices.Map(n.ExtraHostEntries, func(e *ExtraHost) config.ExtraHost { return e }) } // KubeSpan implements the config.Provider interface. @@ -554,13 +511,7 @@ func (d *Device) Addresses() []string { // Routes implements the MachineNetwork interface. func (d *Device) Routes() []config.Route { - routes := make([]config.Route, len(d.DeviceRoutes)) - - for i := 0; i < len(d.DeviceRoutes); i++ { - routes[i] = d.DeviceRoutes[i] - } - - return routes + return slices.Map(d.DeviceRoutes, func(r *Route) config.Route { return r }) } // Bond implements the MachineNetwork interface. @@ -574,13 +525,7 @@ func (d *Device) Bond() config.Bond { // Vlans implements the MachineNetwork interface. func (d *Device) Vlans() []config.Vlan { - vlans := make([]config.Vlan, len(d.DeviceVlans)) - - for i := 0; i < len(d.DeviceVlans); i++ { - vlans[i] = d.DeviceVlans[i] - } - - return vlans + return slices.Map(d.DeviceVlans, func(v *Vlan) config.Vlan { return v }) } // MTU implements the MachineNetwork interface. @@ -720,13 +665,7 @@ func (wc *DeviceWireguardConfig) FirewallMark() int { // Peers implements the MachineNetwork interface. func (wc *DeviceWireguardConfig) Peers() []config.WireguardPeer { - peers := make([]config.WireguardPeer, len(wc.WireguardPeers)) - - for i := 0; i < len(wc.WireguardPeers); i++ { - peers[i] = wc.WireguardPeers[i] - } - - return peers + return slices.Map(wc.WireguardPeers, func(p *DeviceWireguardPeer) config.WireguardPeer { return p }) } // PublicKey implements the MachineNetwork interface. @@ -964,13 +903,7 @@ func (v *Vlan) VIPConfig() config.VIPConfig { // Routes implements the MachineNetwork interface. func (v *Vlan) Routes() []config.Route { - routes := make([]config.Route, len(v.VlanRoutes)) - - for i := 0; i < len(v.VlanRoutes); i++ { - routes[i] = v.VlanRoutes[i] - } - - return routes + return slices.Map(v.VlanRoutes, func(r *Route) config.Route { return r }) } // DHCP implements the MachineNetwork interface. @@ -1015,17 +948,7 @@ func (i *InstallConfig) Image() string { // Extensions implements the config.Provider interface. func (i *InstallConfig) Extensions() []config.Extension { - if len(i.InstallExtensions) == 0 { - return nil - } - - extensions := make([]config.Extension, 0, len(i.InstallExtensions)) - - for _, ext := range i.InstallExtensions { - extensions = append(extensions, ext) - } - - return extensions + return slices.Map(i.InstallExtensions, func(e InstallExtensionConfig) config.Extension { return e }) } // Disk implements the config.Provider interface. @@ -1178,13 +1101,7 @@ func (d *MachineDisk) Device() string { // Partitions implements the config.Provider interface. func (d *MachineDisk) Partitions() []config.Partition { - partitions := make([]config.Partition, len(d.DiskPartitions)) - - for i := 0; i < len(d.DiskPartitions); i++ { - partitions[i] = d.DiskPartitions[i] - } - - return partitions + return slices.Map(d.DiskPartitions, func(p *DiskPartition) config.Partition { return p }) } // Size implements the config.Provider interface. @@ -1224,13 +1141,7 @@ func (e *EncryptionConfig) Options() []string { // Keys implements the config.Provider interface. func (e *EncryptionConfig) Keys() []config.EncryptionKey { - keys := make([]config.EncryptionKey, len(e.EncryptionKeys)) - - for i, key := range e.EncryptionKeys { - keys[i] = key - } - - return keys + return slices.Map(e.EncryptionKeys, func(k *EncryptionKey) config.EncryptionKey { return k }) } // Static implements the config.Provider interface. diff --git a/pkg/machinery/config/types/v1alpha1/v1alpha1_schedulerconfig.go b/pkg/machinery/config/types/v1alpha1/v1alpha1_schedulerconfig.go index b586767a6..af1473697 100644 --- a/pkg/machinery/config/types/v1alpha1/v1alpha1_schedulerconfig.go +++ b/pkg/machinery/config/types/v1alpha1/v1alpha1_schedulerconfig.go @@ -9,6 +9,7 @@ import ( "github.com/talos-systems/talos/pkg/machinery/config" "github.com/talos-systems/talos/pkg/machinery/constants" + "github.com/talos-systems/talos/pkg/machinery/generic/slices" ) // Image implements the config.Scheduler interface. @@ -29,13 +30,7 @@ func (s *SchedulerConfig) ExtraArgs() map[string]string { // ExtraVolumes implements the config.Scheduler interface. func (s *SchedulerConfig) ExtraVolumes() []config.VolumeMount { - volumes := make([]config.VolumeMount, 0, len(s.ExtraVolumesConfig)) - - for _, volume := range s.ExtraVolumesConfig { - volumes = append(volumes, volume) - } - - return volumes + return slices.Map(s.ExtraVolumesConfig, func(v VolumeMountConfig) config.VolumeMount { return v }) } // Env implements the config.Scheduler interface. diff --git a/pkg/machinery/generic/maps/maps.go b/pkg/machinery/generic/maps/maps.go index c70be44c7..60f33a479 100644 --- a/pkg/machinery/generic/maps/maps.go +++ b/pkg/machinery/generic/maps/maps.go @@ -74,6 +74,18 @@ func KeysFunc[K comparable, V, R any](m map[K]V, fn func(K) R) []R { return r } +// Values returns the values of the map m. +// The values will be in an indeterminate order. +func Values[K comparable, V any](m map[K]V) []V { + r := make([]V, 0, len(m)) + + for _, v := range m { + r = append(r, v) + } + + return r +} + // ValuesFunc applies the function fn to each value of the map m and returns a new slice with the results. // The values will be in an indeterminate order. func ValuesFunc[K comparable, V, R any](m map[K]V, fn func(V) R) []R { diff --git a/pkg/machinery/generic/slices/slices.go b/pkg/machinery/generic/slices/slices.go index 725aff36e..1956b84eb 100644 --- a/pkg/machinery/generic/slices/slices.go +++ b/pkg/machinery/generic/slices/slices.go @@ -146,3 +146,15 @@ func IndexFunc[T any](slc []T, fn func(T) bool) int { func Contains[T any](s []T, fn func(T) bool) bool { return IndexFunc(s, fn) >= 0 } + +// Copy returns a slice of V with the last n elements removed. +func Copy[S ~[]V, V any](s S, n int) S { + if s == nil { + return nil + } + + result := make([]V, n) + copy(result, s) + + return result +} diff --git a/pkg/machinery/resources/k8s/endpoint.go b/pkg/machinery/resources/k8s/endpoint.go index e72def931..17f13c3c1 100644 --- a/pkg/machinery/resources/k8s/endpoint.go +++ b/pkg/machinery/resources/k8s/endpoint.go @@ -11,6 +11,8 @@ import ( "github.com/cosi-project/runtime/pkg/resource/meta" "github.com/cosi-project/runtime/pkg/resource/typed" "inet.af/netaddr" + + "github.com/talos-systems/talos/pkg/machinery/generic/slices" ) // EndpointType is type of Endpoint resource. @@ -78,11 +80,5 @@ func (l EndpointList) Merge(endpoint *Endpoint) EndpointList { // Strings returns a slice of formatted endpoints to string. func (l EndpointList) Strings() []string { - res := make([]string, len(l)) - - for i := range l { - res[i] = l[i].String() - } - - return res + return slices.Map(l, netaddr.IP.String) } diff --git a/pkg/machinery/resources/network/node_address.go b/pkg/machinery/resources/network/node_address.go index 4fe3bb8dd..bff8c39a4 100644 --- a/pkg/machinery/resources/network/node_address.go +++ b/pkg/machinery/resources/network/node_address.go @@ -11,6 +11,8 @@ import ( "github.com/cosi-project/runtime/pkg/resource/meta" "github.com/cosi-project/runtime/pkg/resource/typed" "inet.af/netaddr" + + "github.com/talos-systems/talos/pkg/machinery/generic/slices" ) // NodeAddressType is type of NodeAddress resource. @@ -68,13 +70,7 @@ func (NodeAddressRD) ResourceDefinition(resource.Metadata, NodeAddressSpec) meta // IPs returns IP without prefix. func (spec *NodeAddressSpec) IPs() []netaddr.IP { - result := make([]netaddr.IP, len(spec.Addresses)) - - for i := range spec.Addresses { - result[i] = spec.Addresses[i].IP() - } - - return result + return slices.Map(spec.Addresses, netaddr.IPPrefix.IP) } // FilteredNodeAddressID returns resource ID for node addresses with filter applied. diff --git a/pkg/machinery/resources/secrets/cert_sans.go b/pkg/machinery/resources/secrets/cert_sans.go index ec3935453..325df66e0 100644 --- a/pkg/machinery/resources/secrets/cert_sans.go +++ b/pkg/machinery/resources/secrets/cert_sans.go @@ -12,6 +12,8 @@ import ( "github.com/cosi-project/runtime/pkg/resource/meta" "github.com/cosi-project/runtime/pkg/resource/typed" "inet.af/netaddr" + + "github.com/talos-systems/talos/pkg/machinery/generic/slices" ) // CertSANType is type of CertSAN resource. @@ -121,13 +123,7 @@ func (spec *CertSANSpec) AppendDNSNames(dnsNames ...string) { // StdIPs returns a list of converted std.IPs. func (spec *CertSANSpec) StdIPs() []net.IP { - result := make([]net.IP, len(spec.IPs)) - - for i := range spec.IPs { - result[i] = spec.IPs[i].IPAddr().IP - } - - return result + return slices.Map(spec.IPs, func(ip netaddr.IP) net.IP { return ip.IPAddr().IP }) } // Sort the CertSANs. diff --git a/pkg/machinery/role/role.go b/pkg/machinery/role/role.go index b6f81c401..6543df7eb 100644 --- a/pkg/machinery/role/role.go +++ b/pkg/machinery/role/role.go @@ -7,6 +7,8 @@ package role import ( "sort" "strings" + + "github.com/talos-systems/talos/pkg/machinery/generic/maps" ) // Role represents Talos user role. @@ -87,12 +89,7 @@ func Parse(str []string) (Set, []string) { // Strings returns a set as a slice of strings. func (s Set) Strings() []string { - res := make([]string, 0, len(s.roles)) - - for r := range s.roles { - res = append(res, string(r)) - } - + res := maps.KeysFunc(s.roles, func(r Role) string { return string(r) }) sort.Strings(res) return res diff --git a/pkg/machinery/role/role_test.go b/pkg/machinery/role/role_test.go index 03c0b5fc7..a2f571e39 100644 --- a/pkg/machinery/role/role_test.go +++ b/pkg/machinery/role/role_test.go @@ -20,7 +20,7 @@ func TestSet(t *testing.T) { assert.Equal(t, role.MakeSet(role.Admin, role.Reader, role.Role("os:future"), role.Impersonator), roles) assert.Equal(t, []string{"os:admin", "os:future", "os:impersonator", "os:reader"}, roles.Strings()) - assert.Equal(t, []string{}, role.MakeSet().Strings()) + assert.Equal(t, []string(nil), role.MakeSet().Strings()) assert.True(t, roles.Includes(role.Admin)) assert.False(t, roles.Includes(role.Role("wrong"))) diff --git a/pkg/provision/access/adapter.go b/pkg/provision/access/adapter.go index 44bb56f45..ebafa5f05 100644 --- a/pkg/provision/access/adapter.go +++ b/pkg/provision/access/adapter.go @@ -7,6 +7,7 @@ package access import ( "github.com/talos-systems/talos/pkg/cluster" "github.com/talos-systems/talos/pkg/machinery/config/types/v1alpha1/machine" + "github.com/talos-systems/talos/pkg/machinery/generic/slices" "github.com/talos-systems/talos/pkg/provision" ) @@ -25,13 +26,7 @@ type infoWrapper struct { } func (wrapper *infoWrapper) Nodes() []string { - nodes := make([]string, len(wrapper.clusterInfo.Nodes)) - - for i := range nodes { - nodes[i] = wrapper.clusterInfo.Nodes[i].IPs[0].String() - } - - return nodes + return slices.Map(wrapper.clusterInfo.Nodes, func(node provision.NodeInfo) string { return node.IPs[0].String() }) } func (wrapper *infoWrapper) NodesByType(t machine.Type) []string { diff --git a/pkg/provision/providers/qemu/launch.go b/pkg/provision/providers/qemu/launch.go index cefae46c3..1fa81a283 100644 --- a/pkg/provision/providers/qemu/launch.go +++ b/pkg/provision/providers/qemu/launch.go @@ -23,6 +23,7 @@ import ( "github.com/talos-systems/go-blockdevice/blockdevice/partition/gpt" talosnet "github.com/talos-systems/net" + "github.com/talos-systems/talos/pkg/machinery/generic/slices" "github.com/talos-systems/talos/pkg/provision" "github.com/talos-systems/talos/pkg/provision/internal/cniutils" "github.com/talos-systems/talos/pkg/provision/providers/vm" @@ -110,10 +111,7 @@ func withCNI(ctx context.Context, config *LaunchConfig, f func(config *LaunchCon ips[j] = talosnet.FormatCIDR(config.IPs[j], config.CIDRs[j]) } - gatewayAddrs := make([]string, len(config.GatewayAddrs)) - for j := range gatewayAddrs { - gatewayAddrs[j] = config.GatewayAddrs[j].String() - } + gatewayAddrs := slices.Map(config.GatewayAddrs, net.IP.String) runtimeConf := libcni.RuntimeConf{ ContainerID: containerID, diff --git a/pkg/provision/providers/vm/dhcpd.go b/pkg/provision/providers/vm/dhcpd.go index 16547f81e..fae68661b 100644 --- a/pkg/provision/providers/vm/dhcpd.go +++ b/pkg/provision/providers/vm/dhcpd.go @@ -23,6 +23,7 @@ import ( "github.com/insomniacslk/dhcp/iana" "golang.org/x/sync/errgroup" + "github.com/talos-systems/talos/pkg/machinery/generic/slices" "github.com/talos-systems/talos/pkg/provision" ) @@ -260,10 +261,7 @@ func (p *Provisioner) CreateDHCPd(state *State, clusterReq provision.ClusterRequ return err } - gatewayAddrs := make([]string, len(clusterReq.Network.GatewayAddrs)) - for j := range gatewayAddrs { - gatewayAddrs[j] = clusterReq.Network.GatewayAddrs[j].String() - } + gatewayAddrs := slices.Map(clusterReq.Network.GatewayAddrs, net.IP.String) args := []string{ "dhcpd-launch", diff --git a/pkg/provision/providers/vm/network.go b/pkg/provision/providers/vm/network.go index af6358477..8892e6646 100644 --- a/pkg/provision/providers/vm/network.go +++ b/pkg/provision/providers/vm/network.go @@ -21,6 +21,7 @@ import ( "github.com/jsimonetti/rtnetlink" talosnet "github.com/talos-systems/net" + "github.com/talos-systems/talos/pkg/machinery/generic/slices" "github.com/talos-systems/talos/pkg/provision" ) @@ -81,10 +82,7 @@ func (p *Provisioner) CreateNetwork(ctx context.Context, state *State, network p fakeIPs[j] = talosnet.FormatCIDR(fakeIP, network.CIDRs[j]) } - gatewayAddrs := make([]string, len(network.GatewayAddrs)) - for j := range gatewayAddrs { - gatewayAddrs[j] = network.GatewayAddrs[j].String() - } + gatewayAddrs := slices.Map(network.GatewayAddrs, net.IP.String) containerID := uuid.New().String() runtimeConf := libcni.RuntimeConf{