mirror of
https://github.com/k3s-io/kubernetes.git
synced 2025-08-01 15:58:37 +00:00
Fix incorrect message on describe netpol
When I describe network policies, it often tells me that pods are isolated for egress connectivity because the policy that applies to them has no egress rules. However, this would only lead to isolation if there is an explicitly set egress policy type. Otherwise, the policy allows egress traffic. The same applies if you have explicitly set an egress type only, describe will incorrectly report isolated ingress traffic. This PR fixes this by inferring the applicable direction for the policy based on the PolicyTypes, and then if a policy doesn't apply eg to egress, we print 'Not affecting egress traffic'
This commit is contained in:
parent
bef8d426f2
commit
7753bfa3a4
@ -3745,13 +3745,38 @@ func describeNetworkPolicySpec(nps networkingv1.NetworkPolicySpec, w PrefixWrite
|
||||
} else {
|
||||
w.Write(LEVEL_2, "%s\n", metav1.FormatLabelSelector(&nps.PodSelector))
|
||||
}
|
||||
w.Write(LEVEL_1, "Allowing ingress traffic:\n")
|
||||
printNetworkPolicySpecIngressFrom(nps.Ingress, " ", w)
|
||||
w.Write(LEVEL_1, "Allowing egress traffic:\n")
|
||||
printNetworkPolicySpecEgressTo(nps.Egress, " ", w)
|
||||
|
||||
ingressEnabled, egressEnabled := getPolicyType(nps)
|
||||
if ingressEnabled {
|
||||
w.Write(LEVEL_1, "Allowing ingress traffic:\n")
|
||||
printNetworkPolicySpecIngressFrom(nps.Ingress, " ", w)
|
||||
} else {
|
||||
w.Write(LEVEL_1, "Not affecting ingress traffic\n")
|
||||
}
|
||||
if egressEnabled {
|
||||
w.Write(LEVEL_1, "Allowing egress traffic:\n")
|
||||
printNetworkPolicySpecEgressTo(nps.Egress, " ", w)
|
||||
} else {
|
||||
w.Write(LEVEL_1, "Not affecting egress traffic\n")
|
||||
|
||||
}
|
||||
w.Write(LEVEL_1, "Policy Types: %v\n", policyTypesToString(nps.PolicyTypes))
|
||||
}
|
||||
|
||||
func getPolicyType(nps networkingv1.NetworkPolicySpec) (bool, bool) {
|
||||
var ingress, egress bool
|
||||
for _, pt := range nps.PolicyTypes {
|
||||
switch pt {
|
||||
case networkingv1.PolicyTypeIngress:
|
||||
ingress = true
|
||||
case networkingv1.PolicyTypeEgress:
|
||||
egress = true
|
||||
}
|
||||
}
|
||||
|
||||
return ingress, egress
|
||||
}
|
||||
|
||||
func printNetworkPolicySpecIngressFrom(npirs []networkingv1.NetworkPolicyIngressRule, initialIndent string, w PrefixWriter) {
|
||||
if len(npirs) == 0 {
|
||||
w.Write(LEVEL_0, "%s%s\n", initialIndent, "<none> (Selected pods are isolated for ingress connectivity)")
|
||||
|
@ -3142,6 +3142,261 @@ Spec:
|
||||
}
|
||||
}
|
||||
|
||||
func TestDescribeIngressNetworkPolicies(t *testing.T) {
|
||||
expectedTime, err := time.Parse("2006-01-02 15:04:05 Z0700 MST", "2017-06-04 21:45:56 -0700 PDT")
|
||||
if err != nil {
|
||||
t.Errorf("unable to parse time %q error: %s", "2017-06-04 21:45:56 -0700 PDT", err)
|
||||
}
|
||||
expectedOut := `Name: network-policy-1
|
||||
Namespace: default
|
||||
Created on: 2017-06-04 21:45:56 -0700 PDT
|
||||
Labels: <none>
|
||||
Annotations: <none>
|
||||
Spec:
|
||||
PodSelector: foo in (bar1,bar2),foo2 notin (bar1,bar2),id1=app1,id2=app2
|
||||
Allowing ingress traffic:
|
||||
To Port: 80/TCP
|
||||
To Port: 82/TCP
|
||||
From:
|
||||
NamespaceSelector: id=ns1,id2=ns2
|
||||
PodSelector: id=pod1,id2=pod2
|
||||
From:
|
||||
PodSelector: id=app2,id2=app3
|
||||
From:
|
||||
NamespaceSelector: id=app2,id2=app3
|
||||
From:
|
||||
NamespaceSelector: foo in (bar1,bar2),id=app2,id2=app3
|
||||
From:
|
||||
IPBlock:
|
||||
CIDR: 192.168.0.0/16
|
||||
Except: 192.168.3.0/24, 192.168.4.0/24
|
||||
----------
|
||||
To Port: <any> (traffic allowed to all ports)
|
||||
From: <any> (traffic not restricted by source)
|
||||
Not affecting egress traffic
|
||||
Policy Types: Ingress
|
||||
`
|
||||
|
||||
port80 := intstr.FromInt(80)
|
||||
port82 := intstr.FromInt(82)
|
||||
protoTCP := corev1.ProtocolTCP
|
||||
|
||||
versionedFake := fake.NewSimpleClientset(&networkingv1.NetworkPolicy{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
Name: "network-policy-1",
|
||||
Namespace: "default",
|
||||
CreationTimestamp: metav1.NewTime(expectedTime),
|
||||
},
|
||||
Spec: networkingv1.NetworkPolicySpec{
|
||||
PodSelector: metav1.LabelSelector{
|
||||
MatchLabels: map[string]string{
|
||||
"id1": "app1",
|
||||
"id2": "app2",
|
||||
},
|
||||
MatchExpressions: []metav1.LabelSelectorRequirement{
|
||||
{Key: "foo", Operator: "In", Values: []string{"bar1", "bar2"}},
|
||||
{Key: "foo2", Operator: "NotIn", Values: []string{"bar1", "bar2"}},
|
||||
},
|
||||
},
|
||||
Ingress: []networkingv1.NetworkPolicyIngressRule{
|
||||
{
|
||||
Ports: []networkingv1.NetworkPolicyPort{
|
||||
{Port: &port80},
|
||||
{Port: &port82, Protocol: &protoTCP},
|
||||
},
|
||||
From: []networkingv1.NetworkPolicyPeer{
|
||||
{
|
||||
PodSelector: &metav1.LabelSelector{
|
||||
MatchLabels: map[string]string{
|
||||
"id": "pod1",
|
||||
"id2": "pod2",
|
||||
},
|
||||
},
|
||||
NamespaceSelector: &metav1.LabelSelector{
|
||||
MatchLabels: map[string]string{
|
||||
"id": "ns1",
|
||||
"id2": "ns2",
|
||||
},
|
||||
},
|
||||
},
|
||||
{
|
||||
PodSelector: &metav1.LabelSelector{
|
||||
MatchLabels: map[string]string{
|
||||
"id": "app2",
|
||||
"id2": "app3",
|
||||
},
|
||||
},
|
||||
},
|
||||
{
|
||||
NamespaceSelector: &metav1.LabelSelector{
|
||||
MatchLabels: map[string]string{
|
||||
"id": "app2",
|
||||
"id2": "app3",
|
||||
},
|
||||
},
|
||||
},
|
||||
{
|
||||
NamespaceSelector: &metav1.LabelSelector{
|
||||
MatchLabels: map[string]string{
|
||||
"id": "app2",
|
||||
"id2": "app3",
|
||||
},
|
||||
MatchExpressions: []metav1.LabelSelectorRequirement{
|
||||
{Key: "foo", Operator: "In", Values: []string{"bar1", "bar2"}},
|
||||
},
|
||||
},
|
||||
},
|
||||
{
|
||||
IPBlock: &networkingv1.IPBlock{
|
||||
CIDR: "192.168.0.0/16",
|
||||
Except: []string{"192.168.3.0/24", "192.168.4.0/24"},
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
{},
|
||||
},
|
||||
PolicyTypes: []networkingv1.PolicyType{networkingv1.PolicyTypeIngress},
|
||||
},
|
||||
})
|
||||
d := NetworkPolicyDescriber{versionedFake}
|
||||
out, err := d.Describe("default", "network-policy-1", describe.DescriberSettings{})
|
||||
if err != nil {
|
||||
t.Errorf("unexpected error: %s", err)
|
||||
}
|
||||
if out != expectedOut {
|
||||
t.Errorf("want:\n%s\ngot:\n%s", expectedOut, out)
|
||||
}
|
||||
}
|
||||
|
||||
func TestDescribeIsolatedEgressNetworkPolicies(t *testing.T) {
|
||||
expectedTime, err := time.Parse("2006-01-02 15:04:05 Z0700 MST", "2017-06-04 21:45:56 -0700 PDT")
|
||||
if err != nil {
|
||||
t.Errorf("unable to parse time %q error: %s", "2017-06-04 21:45:56 -0700 PDT", err)
|
||||
}
|
||||
expectedOut := `Name: network-policy-1
|
||||
Namespace: default
|
||||
Created on: 2017-06-04 21:45:56 -0700 PDT
|
||||
Labels: <none>
|
||||
Annotations: <none>
|
||||
Spec:
|
||||
PodSelector: foo in (bar1,bar2),foo2 notin (bar1,bar2),id1=app1,id2=app2
|
||||
Allowing ingress traffic:
|
||||
To Port: 80/TCP
|
||||
To Port: 82/TCP
|
||||
From:
|
||||
NamespaceSelector: id=ns1,id2=ns2
|
||||
PodSelector: id=pod1,id2=pod2
|
||||
From:
|
||||
PodSelector: id=app2,id2=app3
|
||||
From:
|
||||
NamespaceSelector: id=app2,id2=app3
|
||||
From:
|
||||
NamespaceSelector: foo in (bar1,bar2),id=app2,id2=app3
|
||||
From:
|
||||
IPBlock:
|
||||
CIDR: 192.168.0.0/16
|
||||
Except: 192.168.3.0/24, 192.168.4.0/24
|
||||
----------
|
||||
To Port: <any> (traffic allowed to all ports)
|
||||
From: <any> (traffic not restricted by source)
|
||||
Allowing egress traffic:
|
||||
<none> (Selected pods are isolated for egress connectivity)
|
||||
Policy Types: Ingress, Egress
|
||||
`
|
||||
|
||||
port80 := intstr.FromInt(80)
|
||||
port82 := intstr.FromInt(82)
|
||||
protoTCP := corev1.ProtocolTCP
|
||||
|
||||
versionedFake := fake.NewSimpleClientset(&networkingv1.NetworkPolicy{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
Name: "network-policy-1",
|
||||
Namespace: "default",
|
||||
CreationTimestamp: metav1.NewTime(expectedTime),
|
||||
},
|
||||
Spec: networkingv1.NetworkPolicySpec{
|
||||
PodSelector: metav1.LabelSelector{
|
||||
MatchLabels: map[string]string{
|
||||
"id1": "app1",
|
||||
"id2": "app2",
|
||||
},
|
||||
MatchExpressions: []metav1.LabelSelectorRequirement{
|
||||
{Key: "foo", Operator: "In", Values: []string{"bar1", "bar2"}},
|
||||
{Key: "foo2", Operator: "NotIn", Values: []string{"bar1", "bar2"}},
|
||||
},
|
||||
},
|
||||
Ingress: []networkingv1.NetworkPolicyIngressRule{
|
||||
{
|
||||
Ports: []networkingv1.NetworkPolicyPort{
|
||||
{Port: &port80},
|
||||
{Port: &port82, Protocol: &protoTCP},
|
||||
},
|
||||
From: []networkingv1.NetworkPolicyPeer{
|
||||
{
|
||||
PodSelector: &metav1.LabelSelector{
|
||||
MatchLabels: map[string]string{
|
||||
"id": "pod1",
|
||||
"id2": "pod2",
|
||||
},
|
||||
},
|
||||
NamespaceSelector: &metav1.LabelSelector{
|
||||
MatchLabels: map[string]string{
|
||||
"id": "ns1",
|
||||
"id2": "ns2",
|
||||
},
|
||||
},
|
||||
},
|
||||
{
|
||||
PodSelector: &metav1.LabelSelector{
|
||||
MatchLabels: map[string]string{
|
||||
"id": "app2",
|
||||
"id2": "app3",
|
||||
},
|
||||
},
|
||||
},
|
||||
{
|
||||
NamespaceSelector: &metav1.LabelSelector{
|
||||
MatchLabels: map[string]string{
|
||||
"id": "app2",
|
||||
"id2": "app3",
|
||||
},
|
||||
},
|
||||
},
|
||||
{
|
||||
NamespaceSelector: &metav1.LabelSelector{
|
||||
MatchLabels: map[string]string{
|
||||
"id": "app2",
|
||||
"id2": "app3",
|
||||
},
|
||||
MatchExpressions: []metav1.LabelSelectorRequirement{
|
||||
{Key: "foo", Operator: "In", Values: []string{"bar1", "bar2"}},
|
||||
},
|
||||
},
|
||||
},
|
||||
{
|
||||
IPBlock: &networkingv1.IPBlock{
|
||||
CIDR: "192.168.0.0/16",
|
||||
Except: []string{"192.168.3.0/24", "192.168.4.0/24"},
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
{},
|
||||
},
|
||||
PolicyTypes: []networkingv1.PolicyType{networkingv1.PolicyTypeIngress, networkingv1.PolicyTypeEgress},
|
||||
},
|
||||
})
|
||||
d := NetworkPolicyDescriber{versionedFake}
|
||||
out, err := d.Describe("default", "network-policy-1", describe.DescriberSettings{})
|
||||
if err != nil {
|
||||
t.Errorf("unexpected error: %s", err)
|
||||
}
|
||||
if out != expectedOut {
|
||||
t.Errorf("want:\n%s\ngot:\n%s", expectedOut, out)
|
||||
}
|
||||
}
|
||||
|
||||
func TestDescribeServiceAccount(t *testing.T) {
|
||||
fake := fake.NewSimpleClientset(&corev1.ServiceAccount{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
|
Loading…
Reference in New Issue
Block a user