github.com/cilium/cilium@v1.16.2/pkg/policy/api/ingress_test.go (about)

     1  // SPDX-License-Identifier: Apache-2.0
     2  // Copyright Authors of Cilium
     3  
     4  package api
     5  
     6  import (
     7  	"context"
     8  	"testing"
     9  
    10  	"fmt"
    11  
    12  	"github.com/stretchr/testify/require"
    13  	"k8s.io/apimachinery/pkg/util/intstr"
    14  
    15  	slim_metav1 "github.com/cilium/cilium/pkg/k8s/slim/k8s/apis/meta/v1"
    16  )
    17  
    18  func TestIngressRequiresDerivativeRuleWithoutToGroups(t *testing.T) {
    19  	ig := IngressRule{}
    20  	require.Equal(t, false, ig.RequiresDerivative())
    21  }
    22  
    23  func TestRequiresDerivativeRuleWithFromGroups(t *testing.T) {
    24  	ig := IngressRule{}
    25  	ig.FromGroups = []Groups{
    26  		GetGroupsRule(),
    27  	}
    28  	require.Equal(t, true, ig.RequiresDerivative())
    29  }
    30  
    31  func TestCreateDerivativeRuleWithoutFromGroups(t *testing.T) {
    32  	ig := &IngressRule{
    33  		IngressCommonRule: IngressCommonRule{
    34  			FromEndpoints: []EndpointSelector{
    35  				{
    36  					LabelSelector: &slim_metav1.LabelSelector{MatchLabels: map[string]string{
    37  						"test": "true",
    38  					},
    39  					},
    40  				},
    41  			},
    42  		},
    43  	}
    44  	newRule, err := ig.CreateDerivative(context.TODO())
    45  	require.EqualValues(t, newRule, ig)
    46  	require.Nil(t, err)
    47  }
    48  
    49  func TestCreateDerivativeRuleWithFromGroups(t *testing.T) {
    50  	cb := GetCallBackWithRule("192.168.1.1")
    51  	RegisterToGroupsProvider(AWSProvider, cb)
    52  
    53  	ig := &IngressRule{
    54  		IngressCommonRule: IngressCommonRule{
    55  			FromGroups: []Groups{
    56  				GetGroupsRule(),
    57  			},
    58  		},
    59  	}
    60  
    61  	// Checking that the derivative rule is working correctly
    62  	require.Equal(t, true, ig.RequiresDerivative())
    63  
    64  	newRule, err := ig.CreateDerivative(context.TODO())
    65  	require.Nil(t, err)
    66  	require.Equal(t, 0, len(newRule.FromGroups))
    67  	require.Equal(t, 1, len(newRule.FromCIDRSet))
    68  }
    69  
    70  func TestIsLabelBasedIngress(t *testing.T) {
    71  	setUpSuite(t)
    72  
    73  	type args struct {
    74  		eg *IngressRule
    75  	}
    76  	type wanted struct {
    77  		isLabelBased bool
    78  	}
    79  
    80  	tests := []struct {
    81  		name        string
    82  		setupArgs   func() args
    83  		setupWanted func() wanted
    84  	}{
    85  		{
    86  			name: "label-based-rule",
    87  			setupArgs: func() args {
    88  				return args{
    89  					eg: &IngressRule{
    90  						IngressCommonRule: IngressCommonRule{
    91  							FromEndpoints: []EndpointSelector{
    92  								{
    93  									LabelSelector: &slim_metav1.LabelSelector{MatchLabels: map[string]string{
    94  										"test": "true",
    95  									},
    96  									},
    97  								},
    98  							},
    99  						},
   100  					},
   101  				}
   102  			},
   103  			setupWanted: func() wanted {
   104  				return wanted{
   105  					isLabelBased: true,
   106  				}
   107  			},
   108  		},
   109  		{
   110  			name: "cidr-based-rule",
   111  			setupArgs: func() args {
   112  				return args{
   113  					&IngressRule{
   114  						IngressCommonRule: IngressCommonRule{
   115  							FromCIDR: CIDRSlice{"192.0.0.0/3"},
   116  						},
   117  					},
   118  				}
   119  			},
   120  			setupWanted: func() wanted {
   121  				return wanted{
   122  					isLabelBased: true,
   123  				}
   124  			},
   125  		},
   126  		{
   127  			name: "cidrset-based-rule",
   128  			setupArgs: func() args {
   129  				return args{
   130  					&IngressRule{
   131  						IngressCommonRule: IngressCommonRule{
   132  							FromCIDRSet: CIDRRuleSlice{
   133  								{
   134  									Cidr: "192.0.0.0/3",
   135  								},
   136  							},
   137  						},
   138  					},
   139  				}
   140  			},
   141  			setupWanted: func() wanted {
   142  				return wanted{
   143  					isLabelBased: true,
   144  				}
   145  			},
   146  		},
   147  		{
   148  			name: "rule-with-requirements",
   149  			setupArgs: func() args {
   150  				return args{
   151  					&IngressRule{
   152  						IngressCommonRule: IngressCommonRule{
   153  							FromRequires: []EndpointSelector{
   154  								{
   155  									LabelSelector: &slim_metav1.LabelSelector{MatchLabels: map[string]string{
   156  										"test": "true",
   157  									},
   158  									},
   159  								},
   160  							},
   161  						},
   162  					},
   163  				}
   164  			},
   165  			setupWanted: func() wanted {
   166  				return wanted{
   167  					isLabelBased: false,
   168  				}
   169  			},
   170  		},
   171  		{
   172  			name: "rule-with-entities",
   173  			setupArgs: func() args {
   174  				return args{
   175  					&IngressRule{
   176  						IngressCommonRule: IngressCommonRule{
   177  							FromEntities: EntitySlice{
   178  								EntityHost,
   179  							},
   180  						},
   181  					},
   182  				}
   183  			},
   184  			setupWanted: func() wanted {
   185  				return wanted{
   186  					isLabelBased: true,
   187  				}
   188  			},
   189  		},
   190  		{
   191  			name: "rule-with-no-l3-specification",
   192  			setupArgs: func() args {
   193  				return args{
   194  					&IngressRule{
   195  						ToPorts: []PortRule{
   196  							{
   197  								Ports: []PortProtocol{
   198  									{
   199  										Port:     "80",
   200  										Protocol: ProtoTCP,
   201  									},
   202  								},
   203  							},
   204  						},
   205  					},
   206  				}
   207  			},
   208  			setupWanted: func() wanted {
   209  				return wanted{
   210  					isLabelBased: true,
   211  				}
   212  			},
   213  		},
   214  		{
   215  			name: "rule-with-named-port",
   216  			setupArgs: func() args {
   217  				return args{
   218  					&IngressRule{
   219  						ToPorts: []PortRule{
   220  							{
   221  								Ports: []PortProtocol{
   222  									{
   223  										Port:     "port-80",
   224  										Protocol: ProtoTCP,
   225  									},
   226  								},
   227  							},
   228  						},
   229  					},
   230  				}
   231  			},
   232  			setupWanted: func() wanted {
   233  				return wanted{
   234  					isLabelBased: true,
   235  				}
   236  			},
   237  		},
   238  		{
   239  			name: "rule-with-icmp",
   240  			setupArgs: func() args {
   241  				icmpType := intstr.FromInt(8)
   242  				return args{
   243  					&IngressRule{
   244  						ICMPs: ICMPRules{
   245  							{
   246  								Fields: []ICMPField{
   247  									{
   248  										Type: &icmpType,
   249  									},
   250  								},
   251  							},
   252  						},
   253  					},
   254  				}
   255  			},
   256  			setupWanted: func() wanted {
   257  				return wanted{
   258  					isLabelBased: true,
   259  				}
   260  			},
   261  		},
   262  		{
   263  			name: "rule-with-icmp6",
   264  			setupArgs: func() args {
   265  				icmpType := intstr.FromInt(128)
   266  				return args{
   267  					&IngressRule{
   268  						ICMPs: ICMPRules{
   269  							{
   270  								Fields: []ICMPField{
   271  									{
   272  										Family: IPv6Family,
   273  										Type:   &icmpType,
   274  									},
   275  								},
   276  							},
   277  						},
   278  					},
   279  				}
   280  			},
   281  			setupWanted: func() wanted {
   282  				return wanted{
   283  					isLabelBased: true,
   284  				}
   285  			},
   286  		},
   287  	}
   288  
   289  	for _, tt := range tests {
   290  		args := tt.setupArgs()
   291  		want := tt.setupWanted()
   292  		require.Equal(t, nil, args.eg.sanitize(), fmt.Sprintf("Test name: %q", tt.name))
   293  		isLabelBased := args.eg.AllowsWildcarding()
   294  		require.EqualValues(t, want.isLabelBased, isLabelBased, fmt.Sprintf("Test name: %q", tt.name))
   295  	}
   296  }
   297  
   298  func TestIngressCommonRuleDeepEqual(t *testing.T) {
   299  	testCases := []struct {
   300  		name      string
   301  		in, other *IngressCommonRule
   302  		expected  bool
   303  	}{
   304  		{
   305  			name:     "All fields are nil in both",
   306  			in:       &IngressCommonRule{},
   307  			other:    &IngressCommonRule{},
   308  			expected: true,
   309  		},
   310  		{
   311  			name: "All fields are empty in both",
   312  			in: &IngressCommonRule{
   313  				FromEndpoints: []EndpointSelector{},
   314  				FromCIDR:      []CIDR{},
   315  				FromCIDRSet:   []CIDRRule{},
   316  				FromEntities:  []Entity{},
   317  			},
   318  			other: &IngressCommonRule{
   319  				FromEndpoints: []EndpointSelector{},
   320  				FromCIDR:      []CIDR{},
   321  				FromCIDRSet:   []CIDRRule{},
   322  				FromEntities:  []Entity{},
   323  			},
   324  			expected: true,
   325  		},
   326  		{
   327  			name: "FromEndpoints is nil in left operand",
   328  			in: &IngressCommonRule{
   329  				FromEndpoints: nil,
   330  			},
   331  			other: &IngressCommonRule{
   332  				FromEndpoints: []EndpointSelector{},
   333  			},
   334  			expected: false,
   335  		},
   336  		{
   337  			name: "FromEndpoints is empty in left operand",
   338  			in: &IngressCommonRule{
   339  				FromEndpoints: []EndpointSelector{},
   340  			},
   341  			other: &IngressCommonRule{
   342  				FromEndpoints: nil,
   343  			},
   344  			expected: false,
   345  		},
   346  		{
   347  			name: "FromCIDR is nil in left operand",
   348  			in: &IngressCommonRule{
   349  				FromCIDR: nil,
   350  			},
   351  			other: &IngressCommonRule{
   352  				FromCIDR: []CIDR{},
   353  			},
   354  			expected: false,
   355  		},
   356  		{
   357  			name: "FromCIDR is empty in left operand",
   358  			in: &IngressCommonRule{
   359  				FromCIDR: []CIDR{},
   360  			},
   361  			other: &IngressCommonRule{
   362  				FromCIDR: nil,
   363  			},
   364  			expected: false,
   365  		},
   366  		{
   367  			name: "FromCIDRSet is nil in left operand",
   368  			in: &IngressCommonRule{
   369  				FromCIDRSet: nil,
   370  			},
   371  			other: &IngressCommonRule{
   372  				FromCIDRSet: []CIDRRule{},
   373  			},
   374  			expected: false,
   375  		},
   376  		{
   377  			name: "FromCIDRSet is empty in left operand",
   378  			in: &IngressCommonRule{
   379  				FromCIDRSet: []CIDRRule{},
   380  			},
   381  			other: &IngressCommonRule{
   382  				FromCIDRSet: nil,
   383  			},
   384  			expected: false,
   385  		},
   386  		{
   387  			name: "FromEntities is nil in left operand",
   388  			in: &IngressCommonRule{
   389  				FromEntities: nil,
   390  			},
   391  			other: &IngressCommonRule{
   392  				FromEntities: []Entity{},
   393  			},
   394  			expected: false,
   395  		},
   396  		{
   397  			name: "FromEntities is empty in left operand",
   398  			in: &IngressCommonRule{
   399  				FromEntities: []Entity{},
   400  			},
   401  			other: &IngressCommonRule{
   402  				FromEntities: nil,
   403  			},
   404  			expected: false,
   405  		},
   406  	}
   407  	for _, tc := range testCases {
   408  		t.Run(tc.name, func(t *testing.T) {
   409  			require.Equal(t, tc.expected, tc.in.DeepEqual(tc.other))
   410  		})
   411  	}
   412  }