github.com/verrazzano/verrazzano@v1.7.1/tools/oam-converter/pkg/resources/authorizationpolicy/authorizationpolicy_test.go (about) 1 // Copyright (c) 2023, Oracle and/or its affiliates. 2 // Licensed under the Universal Permissive License v 1.0 as shown at https://oss.oracle.com/licenses/upl. 3 4 package authorizationpolicy 5 6 import ( 7 "fmt" 8 "github.com/stretchr/testify/assert" 9 vzapi "github.com/verrazzano/verrazzano/application-operator/apis/oam/v1alpha1" 10 "github.com/verrazzano/verrazzano/application-operator/constants" 11 consts "github.com/verrazzano/verrazzano/tools/oam-converter/pkg/constants" 12 "istio.io/api/security/v1beta1" 13 v1beta12 "istio.io/api/type/v1beta1" 14 clisecurity "istio.io/client-go/pkg/apis/security/v1beta1" 15 metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" 16 "strings" 17 "testing" 18 ) 19 20 func Test_getIngressTraitNsn(t *testing.T) { 21 actual := getIngressTraitNsn("hello", "helidon") 22 expected := "hello-helidon" 23 assert.Equal(t, expected, actual, "Unexpected result for Namespace: %s, Name: %s", "hello", "helidon") 24 } 25 26 func Test_CreateAuthorizationPolicyRule(t *testing.T) { 27 // Define a struct to represent each test case. 28 type testCase struct { 29 Name string 30 Rule *vzapi.AuthorizationRule 31 Path string 32 Hosts []string 33 RequireFrom bool 34 ExpectedResult *v1beta1.Rule 35 ExpectedError bool 36 } 37 38 // Define the test cases using the testCase struct. 39 testCases := []testCase{ 40 { 41 Name: "Valid authorization rule without 'From' clause", 42 Rule: &vzapi.AuthorizationRule{ 43 When: []*vzapi.AuthorizationRuleCondition{ 44 {Key: "app", Values: []string{"myapp"}}, 45 }, 46 }, 47 Path: "/api/v1", 48 Hosts: []string{"example.com"}, 49 RequireFrom: false, 50 ExpectedResult: &v1beta1.Rule{ 51 When: []*v1beta1.Condition{ 52 {Key: "app", Values: []string{"myapp"}}, 53 }, 54 To: []*v1beta1.Rule_To{{ 55 Operation: &v1beta1.Operation{ 56 Hosts: []string{"example.com"}, 57 Paths: []string{"/api/v1"}, 58 }, 59 }}, 60 }, 61 ExpectedError: false, 62 }, 63 { 64 Name: "Authorization rule with missing 'From' clause", 65 Rule: &vzapi.AuthorizationRule{ 66 From: nil, 67 }, 68 Path: "", 69 Hosts: []string{}, 70 RequireFrom: true, 71 ExpectedResult: nil, 72 ExpectedError: true, 73 }, 74 } 75 76 // Run the test cases. 77 for _, tc := range testCases { 78 t.Run(tc.Name, func(t *testing.T) { 79 // Call the function being tested. 80 ruleResult, err := createAuthorizationPolicyRule(tc.Rule, tc.Path, tc.Hosts, tc.RequireFrom) 81 82 // Perform assertions. 83 if tc.ExpectedError { 84 assert.Errorf(t, err, "Error was expected") 85 assert.Contains(t, err.Error(), "Authorization Policy requires 'From' clause", "Unexpected error message") 86 assert.Nil(t, ruleResult, "Result should be nil due to error") 87 } else { 88 assert.Nil(t, err, "Error was not expected") 89 assert.Equal(t, tc.ExpectedResult, ruleResult, "Unexpected result") 90 } 91 }) 92 } 93 } 94 95 func TestMutateAuthorizationPolicy(t *testing.T) { 96 // Input data 97 vzPolicy := &vzapi.AuthorizationPolicy{ 98 Rules: []*vzapi.AuthorizationRule{ 99 { 100 From: nil, 101 When: []*vzapi.AuthorizationRuleCondition{ 102 {Key: "app", Values: []string{"myapp"}}, 103 }, 104 }, 105 }, 106 } 107 path := "/api/v1" 108 hosts := []string{"example.com"} 109 requireFrom := false 110 111 // Call the function being tested 112 authzPolicy := &clisecurity.AuthorizationPolicy{} 113 resultPolicy, err := mutateAuthorizationPolicy(authzPolicy, vzPolicy, path, hosts, requireFrom) 114 115 // Assertions 116 assert.Nil(t, err, "Error was not expected") 117 assert.NotNil(t, resultPolicy, "Result policy should not be nil") 118 assert.Equal(t, 1, len(resultPolicy.Spec.Rules), "Unexpected number of rules in the result policy") 119 120 // Check the contents of the rule 121 expectedRule := &v1beta1.Rule{ 122 When: []*v1beta1.Condition{ 123 {Key: "app", Values: []string{"myapp"}}, 124 }, 125 To: []*v1beta1.Rule_To{{ 126 Operation: &v1beta1.Operation{ 127 Hosts: hosts, 128 Paths: []string{path}, 129 }, 130 }}, 131 } 132 assert.Equal(t, expectedRule, resultPolicy.Spec.Rules[0], "Result rule does not match the expected rule") 133 134 // Check the authzPolicy.Spec.Selector 135 expectedSelector := &v1beta12.WorkloadSelector{ 136 MatchLabels: map[string]string{"istio": "ingressgateway"}, 137 } 138 assert.Equal(t, expectedSelector, resultPolicy.Spec.Selector, "Result selector does not match the expected selector") 139 } 140 141 func TestCreateAuthorizationPolicies(t *testing.T) { 142 // Input data 143 trait := &vzapi.IngressTrait{ 144 ObjectMeta: metav1.ObjectMeta{ 145 Namespace: "my-namespace", 146 Name: "my-ingress-trait", 147 }, 148 } 149 rule := vzapi.IngressRule{ 150 Paths: []vzapi.IngressPath{ 151 { 152 Path: "/api/v1", 153 Policy: &vzapi.AuthorizationPolicy{ 154 Rules: []*vzapi.AuthorizationRule{ 155 { 156 From: &vzapi.AuthorizationRuleFrom{ 157 RequestPrincipals: []string{"user:john"}, 158 }, 159 When: []*vzapi.AuthorizationRuleCondition{ 160 {Key: "app", Values: []string{"myapp"}}, 161 }, 162 }, 163 }, 164 }, 165 }, 166 }, 167 } 168 namePrefix := "test-policy" 169 hosts := []string{"example.com"} 170 171 // Call the function being tested for each path 172 var authzPolicies []*clisecurity.AuthorizationPolicy 173 for _, path := range rule.Paths { 174 authzPolicy, err := CreateAuthorizationPolicies(trait, vzapi.IngressRule{Paths: []vzapi.IngressPath{path}}, namePrefix, hosts) 175 assert.NoError(t, err, "Error was not expected") 176 authzPolicies = append(authzPolicies, authzPolicy) 177 } 178 179 // Assertions 180 assert.NotNil(t, authzPolicies, "Result policies should not be nil") 181 182 // Check the number of returned AuthorizationPolicies 183 expectedNumPolicies := len(rule.Paths) 184 assert.Equal(t, expectedNumPolicies, len(authzPolicies), "Unexpected number of policies returned") 185 186 // Check the contents of each returned AuthorizationPolicy 187 for i, authzPolicy := range authzPolicies { 188 expectedPolicyName := fmt.Sprintf("test-policy-%s", strings.Replace(rule.Paths[i].Path, "/", "", -1)) 189 expectedPolicyNamespace := constants.IstioSystemNamespace 190 expectedPolicyLabels := map[string]string{ 191 constants.LabelIngressTraitNsn: getIngressTraitNsn(trait.Namespace, trait.Name), 192 } 193 194 assert.Equal(t, "AuthorizationPolicy", authzPolicy.Kind, "Kind does not match") 195 assert.Equal(t, consts.AuthorizationAPIVersion, authzPolicy.APIVersion, "APIVersion does not match") 196 assert.Equal(t, expectedPolicyName, authzPolicy.ObjectMeta.Name, "Policy name does not match") 197 assert.Equal(t, expectedPolicyNamespace, authzPolicy.ObjectMeta.Namespace, "Policy namespace does not match") 198 assert.Equal(t, expectedPolicyLabels, authzPolicy.ObjectMeta.Labels, "Policy labels do not match") 199 200 // Check the Rule in the returned AuthorizationPolicy 201 assert.Equal(t, 1, len(authzPolicy.Spec.Rules), "Unexpected number of rules in the policy") 202 203 } 204 }