Skip to content
Open
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
75 changes: 75 additions & 0 deletions pkg/utils/net_test.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,75 @@
/*
Copyright 2023 The Fluid Authors.

Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at

http://www.apache.org/licenses/LICENSE-2.0

Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/

package utils

import (
"reflect"
"testing"
)

func TestSortIpAddresses(t *testing.T) {
tests := []struct {
name string
ips []string
want []string
}{
{
name: "empty_input",
ips: []string{},
want: nil,
},
{
name: "single_ip",
ips: []string{"10.0.0.1"},
want: []string{"10.0.0.1"},
},
{
name: "already_sorted",
ips: []string{"10.0.0.1", "10.0.0.2", "10.0.0.3"},
want: []string{"10.0.0.1", "10.0.0.2", "10.0.0.3"},
},
{
name: "unsorted_ips",
ips: []string{"10.0.0.3", "10.0.0.1", "10.0.0.2"},
want: []string{"10.0.0.1", "10.0.0.2", "10.0.0.3"},
},
{
name: "duplicate_ips_are_deduplicated",
ips: []string{"10.0.0.1", "10.0.0.2", "10.0.0.1"},
want: []string{"10.0.0.1", "10.0.0.2"},
},
{
name: "cross_subnet_ordering",
ips: []string{"192.168.1.1", "10.0.0.1", "172.16.0.1"},
want: []string{"10.0.0.1", "172.16.0.1", "192.168.1.1"},
},
{
name: "last_octet_ordering",
ips: []string{"10.0.0.100", "10.0.0.20", "10.0.0.3"},
want: []string{"10.0.0.3", "10.0.0.20", "10.0.0.100"},
},

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Nice, focused table here — the cases already pin down the important behaviors (dedup, and byte-wise numeric ordering rather than lexical, which last_octet_ordering and cross_subnet_ordering catch well). Two optional additions would round it out:

  1. A mixed IPv4/IPv6 case. SortIpAddresses parses everything to 16-byte net.IP and sorts with bytes.Compare, so cross-version ordering is worth locking down as a regression guard, e.g. ["2001:db8::1", "::1", "192.168.1.1", "10.0.0.1"] -> ["::1", "10.0.0.1", "192.168.1.1", "2001:db8::1"].
  2. An invalid-IP case to document current behavior. Note the function does not filter invalid input: net.ParseIP("not-an-ip") returns nil, and nil.String() yields "<nil>", which then appears in the output. So ["10.0.0.1", "not-an-ip"] currently sorts to ["<nil>", "10.0.0.1"] (the nil parses to an empty slice and sorts first). Worth asserting the real behavior — or, if filtering is the intended contract, that would be a change to the function itself rather than the test.

Both are non-blocking.

}
Comment on lines +25 to +65

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

medium

The test suite is a great start, but it could be made more comprehensive by including tests for important edge cases. This would improve the robustness of the SortIpAddresses utility.

Specifically, please consider adding test cases for:

  1. Invalid IP strings: The SortIpAddresses function does not currently specify behavior for invalid IP strings (e.g., "not-an-ip", ""). net.ParseIP returns nil for these, and ip.String() on a nil net.IP results in the string "<nil>" in the output. A test should be added to assert the desired behavior, which would ideally be to filter out invalid IPs.

  2. Mixed IPv4 and IPv6 addresses: As noted in the pull request description, bytes.Compare has specific behavior for different IP versions. Adding a test with a mix of IPv4 and IPv6 addresses would ensure the sorting is correct and provide a valuable regression guard.

Here are some example test cases you could add:

{
name: "with_invalid_ips",
ips: []string{"10.0.0.2", "not-an-ip", "10.0.0.1"},
want: []string{"10.0.0.1", "10.0.0.2"},
},
{
name: "mixed_ipv4_and_ipv6",
ips: []string{"2001:db8::1", "::1", "192.168.1.1", "10.0.0.1"},
want: []string{"::1", "10.0.0.1", "192.168.1.1", "2001:db8::1"},
},


for _, tt := range tests {
t.Run(tt.name, func(t *testing.T) {
got := SortIpAddresses(tt.ips)
if !reflect.DeepEqual(got, tt.want) {
t.Errorf("SortIpAddresses() = %v, want %v", got, tt.want)
}
})
}
}
Loading