Skip to content

Commit

Permalink
Add Action to NetworkPolicy Evaluation response (#6112)
Browse files Browse the repository at this point in the history
As necessary for networkpolicyevaluation consumption, this PR
adds the Action field to the above antctl command response.

Signed-off-by: Qiyue Yao <[email protected]>
  • Loading branch information
qiyueyao authored Apr 3, 2024
1 parent 1e916ac commit 933e5cb
Show file tree
Hide file tree
Showing 7 changed files with 82 additions and 24 deletions.
3 changes: 1 addition & 2 deletions pkg/antctl/output/output.go
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,6 @@ import (
"io"
"reflect"
"sort"
"strconv"
"strings"
"text/tabwriter"

Expand Down Expand Up @@ -322,7 +321,7 @@ func TableOutputForQueryEndpoint(obj interface{}, writer io.Writer) error {
toStringRep := func(effectiveRules []apis.Rule) [][]string {
ruleStrings := make([][]string, 0)
for _, rule := range effectiveRules {
ruleStrings = append(ruleStrings, []string{rule.PolicyRef.Name, rule.PolicyRef.Namespace, strconv.Itoa(rule.RuleIndex), string(rule.PolicyRef.UID)})
ruleStrings = append(ruleStrings, []string{rule.PolicyRef.Name, rule.PolicyRef.Namespace, fmt.Sprint(rule.RuleIndex), string(rule.PolicyRef.UID)})
}
return ruleStrings
}
Expand Down
15 changes: 13 additions & 2 deletions pkg/antctl/transform/networkpolicy/response.go
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@ package networkpolicy
import (
"encoding/json"
"io"
"math"
"reflect"
"sort"
"strconv"
Expand Down Expand Up @@ -181,20 +182,30 @@ func EvaluationTransform(reader io.Reader, _ bool, _ map[string]string) (interfa
var _ common.TableOutput = new(EvaluationResponse)

func (r EvaluationResponse) GetTableHeader() []string {
return []string{"NAME", "NAMESPACE", "POLICY-TYPE", "RULE-INDEX", "DIRECTION"}
return []string{"NAME", "NAMESPACE", "POLICY-TYPE", "RULE-INDEX", "DIRECTION", "ACTION"}
}

func (r EvaluationResponse) GetTableRow(_ int) []string {
if r.NetworkPolicyEvaluation != nil && r.Response != nil {
// Handle K8s NPs empty action field. "Allow" corresponds to a K8s NP
// allow action, and "Isolate" corresponds to a drop action because of the
// default isolation model. Otherwise, display the action field content.
action := "Allow"
if r.Response.Rule.Action != nil {
action = string(*r.Response.Rule.Action)
} else if r.Response.RuleIndex == math.MaxInt32 {
action = "Isolate"
}
return []string{
r.Response.NetworkPolicy.Name,
r.Response.NetworkPolicy.Namespace,
string(r.Response.NetworkPolicy.Type),
strconv.Itoa(int(r.Response.RuleIndex)),
string(r.Response.Rule.Direction),
action,
}
}
return make([]string, 5)
return make([]string, len(r.GetTableHeader()))
}

func (r EvaluationResponse) SortRows() bool {
Expand Down
69 changes: 58 additions & 11 deletions pkg/antctl/transform/networkpolicy/response_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,8 @@
package networkpolicy

import (
"fmt"
"math"
"testing"

"github.com/stretchr/testify/assert"
Expand All @@ -23,6 +25,7 @@ import (
"k8s.io/utils/ptr"

cpv1beta "antrea.io/antrea/pkg/apis/controlplane/v1beta2"
crdv1beta1 "antrea.io/antrea/pkg/apis/crd/v1beta1"
)

func TestListTransform(t *testing.T) {
Expand Down Expand Up @@ -176,17 +179,61 @@ func TestListTransform(t *testing.T) {

func TestEvaluationResponseTransform(t *testing.T) {
test := EvaluationResponse{&cpv1beta.NetworkPolicyEvaluation{}}
assert.Equal(t, []string{"NAME", "NAMESPACE", "POLICY-TYPE", "RULE-INDEX", "DIRECTION"}, test.GetTableHeader())
assert.Equal(t, []string{"NAME", "NAMESPACE", "POLICY-TYPE", "RULE-INDEX", "DIRECTION", "ACTION"}, test.GetTableHeader())
assert.False(t, test.SortRows())
assert.Equal(t, []string{"", "", "", "", ""}, test.GetTableRow(32))
test.Response = &cpv1beta.NetworkPolicyEvaluationResponse{
NetworkPolicy: cpv1beta.NetworkPolicyReference{
Type: cpv1beta.K8sNetworkPolicy,
Namespace: "ns",
Name: "testName",
},
RuleIndex: 10,
Rule: cpv1beta.RuleRef{Direction: cpv1beta.DirectionIn},
assert.Equal(t, []string{"", "", "", "", "", ""}, test.GetTableRow(32))
testDropAction := crdv1beta1.RuleActionDrop

tests := []struct {
name string
testResponse *cpv1beta.NetworkPolicyEvaluationResponse
expectedOutput []string
}{
{
name: "k8s rule",
testResponse: &cpv1beta.NetworkPolicyEvaluationResponse{
NetworkPolicy: cpv1beta.NetworkPolicyReference{
Type: cpv1beta.K8sNetworkPolicy,
Namespace: "ns",
Name: "testK8s",
},
RuleIndex: 10,
Rule: cpv1beta.RuleRef{Direction: cpv1beta.DirectionIn},
},
expectedOutput: []string{"testK8s", "ns", "K8sNetworkPolicy", "10", "In", "Allow"},
},
{
name: "anp rule",
testResponse: &cpv1beta.NetworkPolicyEvaluationResponse{
NetworkPolicy: cpv1beta.NetworkPolicyReference{
Type: cpv1beta.AntreaNetworkPolicy,
Namespace: "ns",
Name: "testANP",
},
RuleIndex: 10,
Rule: cpv1beta.RuleRef{Direction: cpv1beta.DirectionIn, Action: &testDropAction},
},
expectedOutput: []string{"testANP", "ns", "AntreaNetworkPolicy", "10", "In", "Drop"},
},
{
name: "k8s default isolation",
testResponse: &cpv1beta.NetworkPolicyEvaluationResponse{
NetworkPolicy: cpv1beta.NetworkPolicyReference{
Type: cpv1beta.K8sNetworkPolicy,
Namespace: "ns",
Name: "testK8s",
},
RuleIndex: math.MaxInt32,
Rule: cpv1beta.RuleRef{Direction: cpv1beta.DirectionIn},
},
expectedOutput: []string{"testK8s", "ns", "K8sNetworkPolicy", fmt.Sprint(math.MaxInt32), "In", "Isolate"},
},
}

for _, tt := range tests {
t.Run(tt.name, func(t *testing.T) {
test.Response = tt.testResponse
assert.Equal(t, tt.expectedOutput, test.GetTableRow(32))
})
}
assert.Equal(t, []string{"testName", "ns", "K8sNetworkPolicy", "10", "In"}, test.GetTableRow(32))
}
2 changes: 1 addition & 1 deletion pkg/apiserver/apis/types.go
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,7 @@ type EndpointQueryResponse struct {
type Rule struct {
PolicyRef v1beta2.NetworkPolicyReference `json:"policyref,omitempty"`
Direction v1beta2.Direction `json:"direction,omitempty"`
RuleIndex int `json:"ruleindex,omitempty"`
RuleIndex int32 `json:"ruleindex,omitempty"`
}

type Endpoint struct {
Expand Down
8 changes: 4 additions & 4 deletions pkg/controller/networkpolicy/endpoint_querier.go
Original file line number Diff line number Diff line change
Expand Up @@ -146,7 +146,7 @@ func (eq *EndpointQuerierImpl) QueryNetworkPolicyRules(namespace, podName string
return nil, err
}
for _, policy := range policies {
egressIndex, ingressIndex := 0, 0
egressIndex, ingressIndex := int32(0), int32(0)
for _, rule := range policy.(*antreatypes.NetworkPolicy).Rules {
for _, addressGroupTrial := range rule.To.AddressGroups {
if addressGroupTrial == string(addressGroup.(*antreatypes.AddressGroup).UID) {
Expand Down Expand Up @@ -191,10 +191,10 @@ func processEndpointAppliedRules(appliedPolicies []*antreatypes.NetworkPolicy, i
// check if the Kubernetes NetworkPolicy creates ingress or egress isolationRules
for _, rule := range internalPolicy.Rules {
if rule.Direction == controlplane.DirectionIn && !isSourceEndpoint {
isolationRules = append(isolationRules, &antreatypes.RuleInfo{Policy: internalPolicy, Index: math.MaxInt,
isolationRules = append(isolationRules, &antreatypes.RuleInfo{Policy: internalPolicy, Index: math.MaxInt32,
Rule: &controlplane.NetworkPolicyRule{Direction: rule.Direction, Name: rule.Name, Action: rule.Action}})
} else if rule.Direction == controlplane.DirectionOut && isSourceEndpoint {
isolationRules = append(isolationRules, &antreatypes.RuleInfo{Policy: internalPolicy, Index: math.MaxInt,
isolationRules = append(isolationRules, &antreatypes.RuleInfo{Policy: internalPolicy, Index: math.MaxInt32,
Rule: &controlplane.NetworkPolicyRule{Direction: rule.Direction, Name: rule.Name, Action: rule.Action}})
}
}
Expand Down Expand Up @@ -313,7 +313,7 @@ func (eq *policyRuleQuerier) QueryNetworkPolicyEvaluation(entities *controlplane
}
return &controlplane.NetworkPolicyEvaluationResponse{
NetworkPolicy: *endpointAnalysisRule.Policy.SourceRef,
RuleIndex: int32(endpointAnalysisRule.Index),
RuleIndex: endpointAnalysisRule.Index,
Rule: controlplane.RuleRef{
Direction: endpointAnalysisRule.Rule.Direction,
Name: endpointAnalysisRule.Rule.Name,
Expand Down
7 changes: 4 additions & 3 deletions pkg/controller/networkpolicy/endpoint_querier_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@ package networkpolicy

import (
"fmt"
"math"
"testing"
"time"

Expand Down Expand Up @@ -395,7 +396,7 @@ func TestQueryNetworkPolicyEvaluation(t *testing.T) {
for i := 0; i < len(policy.Rules); i++ {
ruleInfoMatches[i] = &antreatypes.RuleInfo{
Policy: policy,
Index: i,
Index: int32(i),
Rule: &controlplane.NetworkPolicyRule{Direction: policy.Rules[i].Direction, Name: policy.Rules[i].Name, Action: policy.Rules[i].Action},
}
}
Expand Down Expand Up @@ -529,7 +530,7 @@ func TestQueryNetworkPolicyEvaluation(t *testing.T) {
},
expectedResult: &controlplane.NetworkPolicyEvaluationResponse{
NetworkPolicy: controlplane.NetworkPolicyReference{Type: controlplane.K8sNetworkPolicy, Namespace: namespace, Name: "Policy111", UID: uid1},
RuleIndex: -1,
RuleIndex: math.MaxInt32,
Rule: controlplane.RuleRef{Direction: controlplane.DirectionOut, Name: "Policy111Rule0"},
},
},
Expand All @@ -542,7 +543,7 @@ func TestQueryNetworkPolicyEvaluation(t *testing.T) {
},
expectedResult: &controlplane.NetworkPolicyEvaluationResponse{
NetworkPolicy: controlplane.NetworkPolicyReference{Type: controlplane.K8sNetworkPolicy, Namespace: namespace, Name: "Policy222", UID: uid2},
RuleIndex: -1,
RuleIndex: math.MaxInt32,
Rule: controlplane.RuleRef{Direction: controlplane.DirectionIn, Name: "Policy222Rule0"},
},
},
Expand Down
2 changes: 1 addition & 1 deletion pkg/controller/types/networkpolicy.go
Original file line number Diff line number Diff line change
Expand Up @@ -139,7 +139,7 @@ func (p *NetworkPolicy) GetAppliedToGroups() sets.Set[string] {
// corresponding ingress/egress rules, and the original rule info.
type RuleInfo struct {
Policy *NetworkPolicy
Index int
Index int32
Rule *controlplane.NetworkPolicyRule
}

Expand Down

0 comments on commit 933e5cb

Please sign in to comment.