diff --git a/.github/workflows/lint.yaml b/.github/workflows/lint.yaml index 4a64293f19..966033c3f5 100644 --- a/.github/workflows/lint.yaml +++ b/.github/workflows/lint.yaml @@ -39,7 +39,6 @@ jobs: exit 1 fi - # https://github.com/golangci/golangci-lint-action?tab=readme-ov-file#verify - name: Verify linter configuration and Lint go code uses: golangci/golangci-lint-action@v9 diff --git a/.golangci.yml b/.golangci.yml index fba7224513..674bcb77f5 100644 --- a/.golangci.yml +++ b/.golangci.yml @@ -31,6 +31,7 @@ linters: - gocritic # Analyze source code for various issues, including bugs, performance hiccups, and non-idiomatic coding practices. https://golangci-lint.run/docs/linters/configuration/#gocritic - gochecknoinits # Checks that there are no init() functions in the code. https://golangci-lint.run/docs/linters/configuration/#gochecknoinits - goconst # Finds repeated strings that could be replaced by a constant. https://golangci-lint.run/docs/linters/configuration/#goconst + - modernize # A suite of analyzers that suggest simplifications to Go code, using modern language and library features. https://golangci-lint.run/docs/linters/configuration/#modernize # tests - testifylint # Checks usage of github.com/stretchr/testify. https://golangci-lint.run/docs/linters/configuration/#testifylint diff --git a/apis/v1alpha1/dnsendpoint.go b/apis/v1alpha1/dnsendpoint.go index 522bd1beeb..a4356e81b7 100644 --- a/apis/v1alpha1/dnsendpoint.go +++ b/apis/v1alpha1/dnsendpoint.go @@ -35,17 +35,17 @@ import ( // +versionName=v1alpha1 type DNSEndpoint struct { metav1.TypeMeta `json:",inline"` - metav1.ObjectMeta `json:"metadata,omitempty"` + metav1.ObjectMeta `json:"metadata"` - Spec DNSEndpointSpec `json:"spec,omitempty"` - Status DNSEndpointStatus `json:"status,omitempty"` + Spec DNSEndpointSpec `json:"spec"` + Status DNSEndpointStatus `json:"status"` } // +k8s:deepcopy-gen:interfaces=k8s.io/apimachinery/pkg/runtime.Object // DNSEndpointList is a list of DNSEndpoint objects type DNSEndpointList struct { metav1.TypeMeta `json:",inline"` - metav1.ListMeta `json:"metadata,omitempty"` + metav1.ListMeta `json:"metadata"` Items []DNSEndpoint `json:"items"` } diff --git a/endpoint/domain_filter_test.go b/endpoint/domain_filter_test.go index 3287434642..016f533a29 100644 --- a/endpoint/domain_filter_test.go +++ b/endpoint/domain_filter_test.go @@ -635,19 +635,19 @@ func TestRegexDomainFilterIsConfigured(t *testing.T) { func TestDomainFilterDeserializeError(t *testing.T) { for _, tt := range []struct { name string - serialized map[string]interface{} + serialized map[string]any expectedError string }{ { name: "invalid json", - serialized: map[string]interface{}{ + serialized: map[string]any{ "include": 3, }, expectedError: "json: cannot unmarshal number into Go struct field domainFilterSerde.include of type []string", }, { name: "include and regex", - serialized: map[string]interface{}{ + serialized: map[string]any{ "include": []string{"example.com"}, "regexInclude": "example.com", }, @@ -655,7 +655,7 @@ func TestDomainFilterDeserializeError(t *testing.T) { }, { name: "exclude and regex", - serialized: map[string]interface{}{ + serialized: map[string]any{ "exclude": []string{"example.com"}, "regexInclude": "example.com", }, @@ -663,7 +663,7 @@ func TestDomainFilterDeserializeError(t *testing.T) { }, { name: "include and regexExclude", - serialized: map[string]interface{}{ + serialized: map[string]any{ "include": []string{"example.com"}, "regexExclude": "example.com", }, @@ -671,7 +671,7 @@ func TestDomainFilterDeserializeError(t *testing.T) { }, { name: "exclude and regexExclude", - serialized: map[string]interface{}{ + serialized: map[string]any{ "exclude": []string{"example.com"}, "regexExclude": "example.com", }, @@ -679,14 +679,14 @@ func TestDomainFilterDeserializeError(t *testing.T) { }, { name: "invalid regex", - serialized: map[string]interface{}{ + serialized: map[string]any{ "regexInclude": "*", }, expectedError: "invalid regexInclude: error parsing regexp: missing argument to repetition operator: `*`", }, { name: "invalid regexExclude", - serialized: map[string]interface{}{ + serialized: map[string]any{ "regexExclude": "*", }, expectedError: "invalid regexExclude: error parsing regexp: missing argument to repetition operator: `*`", diff --git a/internal/gen/docs/utils/utils_test.go b/internal/gen/docs/utils/utils_test.go index b330e9f9e3..1438938f90 100644 --- a/internal/gen/docs/utils/utils_test.go +++ b/internal/gen/docs/utils/utils_test.go @@ -50,17 +50,17 @@ func TestWriteToFile(t *testing.T) { func TestFuncs(t *testing.T) { tests := []struct { tpl, expect string - vars interface{} + vars any }{ { tpl: `{{ backtick 3 }}`, expect: "```", - vars: map[string]interface{}{}, + vars: map[string]any{}, }, { tpl: `{{ capitalize .name }}`, expect: "Capital", - vars: map[string]interface{}{"name": "capital"}, + vars: map[string]any{"name": "capital"}, }, } diff --git a/internal/testutils/endpoint.go b/internal/testutils/endpoint.go index 0a33d3a218..277d34e374 100644 --- a/internal/testutils/endpoint.go +++ b/internal/testutils/endpoint.go @@ -145,7 +145,7 @@ func GenerateTestEndpointsByType(typeCounts map[string]int) []*endpoint.Endpoint var result []*endpoint.Endpoint idx := 0 for rt, count := range typeCounts { - for i := 0; i < count; i++ { + for range count { result = append(result, &endpoint.Endpoint{ DNSName: fmt.Sprintf("%s-%d.example.com", strings.ToLower(rt), idx), Targets: endpoint.Targets{fmt.Sprintf("192.0.2.%d", idx)}, diff --git a/pkg/apis/externaldns/types.go b/pkg/apis/externaldns/types.go index f86ed7d5ee..21531a4c20 100644 --- a/pkg/apis/externaldns/types.go +++ b/pkg/apis/externaldns/types.go @@ -462,7 +462,7 @@ func (cfg *Config) String() string { // prevent logging of sensitive information temp := *cfg - t := reflect.TypeOf(temp) + t := reflect.TypeFor[Config]() for i := 0; i < t.NumField(); i++ { f := t.Field(i) if val, ok := f.Tag.Lookup("secure"); ok && val == "yes" { diff --git a/pkg/events/controller.go b/pkg/events/controller.go index 9c13fa0fb0..e8a4b91568 100644 --- a/pkg/events/controller.go +++ b/pkg/events/controller.go @@ -93,7 +93,7 @@ func (ec *Controller) run(ctx context.Context) { defer log.Info("event Controller terminated") defer utilruntime.HandleCrash() var waitGroup wait.Group - for i := 0; i < workers; i++ { + for range workers { waitGroup.StartWithContext(ctx, func(ctx context.Context) { for ec.processNextWorkItem(ctx) { } diff --git a/pkg/events/controller_test.go b/pkg/events/controller_test.go index 3141f0a7bd..b8b93f5fde 100644 --- a/pkg/events/controller_test.go +++ b/pkg/events/controller_test.go @@ -17,7 +17,6 @@ limitations under the License. package events import ( - "context" "fmt" "net/http" "net/http/httptest" @@ -68,7 +67,7 @@ users: user: token: fake-token ` - err = os.WriteFile(mockKubeCfgPath, []byte(fmt.Sprintf(kubeCfgTemplate, svr.URL)), os.FileMode(0755)) + err = os.WriteFile(mockKubeCfgPath, fmt.Appendf(nil, kubeCfgTemplate, svr.URL), os.FileMode(0755)) require.NoError(t, err) cfg := NewConfig( @@ -95,8 +94,7 @@ func TestController_Run_NoEmitEvents(t *testing.T) { func TestController_Run_EmitEvents(t *testing.T) { log.SetLevel(log.ErrorLevel) - ctx, cancel := context.WithCancel(context.Background()) - defer cancel() + ctx := t.Context() eventCreated := make(chan struct{}) kubeClient := fake.NewClientset() diff --git a/pkg/http/http_benchmark_test.go b/pkg/http/http_benchmark_test.go index efdf4e216e..aaf8991d6c 100644 --- a/pkg/http/http_benchmark_test.go +++ b/pkg/http/http_benchmark_test.go @@ -85,7 +85,7 @@ func TestRoundTripper_Concurrent(t *testing.T) { var wg sync.WaitGroup wg.Add(numGoroutines) - for i := 0; i < numGoroutines; i++ { + for range numGoroutines { go func() { defer wg.Done() body, err := api.doStuff() diff --git a/provider/akamai/akamai.go b/provider/akamai/akamai.go index b513150bf5..46202072f6 100644 --- a/provider/akamai/akamai.go +++ b/provider/akamai/akamai.go @@ -234,7 +234,7 @@ func (p AkamaiProvider) Records(context.Context) ([]*endpoint.Endpoint, error) { log.Debugf("Skipping endpoint. Record name %s doesn't match containing zone %s.", recordset.Name, zone) continue } - var temp interface{} = int64(recordset.TTL) + var temp any = int64(recordset.TTL) ttl := endpoint.TTL(temp.(int64)) endpoints = append(endpoints, endpoint.NewEndpointWithTTL(recordset.Name, recordset.Type, @@ -352,7 +352,7 @@ func trimTxtRdata(rdata []string, rtype string) []string { } func ttlAsInt(src endpoint.TTL) int { - var temp interface{} = int64(src) + var temp any = int64(src) temp64 := temp.(int64) var ttl = defaultTTL if temp64 > 0 && temp64 <= int64(maxInt) { diff --git a/provider/akamai/akamai_test.go b/provider/akamai/akamai_test.go index df8b465c80..0079228263 100644 --- a/provider/akamai/akamai_test.go +++ b/provider/akamai/akamai_test.go @@ -34,9 +34,9 @@ import ( type edgednsStubData struct { objType string // zone, record, recordsets - output []interface{} - updateRecords []interface{} - createRecords []interface{} + output []any + updateRecords []any + createRecords []any } type edgednsStub struct { @@ -73,7 +73,7 @@ func (r *edgednsStub) createStubDataEntry(objtype string) { return } -func (r *edgednsStub) setOutput(objtype string, output []interface{}) { +func (r *edgednsStub) setOutput(objtype string, output []any) { log.Debugf("Setting output to %v", output) r.createStubDataEntry(objtype) stubdata := r.stubData[objtype] @@ -83,7 +83,7 @@ func (r *edgednsStub) setOutput(objtype string, output []interface{}) { return } -func (r *edgednsStub) setUpdateRecords(objtype string, records []interface{}) { +func (r *edgednsStub) setUpdateRecords(objtype string, records []any) { log.Debugf("Setting updaterecords to %v", records) r.createStubDataEntry(objtype) stubdata := r.stubData[objtype] @@ -93,7 +93,7 @@ func (r *edgednsStub) setUpdateRecords(objtype string, records []interface{}) { return } -func (r *edgednsStub) setCreateRecords(objtype string, records []interface{}) { +func (r *edgednsStub) setCreateRecords(objtype string, records []any) { log.Debugf("Setting createrecords to %v", records) r.createStubDataEntry(objtype) stubdata := r.stubData[objtype] @@ -157,7 +157,7 @@ func TestFetchZonesZoneIDFilter(t *testing.T) { idfilter := provider.NewZoneIDFilter([]string{"Test"}) c, err := createAkamaiStubProvider(stub, domfilter, idfilter) assert.NoError(t, err) - stub.setOutput("zone", []interface{}{"test1.testzone.com", "test2.testzone.com"}) + stub.setOutput("zone", []any{"test1.testzone.com", "test2.testzone.com"}) x, _ := c.fetchZones() y, err := json.Marshal(x) @@ -173,7 +173,7 @@ func TestFetchZonesEmpty(t *testing.T) { idfilter := provider.NewZoneIDFilter([]string{"Nonexistent"}) c, err := createAkamaiStubProvider(stub, domfilter, idfilter) require.NoError(t, err) - stub.setOutput("zone", []interface{}{}) + stub.setOutput("zone", []any{}) x, _ := c.fetchZones() y, err := json.Marshal(x) @@ -190,8 +190,8 @@ func TestAkamaiRecords(t *testing.T) { idfilter := provider.ZoneIDFilter{} c, err := createAkamaiStubProvider(stub, domfilter, idfilter) require.NoError(t, err) - stub.setOutput("zone", []interface{}{"test1.testzone.com"}) - recordsets := make([]interface{}, 0) + stub.setOutput("zone", []any{"test1.testzone.com"}) + recordsets := make([]any, 0) recordsets = append(recordsets, dns.Recordset{ Name: "www.example.com", Type: endpoint.RecordTypeA, @@ -225,8 +225,8 @@ func TestAkamaiRecordsEmpty(t *testing.T) { idfilter := provider.NewZoneIDFilter([]string{"Nonexistent"}) c, err := createAkamaiStubProvider(stub, domfilter, idfilter) require.NoError(t, err) - stub.setOutput("zone", []interface{}{"test1.testzone.com"}) - recordsets := make([]interface{}, 0) + stub.setOutput("zone", []any{"test1.testzone.com"}) + recordsets := make([]any, 0) stub.setOutput("recordset", recordsets) x, _ := c.Records(context.Background()) @@ -239,8 +239,8 @@ func TestAkamaiRecordsFilters(t *testing.T) { idfilter := provider.ZoneIDFilter{} c, err := createAkamaiStubProvider(stub, domfilter, idfilter) assert.NoError(t, err) - stub.setOutput("zone", []interface{}{"www.exclude.me"}) - recordsets := make([]interface{}, 0) + stub.setOutput("zone", []any{"www.exclude.me"}) + recordsets := make([]any, 0) recordsets = append(recordsets, dns.Recordset{ Name: "www.example.com", Type: endpoint.RecordTypeA, @@ -374,7 +374,7 @@ func TestAkamaiApplyChanges(t *testing.T) { c, err := createAkamaiStubProvider(stub, domfilter, idfilter) assert.NoError(t, err) - stub.setOutput("zone", []interface{}{"example.com"}) + stub.setOutput("zone", []any{"example.com"}) changes := &plan.Changes{} changes.Create = []*endpoint.Endpoint{ {DNSName: "www.example.com", RecordType: "A", Targets: endpoint.Targets{"target"}, RecordTTL: 300}, diff --git a/provider/alibabacloud/alibaba_cloud.go b/provider/alibabacloud/alibaba_cloud.go index fcb750f4f8..b9361af0e2 100644 --- a/provider/alibabacloud/alibaba_cloud.go +++ b/provider/alibabacloud/alibaba_cloud.go @@ -20,6 +20,7 @@ import ( "context" "fmt" "os" + "slices" "sort" "strings" "sync" @@ -601,13 +602,9 @@ func (p *AlibabaCloudProvider) deleteRecords(recordMap map[string][]alidns.Recor value = p.unescapeTXTRecordValue(value) } - for _, target := range endpoint.Targets { - // Find matched record to delete - if value == target { - p.deleteRecord(record.RecordId) - found = true - break - } + if slices.Contains(endpoint.Targets, value) { + p.deleteRecord(record.RecordId) + found = true } } if !found { @@ -955,13 +952,9 @@ func (p *AlibabaCloudProvider) deletePrivateZoneRecords(zones map[string]*alibab if record.Type == "TXT" { value = p.unescapeTXTRecordValue(value) } - for _, target := range endpoint.Targets { - // Find matched record to delete - if value == target { - p.deletePrivateZoneRecord(record.RecordId) - found = true - break - } + if slices.Contains(endpoint.Targets, value) { + p.deletePrivateZoneRecord(record.RecordId) + found = true } } } @@ -1047,14 +1040,7 @@ func (p *AlibabaCloudProvider) updatePrivateZoneRecords(zones map[string]*alibab if record.Type == "TXT" { value = p.unescapeTXTRecordValue(value) } - found := false - for _, target := range endpoint.Targets { - // Find matched record to delete - if value == target { - found = true - break - } - } + found := slices.Contains(endpoint.Targets, value) if found { if !p.equalsPrivateZone(record, endpoint) { // Update record diff --git a/provider/aws/aws.go b/provider/aws/aws.go index 68d6e62b9d..417e87eb5d 100644 --- a/provider/aws/aws.go +++ b/provider/aws/aws.go @@ -1112,12 +1112,9 @@ func findChangesInQueue(changes Route53Changes, queue Route53Changes) (Route53Ch for _, c := range changes { found := false - for _, qc := range queue { - if c == qc { - foundChanges = append(foundChanges, c) - found = true - break - } + if slices.Contains(queue, c) { + foundChanges = append(foundChanges, c) + found = true } if !found { notFoundChanges = append(notFoundChanges, c) diff --git a/provider/aws/aws_test.go b/provider/aws/aws_test.go index c5ad1529fa..1738aa0d54 100644 --- a/provider/aws/aws_test.go +++ b/provider/aws/aws_test.go @@ -20,6 +20,7 @@ import ( "bytes" "context" "fmt" + "maps" "math" "net" "sort" @@ -68,7 +69,7 @@ type Route53APIStub struct { // being called. // // Route53APIStub.MockMethod("MyMethod", arg1, arg2) -func (r *Route53APIStub) MockMethod(method string, args ...interface{}) *mock.Call { +func (r *Route53APIStub) MockMethod(method string, args ...any) *mock.Call { return r.m.On(method, args...) } @@ -284,7 +285,7 @@ func (m *dynamicMock) ChangeResourceRecordSets(input *route53.ChangeResourceReco return nil, args.Error(1) } -func (m *dynamicMock) isMocked(method string, arguments ...interface{}) bool { +func (m *dynamicMock) isMocked(method string, arguments ...any) bool { for _, call := range m.ExpectedCalls { if call.Method == method && call.Repeatability > -1 { _, diffCount := call.Arguments.Diff(arguments) @@ -316,12 +317,8 @@ func TestAWSZones(t *testing.T) { } allZones := map[string]*route53types.HostedZone{} - for k, v := range publicZones { - allZones[k] = v - } - for k, v := range privateZones { - allZones[k] = v - } + maps.Copy(allZones, publicZones) + maps.Copy(allZones, privateZones) noZones := map[string]*route53types.HostedZone{} @@ -1607,7 +1604,7 @@ func TestAWSsubmitChanges(t *testing.T) { const hosts = defaultBatchChangeSize / subnets endpoints := make([]*endpoint.Endpoint, 0) - for i := 0; i < subnets; i++ { + for i := range subnets { for j := 1; j < (hosts + 1); j++ { hostname := fmt.Sprintf("subnet%dhost%d.zone-1.ext-dns-test-2.teapot.zalan.do", i, j) ip := fmt.Sprintf("1.1.%d.%d", i, j) @@ -2245,7 +2242,7 @@ func TestAWSCanonicalHostedZoneNotExist(t *testing.T) { } func BenchmarkTestAWSCanonicalHostedZone(b *testing.B) { - for i := 0; i < b.N; i++ { + for b.Loop() { for suffix := range canonicalHostedZones { _ = canonicalHostedZone(fmt.Sprintf("foo.%s", suffix)) } @@ -2253,7 +2250,7 @@ func BenchmarkTestAWSCanonicalHostedZone(b *testing.B) { } func BenchmarkTestAWSNonCanonicalHostedZone(b *testing.B) { - for i := 0; i < b.N; i++ { + for b.Loop() { for range canonicalHostedZones { _ = canonicalHostedZone("extremely.long.zone-2.ext.dns.test.zone.non.canonical.example.com") } diff --git a/provider/civo/civo_test.go b/provider/civo/civo_test.go index 0afa75e8e0..24618d2ec2 100644 --- a/provider/civo/civo_test.go +++ b/provider/civo/civo_test.go @@ -66,7 +66,6 @@ func TestCivoProviderZones(t *testing.T) { assert.NoError(t, err) // Check if the return is a DNSDomain type - assert.Equal(t, reflect.TypeOf(zones), reflect.TypeOf(expected)) assert.ElementsMatch(t, zones, expected) } @@ -1169,7 +1168,7 @@ func TestCivoChangesEmpty(t *testing.T) { // This function is an adapted copy of the testify package's ElementsMatch function with the // call to ObjectsAreEqual replaced with cmp.Equal which better handles struct's with pointers to // other structs. It also ignores ordering when comparing unlike cmp.Equal. -func elementsMatch(t *testing.T, listA, listB interface{}, msgAndArgs ...interface{}) bool { +func elementsMatch(t *testing.T, listA, listB any, msgAndArgs ...any) bool { switch { case listA == nil && listB == nil: return true @@ -1202,10 +1201,10 @@ func elementsMatch(t *testing.T, listA, listB interface{}, msgAndArgs ...interfa // Mark indexes in bValue that we already used visited := make([]bool, bLen) - for i := 0; i < aLen; i++ { + for i := range aLen { element := aValue.Index(i).Interface() found := false - for j := 0; j < bLen; j++ { + for j := range bLen { if visited[j] { continue } @@ -1223,7 +1222,7 @@ func elementsMatch(t *testing.T, listA, listB interface{}, msgAndArgs ...interfa return true } -func isEmpty(xs interface{}) bool { +func isEmpty(xs any) bool { if xs != nil { objValue := reflect.ValueOf(xs) return objValue.Len() == 0 diff --git a/provider/cloudflare/cloudflare_test.go b/provider/cloudflare/cloudflare_test.go index cae7a54c4f..7d0e5bad4b 100644 --- a/provider/cloudflare/cloudflare_test.go +++ b/provider/cloudflare/cloudflare_test.go @@ -481,7 +481,7 @@ func getCustomHostnameIdxByID(chs []cloudflarev0.CustomHostname, customHostnameI return -1 } -func AssertActions(t *testing.T, provider *CloudFlareProvider, endpoints []*endpoint.Endpoint, actions []MockAction, managedRecords []string, args ...interface{}) { +func AssertActions(t *testing.T, provider *CloudFlareProvider, endpoints []*endpoint.Endpoint, actions []MockAction, managedRecords []string, args ...any) { t.Helper() var client *mockCloudFlareClient @@ -2709,7 +2709,7 @@ func TestCloudflareListCustomHostnamesWithPagionation(t *testing.T) { const CustomHostnamesNumber = 342 var generatedEndpoints []*endpoint.Endpoint - for i := 0; i < CustomHostnamesNumber; i++ { + for i := range CustomHostnamesNumber { ep := []*endpoint.Endpoint{ { DNSName: fmt.Sprintf("host-%d.foo.bar.com", i), diff --git a/provider/digitalocean/digital_ocean_test.go b/provider/digitalocean/digital_ocean_test.go index deee1a8cd9..ec2d62fccd 100644 --- a/provider/digitalocean/digital_ocean_test.go +++ b/provider/digitalocean/digital_ocean_test.go @@ -183,7 +183,7 @@ func (m *mockDigitalOceanRecordsFail) Records(ctx context.Context, domain string return []godo.DomainRecord{}, nil, fmt.Errorf("Failed to get records") } -func isEmpty(xs interface{}) bool { +func isEmpty(xs any) bool { if xs != nil { objValue := reflect.ValueOf(xs) return objValue.Len() == 0 @@ -194,7 +194,7 @@ func isEmpty(xs interface{}) bool { // This function is an adapted copy of the testify package's ElementsMatch function with the // call to ObjectsAreEqual replaced with cmp.Equal which better handles struct's with pointers to // other structs. It also ignores ordering when comparing unlike cmp.Equal. -func elementsMatch(t *testing.T, listA, listB interface{}, msgAndArgs ...interface{}) bool { +func elementsMatch(t *testing.T, listA, listB any, msgAndArgs ...any) bool { switch { case listA == nil && listB == nil: return true @@ -227,10 +227,10 @@ func elementsMatch(t *testing.T, listA, listB interface{}, msgAndArgs ...interfa // Mark indexes in bValue that we already used visited := make([]bool, bLen) - for i := 0; i < aLen; i++ { + for i := range aLen { element := aValue.Index(i).Interface() found := false - for j := 0; j < bLen; j++ { + for j := range bLen { if visited[j] { continue } @@ -254,8 +254,8 @@ func TestElementsMatch(t *testing.T) { mockT := new(testing.T) cases := []struct { - expected interface{} - actual interface{} + expected any + actual any result bool }{ // matching diff --git a/provider/godaddy/client.go b/provider/godaddy/client.go index 2efb7824df..26928f834c 100644 --- a/provider/godaddy/client.go +++ b/provider/godaddy/client.go @@ -150,57 +150,57 @@ func NewClient(useOTE bool, apiKey, apiSecret string) (*Client, error) { // // Get is a wrapper for the GET method -func (c *Client) Get(url string, resType interface{}) error { +func (c *Client) Get(url string, resType any) error { return c.CallAPI("GET", url, nil, resType) } // Patch is a wrapper for the PATCH method -func (c *Client) Patch(url string, reqBody, resType interface{}) error { +func (c *Client) Patch(url string, reqBody, resType any) error { return c.CallAPI("PATCH", url, reqBody, resType) } // Post is a wrapper for the POST method -func (c *Client) Post(url string, reqBody, resType interface{}) error { +func (c *Client) Post(url string, reqBody, resType any) error { return c.CallAPI("POST", url, reqBody, resType) } // Put is a wrapper for the PUT method -func (c *Client) Put(url string, reqBody, resType interface{}) error { +func (c *Client) Put(url string, reqBody, resType any) error { return c.CallAPI("PUT", url, reqBody, resType) } // Delete is a wrapper for the DELETE method -func (c *Client) Delete(url string, resType interface{}) error { +func (c *Client) Delete(url string, resType any) error { return c.CallAPI("DELETE", url, nil, resType) } // GetWithContext is a wrapper for the GET method -func (c *Client) GetWithContext(ctx context.Context, url string, resType interface{}) error { +func (c *Client) GetWithContext(ctx context.Context, url string, resType any) error { return c.CallAPIWithContext(ctx, "GET", url, nil, resType) } // PatchWithContext is a wrapper for the PATCH method -func (c *Client) PatchWithContext(ctx context.Context, url string, reqBody, resType interface{}) error { +func (c *Client) PatchWithContext(ctx context.Context, url string, reqBody, resType any) error { return c.CallAPIWithContext(ctx, "PATCH", url, reqBody, resType) } // PostWithContext is a wrapper for the POST method -func (c *Client) PostWithContext(ctx context.Context, url string, reqBody, resType interface{}) error { +func (c *Client) PostWithContext(ctx context.Context, url string, reqBody, resType any) error { return c.CallAPIWithContext(ctx, "POST", url, reqBody, resType) } // PutWithContext is a wrapper for the PUT method -func (c *Client) PutWithContext(ctx context.Context, url string, reqBody, resType interface{}) error { +func (c *Client) PutWithContext(ctx context.Context, url string, reqBody, resType any) error { return c.CallAPIWithContext(ctx, "PUT", url, reqBody, resType) } // DeleteWithContext is a wrapper for the DELETE method -func (c *Client) DeleteWithContext(ctx context.Context, url string, resType interface{}) error { +func (c *Client) DeleteWithContext(ctx context.Context, url string, resType any) error { return c.CallAPIWithContext(ctx, "DELETE", url, nil, resType) } // NewRequest returns a new HTTP request -func (c *Client) NewRequest(method, path string, reqBody interface{}) (*http.Request, error) { +func (c *Client) NewRequest(method, path string, reqBody any) (*http.Request, error) { var body []byte var err error @@ -286,7 +286,7 @@ func (c *Client) Do(req *http.Request) (*http.Response, error) { // // If everything went fine, unmarshall response into resType and return nil // otherwise, return the error -func (c *Client) CallAPI(method, path string, reqBody, resType interface{}) error { +func (c *Client) CallAPI(method, path string, reqBody, resType any) error { return c.CallAPIWithContext(context.Background(), method, path, reqBody, resType) } @@ -310,7 +310,7 @@ func (c *Client) CallAPI(method, path string, reqBody, resType interface{}) erro // // If everything went fine, unmarshall response into resType and return nil // otherwise, return the error -func (c *Client) CallAPIWithContext(ctx context.Context, method, path string, reqBody, resType interface{}) error { +func (c *Client) CallAPIWithContext(ctx context.Context, method, path string, reqBody, resType any) error { req, err := c.NewRequest(method, path, reqBody) if err != nil { return err @@ -325,7 +325,7 @@ func (c *Client) CallAPIWithContext(ctx context.Context, method, path string, re // UnmarshalResponse checks the response and unmarshals it into the response // type if needed Helper function, called from CallAPI -func (c *Client) UnmarshalResponse(response *http.Response, resType interface{}) error { +func (c *Client) UnmarshalResponse(response *http.Response, resType any) error { // Read all the response body defer response.Body.Close() body, err := io.ReadAll(response.Body) @@ -355,7 +355,7 @@ func (c *Client) UnmarshalResponse(response *http.Response, resType interface{}) } func (c *Client) validate() error { - var response interface{} + var response any if err := c.Get(domainsURI, response); err != nil { return err diff --git a/provider/godaddy/godaddy.go b/provider/godaddy/godaddy.go index d732f79113..94b6f16b72 100644 --- a/provider/godaddy/godaddy.go +++ b/provider/godaddy/godaddy.go @@ -47,11 +47,11 @@ var actionNames = []string{ } type gdClient interface { - Patch(string, interface{}, interface{}) error - Post(string, interface{}, interface{}) error - Put(string, interface{}, interface{}) error - Get(string, interface{}) error - Delete(string, interface{}) error + Patch(string, any, any) error + Post(string, any, any) error + Put(string, any, any) error + Get(string, any) error + Delete(string, any) error } // GDProvider declare GoDaddy provider @@ -596,7 +596,7 @@ func maxOf(vars ...int64) int64 { return slices.Max(vars) } -func toString(obj interface{}) string { +func toString(obj any) string { b, err := json.MarshalIndent(obj, "", " ") if err != nil { return fmt.Sprintf("<%v>", err) diff --git a/provider/godaddy/godaddy_test.go b/provider/godaddy/godaddy_test.go index 344391f88f..2e6b8ac728 100644 --- a/provider/godaddy/godaddy_test.go +++ b/provider/godaddy/godaddy_test.go @@ -27,6 +27,7 @@ import ( "github.com/stretchr/testify/assert" "github.com/stretchr/testify/mock" "github.com/stretchr/testify/require" + "sigs.k8s.io/external-dns/endpoint" "sigs.k8s.io/external-dns/plan" ) @@ -47,7 +48,7 @@ var ( zoneNameExampleNet string = "example.net" ) -func (c *mockGoDaddyClient) Post(endpoint string, input interface{}, output interface{}) error { +func (c *mockGoDaddyClient) Post(endpoint string, input any, output any) error { log.Infof("POST: %s - %v", endpoint, input) stub := c.Called(endpoint, input) data, err := json.Marshal(stub.Get(0)) @@ -57,7 +58,7 @@ func (c *mockGoDaddyClient) Post(endpoint string, input interface{}, output inte return stub.Error(1) } -func (c *mockGoDaddyClient) Patch(endpoint string, input interface{}, output interface{}) error { +func (c *mockGoDaddyClient) Patch(endpoint string, input any, output any) error { log.Infof("PATCH: %s - %v", endpoint, input) stub := c.Called(endpoint, input) data, err := json.Marshal(stub.Get(0)) @@ -67,7 +68,7 @@ func (c *mockGoDaddyClient) Patch(endpoint string, input interface{}, output int return stub.Error(1) } -func (c *mockGoDaddyClient) Put(endpoint string, input interface{}, output interface{}) error { +func (c *mockGoDaddyClient) Put(endpoint string, input any, output any) error { log.Infof("PUT: %s - %v", endpoint, input) stub := c.Called(endpoint, input) data, err := json.Marshal(stub.Get(0)) @@ -77,7 +78,7 @@ func (c *mockGoDaddyClient) Put(endpoint string, input interface{}, output inter return stub.Error(1) } -func (c *mockGoDaddyClient) Get(endpoint string, output interface{}) error { +func (c *mockGoDaddyClient) Get(endpoint string, output any) error { log.Infof("GET: %s", endpoint) stub := c.Called(endpoint) data, err := json.Marshal(stub.Get(0)) @@ -87,7 +88,7 @@ func (c *mockGoDaddyClient) Get(endpoint string, output interface{}) error { return stub.Error(1) } -func (c *mockGoDaddyClient) Delete(endpoint string, output interface{}) error { +func (c *mockGoDaddyClient) Delete(endpoint string, output any) error { log.Infof("DELETE: %s", endpoint) stub := c.Called(endpoint) data, err := json.Marshal(stub.Get(0)) diff --git a/provider/google/google_test.go b/provider/google/google_test.go index 2596325446..bc30bc4034 100644 --- a/provider/google/google_test.go +++ b/provider/google/google_test.go @@ -20,6 +20,7 @@ import ( "errors" "fmt" "net/http" + "slices" "sort" "strings" "testing" @@ -192,10 +193,8 @@ func isValidRecordSet(recordSet *dns.ResourceRecordSet) bool { } } case endpoint.RecordTypeA, endpoint.RecordTypeTXT: - for _, rrd := range recordSet.Rrdatas { - if hasTrailingDot(rrd) { - return false - } + if slices.ContainsFunc(recordSet.Rrdatas, hasTrailingDot) { + return false } default: panic("unhandled record type") diff --git a/provider/inmemory/inmemory.go b/provider/inmemory/inmemory.go index b17ef900e7..f45fd0b1b9 100644 --- a/provider/inmemory/inmemory.go +++ b/provider/inmemory/inmemory.go @@ -19,6 +19,7 @@ package inmemory import ( "context" "errors" + "maps" "strings" log "github.com/sirupsen/logrus" @@ -204,9 +205,7 @@ func copyEndpoints(endpoints []*endpoint.Endpoint) []*endpoint.Endpoint { for _, ep := range endpoints { newEp := endpoint.NewEndpointWithTTL(ep.DNSName, ep.RecordType, ep.RecordTTL, ep.Targets...).WithSetIdentifier(ep.SetIdentifier) newEp.Labels = endpoint.NewLabels() - for k, v := range ep.Labels { - newEp.Labels[k] = v - } + maps.Copy(newEp.Labels, ep.Labels) newEp.ProviderSpecific = append(endpoint.ProviderSpecific(nil), ep.ProviderSpecific...) records = append(records, newEp) } diff --git a/provider/ns1/ns1.go b/provider/ns1/ns1.go index 135235ad44..d41f9bf69d 100644 --- a/provider/ns1/ns1.go +++ b/provider/ns1/ns1.go @@ -183,10 +183,7 @@ func (p *NS1Provider) ns1BuildRecord(zoneName string, change *ns1Change) *dns.Re record.AddAnswer(dns.NewAnswer(strings.Split(v, " "))) } // set default ttl, but respect minTTLSeconds - ttl := defaultTTL - if p.minTTLSeconds > ttl { - ttl = p.minTTLSeconds - } + ttl := max(p.minTTLSeconds, defaultTTL) if change.Endpoint.RecordTTL.IsConfigured() { ttl = int(change.Endpoint.RecordTTL) } diff --git a/provider/ovh/ovh_test.go b/provider/ovh/ovh_test.go index 50fdd78a2a..cd721d58e1 100644 --- a/provider/ovh/ovh_test.go +++ b/provider/ovh/ovh_test.go @@ -31,6 +31,7 @@ import ( "github.com/stretchr/testify/assert" "github.com/stretchr/testify/mock" "go.uber.org/ratelimit" + "sigs.k8s.io/external-dns/endpoint" "sigs.k8s.io/external-dns/plan" ) @@ -39,7 +40,7 @@ type mockOvhClient struct { mock.Mock } -func (c *mockOvhClient) PostWithContext(ctx context.Context, endpoint string, input interface{}, output interface{}) error { +func (c *mockOvhClient) PostWithContext(ctx context.Context, endpoint string, input any, output any) error { stub := c.Called(endpoint, input) data, err := json.Marshal(stub.Get(0)) if err != nil { @@ -49,7 +50,7 @@ func (c *mockOvhClient) PostWithContext(ctx context.Context, endpoint string, in return stub.Error(1) } -func (c *mockOvhClient) PutWithContext(ctx context.Context, endpoint string, input interface{}, output interface{}) error { +func (c *mockOvhClient) PutWithContext(ctx context.Context, endpoint string, input any, output any) error { stub := c.Called(endpoint, input) data, err := json.Marshal(stub.Get(0)) if err != nil { @@ -59,7 +60,7 @@ func (c *mockOvhClient) PutWithContext(ctx context.Context, endpoint string, inp return stub.Error(1) } -func (c *mockOvhClient) GetWithContext(ctx context.Context, endpoint string, output interface{}) error { +func (c *mockOvhClient) GetWithContext(ctx context.Context, endpoint string, output any) error { stub := c.Called(endpoint) data, err := json.Marshal(stub.Get(0)) if err != nil { @@ -69,7 +70,7 @@ func (c *mockOvhClient) GetWithContext(ctx context.Context, endpoint string, out return stub.Error(1) } -func (c *mockOvhClient) DeleteWithContext(ctx context.Context, endpoint string, output interface{}) error { +func (c *mockOvhClient) DeleteWithContext(ctx context.Context, endpoint string, output any) error { stub := c.Called(endpoint) data, err := json.Marshal(stub.Get(0)) if err != nil { diff --git a/provider/pdns/pdns.go b/provider/pdns/pdns.go index 998199db47..aba6e969aa 100644 --- a/provider/pdns/pdns.go +++ b/provider/pdns/pdns.go @@ -158,7 +158,7 @@ func (c *PDNSAPIClient) ListZones() ([]pgo.Zone, *http.Response, error) { var zones []pgo.Zone var resp *http.Response var err error - for i := 0; i < retryLimit; i++ { + for i := range retryLimit { zones, resp, err = c.client.ZonesApi.ListZones(c.authCtx, c.serverID) if err != nil { log.Debugf("Unable to fetch zones %v", err) @@ -194,7 +194,7 @@ func (c *PDNSAPIClient) PartitionZones(zones []pgo.Zone) ([]pgo.Zone, []pgo.Zone // ListZone : Method returns the details of a specific zone from PowerDNS // ref: https://doc.powerdns.com/authoritative/http-api/zone.html#get--servers-server_id-zones-zone_id func (c *PDNSAPIClient) ListZone(zoneID string) (pgo.Zone, *http.Response, error) { - for i := 0; i < retryLimit; i++ { + for i := range retryLimit { zone, resp, err := c.client.ZonesApi.ListZone(c.authCtx, c.serverID, zoneID) if err != nil { log.Debugf("Unable to fetch zone %v", err) @@ -213,7 +213,7 @@ func (c *PDNSAPIClient) ListZone(zoneID string) (pgo.Zone, *http.Response, error func (c *PDNSAPIClient) PatchZone(zoneID string, zoneStruct pgo.Zone) (*http.Response, error) { var resp *http.Response var err error - for i := 0; i < retryLimit; i++ { + for i := range retryLimit { resp, err = c.client.ZonesApi.PatchZone(c.authCtx, c.serverID, zoneID, zoneStruct) if err != nil { log.Debugf("Unable to patch zone %v", err) @@ -455,7 +455,7 @@ func (p *PDNSProvider) Records(_ context.Context) ([]*endpoint.Endpoint, error) // AdjustEndpoints performs checks on the provided endpoints and will skip any potentially failing changes. func (p *PDNSProvider) AdjustEndpoints(endpoints []*endpoint.Endpoint) ([]*endpoint.Endpoint, error) { var validEndpoints []*endpoint.Endpoint - for i := 0; i < len(endpoints); i++ { + for i := range endpoints { if !endpoints[i].CheckEndpoint() { log.Warnf("Ignoring Endpoint because of invalid %v record formatting: {Target: '%v'}", endpoints[i].RecordType, endpoints[i].Targets) continue diff --git a/provider/rfc2136/rfc2136.go b/provider/rfc2136/rfc2136.go index 816b782ca3..3bb588b6ae 100644 --- a/provider/rfc2136/rfc2136.go +++ b/provider/rfc2136/rfc2136.go @@ -632,11 +632,7 @@ func chunkBy(slice []*endpoint.Endpoint, chunkSize int) [][]*endpoint.Endpoint { var chunks [][]*endpoint.Endpoint for i := 0; i < len(slice); i += chunkSize { - end := i + chunkSize - - if end > len(slice) { - end = len(slice) - } + end := min(i+chunkSize, len(slice)) chunks = append(chunks, slice[i:end]) } diff --git a/provider/rfc2136/rfc2136_test.go b/provider/rfc2136/rfc2136_test.go index 8c4c6938d1..9a12294221 100644 --- a/provider/rfc2136/rfc2136_test.go +++ b/provider/rfc2136/rfc2136_test.go @@ -891,7 +891,7 @@ func TestRfc2136ApplyChangesWithUpdate(t *testing.T) { func TestChunkBy(t *testing.T) { var records []*endpoint.Endpoint - for i := 0; i < 10; i++ { + for range 10 { records = append(records, &endpoint.Endpoint{ DNSName: "v1.foo.com", RecordType: "A", @@ -941,7 +941,7 @@ func TestRoundRobinLoadBalancing(t *testing.T) { rr, err := dns.NewRR(fmt.Sprintf("%s %d %s %s", "v1.foo.com.", 0, "A", "1.2.3.4")) m.Insert([]dns.RR{rr}) - for i := 0; i < 10; i++ { + for i := range 10 { err := stub.SendMessage(m) assert.NoError(t, err) expectedNameserver := "rfc2136-host" + strconv.Itoa((i%3)+1) @@ -962,7 +962,7 @@ func TestRandomLoadBalancing(t *testing.T) { nameserverCounts := map[string]int{} - for i := 0; i < 25; i++ { + for range 25 { err := stub.SendMessage(m) assert.NoError(t, err) nameserverCounts[stub.lastNameserver]++ diff --git a/provider/transip/transip_test.go b/provider/transip/transip_test.go index 9d6c66a365..727c60a398 100644 --- a/provider/transip/transip_test.go +++ b/provider/transip/transip_test.go @@ -191,10 +191,10 @@ func TestZoneNameForDNSName(t *testing.T) { // fakeClient mocks the REST API client type fakeClient struct { - getFunc func(rest.Request, interface{}) error + getFunc func(rest.Request, any) error } -func (f *fakeClient) Get(request rest.Request, dest interface{}) error { +func (f *fakeClient) Get(request rest.Request, dest any) error { if f.getFunc == nil { return errors.New("GET not defined") } @@ -233,7 +233,7 @@ func (f *fakeClient) PutWithResponse(request rest.Request) (rest.Response, error func TestProviderRecords(t *testing.T) { // set up the fake REST client client := &fakeClient{} - client.getFunc = func(req rest.Request, dest interface{}) error { + client.getFunc = func(req rest.Request, dest any) error { var data []byte switch { case req.Endpoint == "/domains": @@ -332,7 +332,7 @@ func TestProviderEntriesForEndpoint(t *testing.T) { require.NoError(t, err) // define GET function - client.getFunc = func(unused rest.Request, dest interface{}) error { + client.getFunc = func(unused rest.Request, dest any) error { // unmarshal the prepared return data into the given dnsEntriesWrapper return json.Unmarshal(returnData, &dest) } diff --git a/provider/zone_tag_filter_test.go b/provider/zone_tag_filter_test.go index a2a0b688b0..d31afa4673 100644 --- a/provider/zone_tag_filter_test.go +++ b/provider/zone_tag_filter_test.go @@ -127,7 +127,7 @@ func TestZoneTagFilterNotMatchGeneratedValues(t *testing.T) { func BenchmarkZoneTagFilterMatchBasic(b *testing.B) { for _, tc := range basicZoneTags { zoneTagFilter := NewZoneTagFilter(tc.tagsFilter) - for range b.N { + for b.Loop() { zoneTagFilter.Match(tc.zoneTags) } } @@ -148,7 +148,7 @@ var benchFixtures = []struct { func BenchmarkZoneTagFilterComplex(b *testing.B) { for _, tc := range benchFixtures { - for range b.N { + for b.Loop() { tc.source.ZoneTagFilter.Match(tc.source.inputTags) } } @@ -176,7 +176,7 @@ func generateTagFilterAndZoneTags(filter, zone int, match bool) filterZoneTags { toFilterTags := make([]string, 0, filter) inputTags := make(map[string]string, zone) - for i := 0; i < filter; i++ { + for i := range filter { tagIndex := i if !match { tagIndex += 50 @@ -184,7 +184,7 @@ func generateTagFilterAndZoneTags(filter, zone int, match bool) filterZoneTags { toFilterTags = append(toFilterTags, fmt.Sprintf("tag-%d=value-%d", tagIndex, i)) } - for i := 0; i < zone; i++ { + for i := range zone { tagIndex := i if !match { // Make sure the input tags are different from the filter tags diff --git a/provider/zone_type_filter.go b/provider/zone_type_filter.go index c595a4a9c5..85044d7bf7 100644 --- a/provider/zone_type_filter.go +++ b/provider/zone_type_filter.go @@ -36,7 +36,7 @@ func NewZoneTypeFilter(zoneType string) ZoneTypeFilter { } // Match checks whether a zone matches the zone type that's filtered for. -func (f ZoneTypeFilter) Match(rawZoneType interface{}) bool { +func (f ZoneTypeFilter) Match(rawZoneType any) bool { // An empty zone filter includes all hosted zones. if f.zoneType == "" { return true diff --git a/provider/zone_type_filter_test.go b/provider/zone_type_filter_test.go index 903d8e8765..4147ac8edc 100644 --- a/provider/zone_type_filter_test.go +++ b/provider/zone_type_filter_test.go @@ -33,25 +33,25 @@ func TestZoneTypeFilterMatch(t *testing.T) { for _, tc := range []struct { zoneTypeFilter string matches bool - zones []interface{} + zones []any }{ { - "", true, []interface{}{publicZoneStr, privateZoneStr, route53types.HostedZone{}}, + "", true, []any{publicZoneStr, privateZoneStr, route53types.HostedZone{}}, }, { - "public", true, []interface{}{publicZoneStr, publicZoneAWS, route53types.HostedZone{}}, + "public", true, []any{publicZoneStr, publicZoneAWS, route53types.HostedZone{}}, }, { - "public", false, []interface{}{privateZoneStr, privateZoneAWS}, + "public", false, []any{privateZoneStr, privateZoneAWS}, }, { - "private", true, []interface{}{privateZoneStr, privateZoneAWS}, + "private", true, []any{privateZoneStr, privateZoneAWS}, }, { - "private", false, []interface{}{publicZoneStr, publicZoneAWS, route53types.HostedZone{}}, + "private", false, []any{publicZoneStr, publicZoneAWS, route53types.HostedZone{}}, }, { - "unknown", false, []interface{}{publicZoneStr}, + "unknown", false, []any{publicZoneStr}, }, } { t.Run(tc.zoneTypeFilter, func(t *testing.T) { diff --git a/registry/dynamodb.go b/registry/dynamodb.go index 5b83ceeb0f..70ef89eb60 100644 --- a/registry/dynamodb.go +++ b/registry/dynamodb.go @@ -21,6 +21,7 @@ import ( b64 "encoding/base64" "errors" "fmt" + "maps" "strings" "time" @@ -194,9 +195,7 @@ func (im *DynamoDBRegistry) Records(ctx context.Context) ([]*endpoint.Endpoint, key.RecordType = ep.RecordType } if labels, ok := labelMap[key]; ok { - for k, v := range labels { - ep.Labels[k] = v - } + maps.Copy(ep.Labels, labels) ep.SetProviderSpecificProperty(dynamodbAttributeMigrate, "true") delete(txtRecordsMap, key) } diff --git a/registry/txt.go b/registry/txt.go index 417434c851..403dabf9af 100644 --- a/registry/txt.go +++ b/registry/txt.go @@ -19,6 +19,7 @@ package registry import ( "context" "errors" + "maps" "strings" "time" @@ -258,9 +259,7 @@ func (im *TXTRegistry) Records(ctx context.Context) ([]*endpoint.Endpoint, error labels, labelsExist = labelMap[key] } if labelsExist { - for k, v := range labels { - ep.Labels[k] = v - } + maps.Copy(ep.Labels, labels) } if im.oldOwnerID != "" && ep.Labels[endpoint.OwnerLabelKey] == im.oldOwnerID { diff --git a/registry/txt_utils_test.go b/registry/txt_utils_test.go index a81b619f2d..6ab30a70b4 100644 --- a/registry/txt_utils_test.go +++ b/registry/txt_utils_test.go @@ -17,6 +17,8 @@ limitations under the License. package registry import ( + "maps" + "sigs.k8s.io/external-dns/endpoint" ) @@ -35,18 +37,14 @@ func newEndpointWithOwnerAndOwnedRecord(dnsName, target, recordType, ownerID, ow func newMultiTargetEndpointWithOwnerAndLabels(dnsName string, targets endpoint.Targets, recordType, ownerID string, labels endpoint.Labels) *endpoint.Endpoint { e := endpoint.NewEndpoint(dnsName, recordType, targets...) e.Labels[endpoint.OwnerLabelKey] = ownerID - for k, v := range labels { - e.Labels[k] = v - } + maps.Copy(e.Labels, labels) return e } func newEndpointWithOwnerAndLabels(dnsName, target, recordType, ownerID string, labels endpoint.Labels) *endpoint.Endpoint { e := endpoint.NewEndpoint(dnsName, recordType, target) e.Labels[endpoint.OwnerLabelKey] = ownerID - for k, v := range labels { - e.Labels[k] = v - } + maps.Copy(e.Labels, labels) return e } @@ -75,9 +73,7 @@ func cloneEndpointWithOpts(e *endpoint.Endpoint, opt ...func(*endpoint.Endpoint) var labels endpoint.Labels if e.Labels != nil { labels = make(endpoint.Labels, len(e.Labels)) - for k, v := range e.Labels { - labels[k] = v - } + maps.Copy(labels, e.Labels) } var providerSpecific endpoint.ProviderSpecific diff --git a/source/ambassador_host.go b/source/ambassador_host.go index 545e17e3b0..244a9c1b02 100644 --- a/source/ambassador_host.go +++ b/source/ambassador_host.go @@ -85,7 +85,7 @@ func NewAmbassadorHostSource( // Add default resource event handlers to properly initialize informer. ambassadorHostInformer.Informer().AddEventHandler( cache.ResourceEventHandlerFuncs{ - AddFunc: func(obj interface{}) { + AddFunc: func(obj any) { }, }, ) diff --git a/source/compatibility.go b/source/compatibility.go index fc54552f55..7c392e0767 100644 --- a/source/compatibility.go +++ b/source/compatibility.go @@ -89,9 +89,9 @@ func legacyEndpointsFromMoleculeService(svc *v1.Service) []*endpoint.Endpoint { return nil } - hostnameList := strings.Split(strings.ReplaceAll(hostnameAnnotation, " ", ""), ",") + hostnameList := strings.SplitSeq(strings.ReplaceAll(hostnameAnnotation, " ", ""), ",") - for _, hostname := range hostnameList { + for hostname := range hostnameList { // Create a corresponding endpoint for each configured external entrypoint. for _, lb := range svc.Status.LoadBalancer.Ingress { if lb.IP != "" { diff --git a/source/contour_httpproxy.go b/source/contour_httpproxy.go index 901a8c0f66..c8916de7eb 100644 --- a/source/contour_httpproxy.go +++ b/source/contour_httpproxy.go @@ -75,7 +75,7 @@ func NewContourHTTPProxySource( // Add default resource event handlers to properly initialize informer. httpProxyInformer.Informer().AddEventHandler( cache.ResourceEventHandlerFuncs{ - AddFunc: func(obj interface{}) { + AddFunc: func(obj any) { }, }, ) diff --git a/source/crd.go b/source/crd.go index b9d79bb6fa..f328e9f1e7 100644 --- a/source/crd.go +++ b/source/crd.go @@ -146,13 +146,13 @@ func (cs *crdSource) AddEventHandler(_ context.Context, handler func()) { // https://github.com/kubernetes/kubernetes/issues/79610 _, _ = cs.informer.AddEventHandler( cache.ResourceEventHandlerFuncs{ - AddFunc: func(obj interface{}) { + AddFunc: func(obj any) { handler() }, - UpdateFunc: func(old interface{}, newI interface{}) { + UpdateFunc: func(old any, newI any) { handler() }, - DeleteFunc: func(obj interface{}) { + DeleteFunc: func(obj any) { handler() }, }, diff --git a/source/crd_test.go b/source/crd_test.go index ec87b4149d..68a33f98cb 100644 --- a/source/crd_test.go +++ b/source/crd_test.go @@ -41,6 +41,7 @@ import ( "k8s.io/client-go/rest/fake" "k8s.io/client-go/tools/cache" cachetesting "k8s.io/client-go/tools/cache/testing" + apiv1alpha1 "sigs.k8s.io/external-dns/apis/v1alpha1" "sigs.k8s.io/external-dns/endpoint" ) @@ -789,7 +790,7 @@ func generateTestFixtureDNSEndpointsByType(namespace string, typeCounts map[stri var result []apiv1alpha1.DNSEndpoint idx := 0 for rt, count := range typeCounts { - for i := 0; i < count; i++ { + for range count { result = append(result, apiv1alpha1.DNSEndpoint{ ObjectMeta: metav1.ObjectMeta{ Name: fmt.Sprintf("dnsendpoint-%s-%d", rt, idx), diff --git a/source/endpoint_benchmark_test.go b/source/endpoint_benchmark_test.go index a178950d90..b8ac80e345 100644 --- a/source/endpoint_benchmark_test.go +++ b/source/endpoint_benchmark_test.go @@ -94,7 +94,7 @@ func svcInformerWithServices(toLookup, underTest int) (coreinformers.ServiceInfo _, err := svcInformer.Informer().AddEventHandler( cache.ResourceEventHandlerFuncs{ - AddFunc: func(obj interface{}) { + AddFunc: func(obj any) { }, }, ) @@ -155,19 +155,19 @@ func fixturesSvcWithLabels(toLookup, underTest int) []*corev1.Service { } // services with specific labels - for i := 0; i < toLookup; i++ { + for i := range toLookup { svc := createService("nginx-svc-"+strconv.Itoa(i), "default", map[string]string{"app": "nginx", "env": "prod"}) services = append(services, svc) } // services with random labels - for i := 0; i < underTest; i++ { + for i := range underTest { svc := createService("random-svc-"+strconv.Itoa(i), "default", randomLabels(i)) services = append(services, svc) } // Shuffle the services to ensure randomness - for i := 0; i < 3; i++ { + for range 3 { rand.Shuffle(len(services), func(i, j int) { services[i], services[j] = services[j], services[i] }) @@ -211,19 +211,19 @@ func fixturesIstioGatewaySvcWithLabels(toLookup, underTest int) []*istiov1a.Gate } } // services with specific labels - for i := 0; i < toLookup; i++ { + for i := range toLookup { svc := createGateway("istio-gw-"+strconv.Itoa(i), "default", map[string]string{"app": "nginx", "env": "prod"}) result = append(result, svc) } // services with random labels - for i := 0; i < underTest; i++ { + for i := range underTest { svc := createGateway("istio-random-svc-"+strconv.Itoa(i), "default", randomLabels(i)) result = append(result, svc) } // Shuffle the services to ensure randomness - for i := 0; i < 3; i++ { + for range 3 { rand.Shuffle(len(result), func(i, j int) { result[i], result[j] = result[j], result[i] }) diff --git a/source/f5_transportserver.go b/source/f5_transportserver.go index 8061bd8b3d..817affbd38 100644 --- a/source/f5_transportserver.go +++ b/source/f5_transportserver.go @@ -70,7 +70,7 @@ func NewF5TransportServerSource( transportServerInformer.Informer().AddEventHandler( cache.ResourceEventHandlerFuncs{ - AddFunc: func(obj interface{}) { + AddFunc: func(obj any) { }, }, ) diff --git a/source/f5_virtualserver.go b/source/f5_virtualserver.go index d8b288980b..2a9958f839 100644 --- a/source/f5_virtualserver.go +++ b/source/f5_virtualserver.go @@ -70,7 +70,7 @@ func NewF5VirtualServerSource( virtualServerInformer.Informer().AddEventHandler( cache.ResourceEventHandlerFuncs{ - AddFunc: func(obj interface{}) { + AddFunc: func(obj any) { }, }, ) diff --git a/source/fake.go b/source/fake.go index d6b1235fac..d83658255b 100644 --- a/source/fake.go +++ b/source/fake.go @@ -62,7 +62,7 @@ func (sc *fakeSource) AddEventHandler(_ context.Context, handler func()) { func (sc *fakeSource) Endpoints(ctx context.Context) ([]*endpoint.Endpoint, error) { endpoints := make([]*endpoint.Endpoint, 10) - for i := 0; i < 10; i++ { + for i := range 10 { endpoints[i] = sc.generateEndpoint() } diff --git a/source/fqdn/fqdn.go b/source/fqdn/fqdn.go index 17e91d80aa..40bc9e08c5 100644 --- a/source/fqdn/fqdn.go +++ b/source/fqdn/fqdn.go @@ -60,7 +60,7 @@ func ExecTemplate(tmpl *template.Template, obj kubeObject) ([]string, error) { return nil, fmt.Errorf("failed to apply template on %s %s/%s: %w", kind, obj.GetNamespace(), obj.GetName(), err) } var hostnames []string - for _, name := range strings.Split(buf.String(), ",") { + for name := range strings.SplitSeq(buf.String(), ",") { name = strings.TrimFunc(name, unicode.IsSpace) name = strings.TrimSuffix(name, ".") hostnames = append(hostnames, name) diff --git a/source/gateway_test.go b/source/gateway_test.go index 0391855f2c..a524999d96 100644 --- a/source/gateway_test.go +++ b/source/gateway_test.go @@ -93,7 +93,7 @@ func TestGatewayMatchingHost(t *testing.T) { } for _, tt := range tests { t.Run(tt.desc, func(t *testing.T) { - for i := 0; i < 2; i++ { + for range 2 { if host, ok := gwMatchingHost(tt.a, tt.b); host != tt.host || ok != tt.ok { t.Errorf( "gwMatchingHost(%q, %q); got: %q, %v; want: %q, %v", @@ -147,7 +147,7 @@ func TestGatewayMatchingProtocol(t *testing.T) { for _, tt := range tests { t.Run(tt.desc, func(t *testing.T) { - for i := 0; i < 2; i++ { + for range 2 { if ok := gwProtocolMatches(v1.ProtocolType(tt.route), v1.ProtocolType(tt.lis)); ok != tt.ok { t.Errorf( "gwProtocolMatches(%q, %q); got: %v; want: %v", diff --git a/source/gloo_proxy.go b/source/gloo_proxy.go index a443c4eb25..07db71f537 100644 --- a/source/gloo_proxy.go +++ b/source/gloo_proxy.go @@ -20,6 +20,7 @@ import ( "context" "encoding/json" "fmt" + "maps" "strings" log "github.com/sirupsen/logrus" @@ -62,8 +63,8 @@ var ( // Basic redefinition of "Proxy" CRD : https://github.com/solo-io/gloo/blob/v1.4.6/projects/gloo/pkg/api/v1/proxy.pb.go type proxy struct { metav1.TypeMeta `json:",inline"` - Metadata metav1.ObjectMeta `json:"metadata,omitempty"` - Spec proxySpec `json:"spec,omitempty"` + Metadata metav1.ObjectMeta `json:"metadata"` + Spec proxySpec `json:"spec"` } type proxySpec struct { @@ -71,8 +72,8 @@ type proxySpec struct { } type proxySpecListener struct { - HTTPListener proxySpecHTTPListener `json:"httpListener,omitempty"` - MetadataStatic proxyMetadataStatic `json:"metadataStatic,omitempty"` + HTTPListener proxySpecHTTPListener `json:"httpListener"` + MetadataStatic proxyMetadataStatic `json:"metadataStatic"` } type proxyMetadataStatic struct { @@ -81,7 +82,7 @@ type proxyMetadataStatic struct { type proxyMetadataStaticSource struct { ResourceKind string `json:"resourceKind,omitempty"` - ResourceRef proxyMetadataStaticSourceResourceRef `json:"resourceRef,omitempty"` + ResourceRef proxyMetadataStaticSourceResourceRef `json:"resourceRef"` } type proxyMetadataStaticSourceResourceRef struct { @@ -95,8 +96,8 @@ type proxySpecHTTPListener struct { type proxyVirtualHost struct { Domains []string `json:"domains,omitempty"` - Metadata proxyVirtualHostMetadata `json:"metadata,omitempty"` - MetadataStatic proxyVirtualHostMetadataStatic `json:"metadataStatic,omitempty"` + Metadata proxyVirtualHostMetadata `json:"metadata"` + MetadataStatic proxyVirtualHostMetadataStatic `json:"metadataStatic"` } type proxyVirtualHostMetadata struct { @@ -104,7 +105,7 @@ type proxyVirtualHostMetadata struct { } type proxyVirtualHostMetadataStatic struct { - Source []proxyVirtualHostMetadataStaticSource `json:"sources,omitempty"` + Source []proxyVirtualHostMetadataStaticSource `json:"sources"` } type proxyVirtualHostMetadataSource struct { @@ -114,11 +115,12 @@ type proxyVirtualHostMetadataSource struct { } type proxyVirtualHostMetadataStaticSource struct { - ResourceKind string `json:"resourceKind,omitempty"` - ResourceRef proxyVirtualHostMetadataSourceResourceRef `json:"resourceRef,omitempty"` + ResourceKind string `json:"resourceKind"` + ResourceRef proxyVirtualHostMetadataSourceResourceRef `json:"resourceRef"` } type proxyVirtualHostMetadataSourceResourceRef struct { + proxyVirtualHost Name string `json:"name,omitempty"` Namespace string `json:"namespace,omitempty"` } @@ -267,9 +269,7 @@ func (gs *glooSource) annotationsFromProxySource(virtualHost proxyVirtualHost) ( continue } - for key, value := range unstructuredVirtualService.GetAnnotations() { - ants[key] = value - } + maps.Copy(ants, unstructuredVirtualService.GetAnnotations()) } for _, src := range virtualHost.MetadataStatic.Source { @@ -287,9 +287,7 @@ func (gs *glooSource) annotationsFromProxySource(virtualHost proxyVirtualHost) ( continue } - for key, value := range unstructuredVirtualService.GetAnnotations() { - ants[key] = value - } + maps.Copy(ants, unstructuredVirtualService.GetAnnotations()) } return ants, nil } diff --git a/source/informers/indexers.go b/source/informers/indexers.go index b2b947da47..1d0f57ae7f 100644 --- a/source/informers/indexers.go +++ b/source/informers/indexers.go @@ -76,7 +76,7 @@ func IndexerWithOptions[T metav1.Object](optFns ...func(options *IndexSelectorOp } return cache.Indexers{ - IndexWithSelectors: func(obj interface{}) ([]string, error) { + IndexWithSelectors: func(obj any) ([]string, error) { entity, ok := obj.(T) if !ok { return nil, fmt.Errorf("object is not of type %T", new(T)) diff --git a/source/informers/informers_test.go b/source/informers/informers_test.go index 8d5fd05b08..24329b3671 100644 --- a/source/informers/informers_test.go +++ b/source/informers/informers_test.go @@ -50,17 +50,17 @@ func TestWaitForCacheSync(t *testing.T) { }{ { name: "all caches synced", - syncResults: map[reflect.Type]bool{reflect.TypeOf(""): true}, + syncResults: map[reflect.Type]bool{reflect.TypeFor[string](): true}, }, { name: "some caches not synced", - syncResults: map[reflect.Type]bool{reflect.TypeOf(""): false}, + syncResults: map[reflect.Type]bool{reflect.TypeFor[string](): false}, expectError: true, errorMsg: "failed to sync string with timeout 1m0s", }, { name: "context timeout", - syncResults: map[reflect.Type]bool{reflect.TypeOf(""): false}, + syncResults: map[reflect.Type]bool{reflect.TypeFor[string](): false}, expectError: true, errorMsg: "failed to sync string with timeout 1m0s", }, diff --git a/source/kong_tcpingress.go b/source/kong_tcpingress.go index 76efc43723..e142bb1c56 100644 --- a/source/kong_tcpingress.go +++ b/source/kong_tcpingress.go @@ -70,7 +70,7 @@ func NewKongTCPIngressSource(ctx context.Context, dynamicKubeClient dynamic.Inte // Add default resource event handlers to properly initialize informer. kongTCPIngressInformer.Informer().AddEventHandler( cache.ResourceEventHandlerFuncs{ - AddFunc: func(obj interface{}) { + AddFunc: func(obj any) { }, }, ) @@ -243,15 +243,15 @@ func newKongUnstructuredConverter() (*unstructuredConverter, error) { // If that is dealt with at some point the below can be removed and replaced with an actual import type TCPIngress struct { metav1.TypeMeta `json:",inline"` - metav1.ObjectMeta `json:"metadata,omitempty"` + metav1.ObjectMeta `json:"metadata"` - Spec tcpIngressSpec `json:"spec,omitempty"` - Status tcpIngressStatus `json:"status,omitempty"` + Spec tcpIngressSpec `json:"spec"` + Status tcpIngressStatus `json:"status"` } type TCPIngressList struct { metav1.TypeMeta `json:",inline"` - metav1.ListMeta `json:"metadata,omitempty"` + metav1.ListMeta `json:"metadata"` Items []TCPIngress `json:"items"` } @@ -266,7 +266,7 @@ type tcpIngressTLS struct { } type tcpIngressStatus struct { - LoadBalancer corev1.LoadBalancerStatus `json:"loadBalancer,omitempty"` + LoadBalancer corev1.LoadBalancerStatus `json:"loadBalancer"` } type tcpIngressRule struct { diff --git a/source/openshift_route.go b/source/openshift_route.go index f6ce484de7..66180b70ad 100644 --- a/source/openshift_route.go +++ b/source/openshift_route.go @@ -80,7 +80,7 @@ func NewOcpRouteSource( // Add default resource event handlers to properly initialize informer. informer.Informer().AddEventHandler( cache.ResourceEventHandlerFuncs{ - AddFunc: func(obj interface{}) { + AddFunc: func(obj any) { }, }, ) diff --git a/source/pod.go b/source/pod.go index 2d0ff5f92d..215f25d1ce 100644 --- a/source/pod.go +++ b/source/pod.go @@ -83,7 +83,7 @@ func NewPodSource( // The pod informer will otherwise store a full in-memory, go-typed copy of all pod schemas in the cluster. // If watchList is not used it will not prevent memory bursts on the initial informer sync. // When fqdnTemplate is used the entire pod needs to be provided to the rendering call, but the informer itself becomes unneeded. - podInformer.Informer().SetTransform(func(i interface{}) (interface{}, error) { + podInformer.Informer().SetTransform(func(i any) (any, error) { pod, ok := i.(*corev1.Pod) if !ok { return nil, fmt.Errorf("object is not a pod") diff --git a/source/pod_indexer_test.go b/source/pod_indexer_test.go index 402337a390..b74d1e1bc2 100644 --- a/source/pod_indexer_test.go +++ b/source/pod_indexer_test.go @@ -26,6 +26,7 @@ import ( corev1 "k8s.io/api/core/v1" metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" "k8s.io/client-go/kubernetes/fake" + "sigs.k8s.io/external-dns/source/annotations" ) @@ -77,12 +78,12 @@ func fixtureCreatePodsWithNodes(input []podSpec) []*corev1.Pod { for _, el := range input { totalPods := el.totalTarget + el.totalRandom - for i := 0; i < totalPods; i++ { + for i := range totalPods { pods = append(pods, createPod(i, el)) } } - for i := 0; i < 3; i++ { + for range 3 { rand.Shuffle(len(pods), func(i, j int) { pods[i], pods[j] = pods[j], pods[i] }) diff --git a/source/service.go b/source/service.go index 000fd628a1..f978e3294a 100644 --- a/source/service.go +++ b/source/service.go @@ -152,7 +152,7 @@ func NewServiceSource( // Transformer is used to reduce the memory usage of the informer. // The pod informer will otherwise store a full in-memory, go-typed copy of all pod schemas in the cluster. // If watchList is not used it will not prevent memory bursts on the initial informer sync. - _ = podInformer.Informer().SetTransform(func(i interface{}) (interface{}, error) { + _ = podInformer.Informer().SetTransform(func(i any) (any, error) { pod, ok := i.(*v1.Pod) if !ok { return nil, fmt.Errorf("object is not a pod") @@ -368,7 +368,7 @@ func (sc *serviceSource) extractHeadlessEndpoints(svc *v1.Service, hostname stri } // Helper to convert raw objects to EndpointSlice -func convertToEndpointSlices(rawEndpointSlices []interface{}) []*discoveryv1.EndpointSlice { +func convertToEndpointSlices(rawEndpointSlices []any) []*discoveryv1.EndpointSlice { endpointSlices := make([]*discoveryv1.EndpointSlice, 0, len(rawEndpointSlices)) for _, obj := range rawEndpointSlices { endpointSlice, ok := obj.(*discoveryv1.EndpointSlice) diff --git a/source/service_test.go b/source/service_test.go index bec4309bc2..18886ebc18 100644 --- a/source/service_test.go +++ b/source/service_test.go @@ -38,6 +38,7 @@ import ( "k8s.io/apimachinery/pkg/util/intstr" kubeinformers "k8s.io/client-go/informers" "k8s.io/client-go/kubernetes/fake" + "sigs.k8s.io/external-dns/endpoint" "sigs.k8s.io/external-dns/internal/testutils" "sigs.k8s.io/external-dns/source/annotations" @@ -4668,7 +4669,7 @@ func BenchmarkServiceEndpoints(b *testing.B) { ) require.NoError(b, err) - for i := 0; i < b.N; i++ { + for b.Loop() { _, err := client.Endpoints(context.Background()) require.NoError(b, err) } @@ -5112,7 +5113,7 @@ func createTestServicesByType(namespace string, typeCounts map[v1.ServiceType]in var services []*v1.Service idx := 0 for svcType, count := range typeCounts { - for i := 0; i < count; i++ { + for range count { svc := &v1.Service{ ObjectMeta: metav1.ObjectMeta{ Name: fmt.Sprintf("svc-%s-%d", svcType, idx), @@ -5271,7 +5272,7 @@ func TestConvertToEndpointSlices(t *testing.T) { AddressType: discoveryv1.AddressTypeIPv4, } - rawObjects := []interface{}{validSlice} + rawObjects := []any{validSlice} result := convertToEndpointSlices(rawObjects) assert.Len(t, result, 1) @@ -5285,7 +5286,7 @@ func TestConvertToEndpointSlices(t *testing.T) { AddressType: discoveryv1.AddressTypeIPv4, } - rawObjects := []interface{}{invalidObject, validSlice} + rawObjects := []any{invalidObject, validSlice} result := convertToEndpointSlices(rawObjects) assert.Len(t, result, 1) @@ -5293,12 +5294,12 @@ func TestConvertToEndpointSlices(t *testing.T) { }) t.Run("handles empty input", func(t *testing.T) { - result := convertToEndpointSlices([]interface{}{}) + result := convertToEndpointSlices([]any{}) assert.Empty(t, result) }) t.Run("handles all invalid objects", func(t *testing.T) { - rawObjects := []interface{}{"invalid1", 123, map[string]string{"key": "value"}} + rawObjects := []any{"invalid1", 123, map[string]string{"key": "value"}} result := convertToEndpointSlices(rawObjects) assert.Empty(t, result) }) diff --git a/source/skipper_routegroup.go b/source/skipper_routegroup.go index 83676b31d0..fc5737cb80 100644 --- a/source/skipper_routegroup.go +++ b/source/skipper_routegroup.go @@ -317,8 +317,8 @@ func (sc *routeGroupSource) endpointsFromTemplate(rg *routeGroup) ([]*endpoint.E var endpoints []*endpoint.Endpoint // splits the FQDN template and removes the trailing periods - hostnameList := strings.Split(strings.ReplaceAll(hostnames, " ", ""), ",") - for _, hostname := range hostnameList { + hostnameList := strings.SplitSeq(strings.ReplaceAll(hostnames, " ", ""), ",") + for hostname := range hostnameList { hostname = strings.TrimSuffix(hostname, ".") endpoints = append(endpoints, EndpointsForHostname(hostname, targets, ttl, providerSpecific, setIdentifier, resource)...) } diff --git a/source/source.go b/source/source.go index d65595acf0..122af03478 100644 --- a/source/source.go +++ b/source/source.go @@ -66,6 +66,6 @@ func matchLabelSelector(selector labels.Selector, srcAnnotations map[string]stri type eventHandlerFunc func() -func (fn eventHandlerFunc) OnAdd(obj interface{}, isInInitialList bool) { fn() } -func (fn eventHandlerFunc) OnUpdate(oldObj, newObj interface{}) { fn() } -func (fn eventHandlerFunc) OnDelete(obj interface{}) { fn() } +func (fn eventHandlerFunc) OnAdd(obj any, isInInitialList bool) { fn() } +func (fn eventHandlerFunc) OnUpdate(oldObj, newObj any) { fn() } +func (fn eventHandlerFunc) OnDelete(obj any) { fn() } diff --git a/source/traefik_proxy.go b/source/traefik_proxy.go index 710a8b626b..8deca9d851 100644 --- a/source/traefik_proxy.go +++ b/source/traefik_proxy.go @@ -115,17 +115,17 @@ func NewTraefikSource( ingressRouteUdpInformer = informerFactory.ForResource(ingressRouteUDPGVR) _, _ = ingressRouteInformer.Informer().AddEventHandler( cache.ResourceEventHandlerFuncs{ - AddFunc: func(obj interface{}) {}, + AddFunc: func(obj any) {}, }, ) _, _ = ingressRouteTcpInformer.Informer().AddEventHandler( cache.ResourceEventHandlerFuncs{ - AddFunc: func(obj interface{}) {}, + AddFunc: func(obj any) {}, }, ) _, _ = ingressRouteUdpInformer.Informer().AddEventHandler( cache.ResourceEventHandlerFuncs{ - AddFunc: func(obj interface{}) {}, + AddFunc: func(obj any) {}, }, ) } @@ -135,17 +135,17 @@ func NewTraefikSource( oldIngressRouteUdpInformer = informerFactory.ForResource(oldIngressRouteUDPGVR) _, _ = oldIngressRouteInformer.Informer().AddEventHandler( cache.ResourceEventHandlerFuncs{ - AddFunc: func(obj interface{}) {}, + AddFunc: func(obj any) {}, }, ) _, _ = oldIngressRouteTcpInformer.Informer().AddEventHandler( cache.ResourceEventHandlerFuncs{ - AddFunc: func(obj interface{}) {}, + AddFunc: func(obj any) {}, }, ) _, _ = oldIngressRouteUdpInformer.Informer().AddEventHandler( cache.ResourceEventHandlerFuncs{ - AddFunc: func(obj interface{}) {}, + AddFunc: func(obj any) {}, }, ) } @@ -927,7 +927,7 @@ func filterResourcesByAnnotations[T any](resources []*T, annotationFilter string return filteredList, nil } -func getAnnotations(obj interface{}) map[string]string { +func getAnnotations(obj any) map[string]string { switch o := obj.(type) { case *IngressRouteUDP: return o.Annotations @@ -940,7 +940,7 @@ func getAnnotations(obj interface{}) map[string]string { } } -func getObjectFullName(obj interface{}) string { +func getObjectFullName(obj any) string { switch o := obj.(type) { case *IngressRouteUDP: return fmt.Sprintf("%s/%s", o.Namespace, o.Name)