mirror of
				https://github.com/optim-enterprises-bv/kubernetes.git
				synced 2025-11-03 19:58:17 +00:00 
			
		
		
		
	Promote endPort to GA
This commit is contained in:
		
				
					committed by
					
						
						Ricardo Pchevuzinske Katz
					
				
			
			
				
	
			
			
			
						parent
						
							f045fb688f
						
					
				
				
					commit
					3e7bdbbf30
				
			@@ -154,8 +154,6 @@ type NetworkPolicyPort struct {
 | 
			
		||||
	// should be allowed by the policy. This field cannot be defined if the port field
 | 
			
		||||
	// is not defined or if the port field is defined as a named (string) port.
 | 
			
		||||
	// The endPort must be equal or greater than port.
 | 
			
		||||
	// This feature is in Beta state and is enabled by default.
 | 
			
		||||
	// It can be disabled using the Feature Gate "NetworkPolicyEndPort".
 | 
			
		||||
	// +optional
 | 
			
		||||
	EndPort *int32
 | 
			
		||||
}
 | 
			
		||||
 
 | 
			
		||||
@@ -545,6 +545,7 @@ const (
 | 
			
		||||
	// kep: http://kep.k8s.io/2079
 | 
			
		||||
	// alpha: v1.21
 | 
			
		||||
	// beta:  v1.22
 | 
			
		||||
	// ga: v1.25
 | 
			
		||||
	//
 | 
			
		||||
	// Enables the endPort field in NetworkPolicy to enable a Port Range behavior in Network Policies.
 | 
			
		||||
	NetworkPolicyEndPort featuregate.Feature = "NetworkPolicyEndPort"
 | 
			
		||||
@@ -945,7 +946,7 @@ var defaultKubernetesFeatureGates = map[featuregate.Feature]featuregate.FeatureS
 | 
			
		||||
 | 
			
		||||
	MixedProtocolLBService: {Default: true, PreRelease: featuregate.Beta},
 | 
			
		||||
 | 
			
		||||
	NetworkPolicyEndPort: {Default: true, PreRelease: featuregate.Beta},
 | 
			
		||||
	NetworkPolicyEndPort: {Default: true, PreRelease: featuregate.GA, LockToDefault: true}, // remove in 1.27
 | 
			
		||||
 | 
			
		||||
	NetworkPolicyStatus: {Default: false, PreRelease: featuregate.Alpha},
 | 
			
		||||
 | 
			
		||||
 
 | 
			
		||||
@@ -71,9 +71,6 @@ func (networkPolicyStrategy) PrepareForCreate(ctx context.Context, obj runtime.O
 | 
			
		||||
 | 
			
		||||
	networkPolicy.Generation = 1
 | 
			
		||||
 | 
			
		||||
	if !utilfeature.DefaultFeatureGate.Enabled(features.NetworkPolicyEndPort) {
 | 
			
		||||
		dropNetworkPolicyEndPort(networkPolicy)
 | 
			
		||||
	}
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
// PrepareForUpdate clears fields that are not allowed to be set by end users on update.
 | 
			
		||||
@@ -88,10 +85,6 @@ func (networkPolicyStrategy) PrepareForUpdate(ctx context.Context, obj, old runt
 | 
			
		||||
		newNetworkPolicy.Status = oldNetworkPolicy.Status
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	if !utilfeature.DefaultFeatureGate.Enabled(features.NetworkPolicyEndPort) && !endPortInUse(oldNetworkPolicy) {
 | 
			
		||||
		dropNetworkPolicyEndPort(newNetworkPolicy)
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	// Any changes to the spec increment the generation number, any changes to the
 | 
			
		||||
	// status should reflect the generation number of the corresponding object.
 | 
			
		||||
	// See metav1.ObjectMeta description for more information on Generation.
 | 
			
		||||
@@ -187,42 +180,3 @@ func (networkPolicyStatusStrategy) ValidateUpdate(ctx context.Context, obj, old
 | 
			
		||||
func (networkPolicyStatusStrategy) WarningsOnUpdate(ctx context.Context, obj, old runtime.Object) []string {
 | 
			
		||||
	return nil
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
// Drops Network Policy EndPort fields if Feature Gate is also disabled.
 | 
			
		||||
// This should be used in future Network Policy evolutions
 | 
			
		||||
func dropNetworkPolicyEndPort(netPol *networking.NetworkPolicy) {
 | 
			
		||||
	for idx, ingressSpec := range netPol.Spec.Ingress {
 | 
			
		||||
		for idxPort, port := range ingressSpec.Ports {
 | 
			
		||||
			if port.EndPort != nil {
 | 
			
		||||
				netPol.Spec.Ingress[idx].Ports[idxPort].EndPort = nil
 | 
			
		||||
			}
 | 
			
		||||
		}
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	for idx, egressSpec := range netPol.Spec.Egress {
 | 
			
		||||
		for idxPort, port := range egressSpec.Ports {
 | 
			
		||||
			if port.EndPort != nil {
 | 
			
		||||
				netPol.Spec.Egress[idx].Ports[idxPort].EndPort = nil
 | 
			
		||||
			}
 | 
			
		||||
		}
 | 
			
		||||
	}
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
func endPortInUse(netPol *networking.NetworkPolicy) bool {
 | 
			
		||||
	for _, ingressSpec := range netPol.Spec.Ingress {
 | 
			
		||||
		for _, port := range ingressSpec.Ports {
 | 
			
		||||
			if port.EndPort != nil {
 | 
			
		||||
				return true
 | 
			
		||||
			}
 | 
			
		||||
		}
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	for _, egressSpec := range netPol.Spec.Egress {
 | 
			
		||||
		for _, port := range egressSpec.Ports {
 | 
			
		||||
			if port.EndPort != nil {
 | 
			
		||||
				return true
 | 
			
		||||
			}
 | 
			
		||||
		}
 | 
			
		||||
	}
 | 
			
		||||
	return false
 | 
			
		||||
}
 | 
			
		||||
 
 | 
			
		||||
@@ -18,7 +18,6 @@ package networkpolicy
 | 
			
		||||
 | 
			
		||||
import (
 | 
			
		||||
	"context"
 | 
			
		||||
	"fmt"
 | 
			
		||||
	"reflect"
 | 
			
		||||
	"testing"
 | 
			
		||||
	"time"
 | 
			
		||||
@@ -94,173 +93,14 @@ func makeNetworkPolicy(isIngress, isEgress, hasEndPort bool) *networking.Network
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
func TestNetworkPolicyStrategy(t *testing.T) {
 | 
			
		||||
	for _, tc := range []struct {
 | 
			
		||||
		name              string
 | 
			
		||||
		hasEndPort        bool
 | 
			
		||||
		enableFeatureGate bool
 | 
			
		||||
		isIngress         bool
 | 
			
		||||
		isEgress          bool
 | 
			
		||||
	}{
 | 
			
		||||
		{
 | 
			
		||||
			name:              "Create Ingress Rule with EndPort Feature Gate enabled and with EndPort defined",
 | 
			
		||||
			hasEndPort:        true,
 | 
			
		||||
			enableFeatureGate: true,
 | 
			
		||||
			isIngress:         true,
 | 
			
		||||
			isEgress:          false,
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			name:              "Create Ingress Rule with EndPort Feature Gate disabled and with EndPort defined",
 | 
			
		||||
			hasEndPort:        true,
 | 
			
		||||
			enableFeatureGate: false,
 | 
			
		||||
			isIngress:         true,
 | 
			
		||||
			isEgress:          false,
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			name:              "Create Ingress Rule with EndPort Feature Gate enabled and with endPort undefined",
 | 
			
		||||
			hasEndPort:        false,
 | 
			
		||||
			enableFeatureGate: true,
 | 
			
		||||
			isIngress:         true,
 | 
			
		||||
			isEgress:          false,
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			name:              "Create Ingress Rule with EndPort Feature Gate disabled and with endPort undefined",
 | 
			
		||||
			hasEndPort:        false,
 | 
			
		||||
			enableFeatureGate: false,
 | 
			
		||||
			isIngress:         true,
 | 
			
		||||
			isEgress:          false,
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			name:              "Create Egress Rule with EndPort Feature Gate enabled and with endPort defined",
 | 
			
		||||
			hasEndPort:        true,
 | 
			
		||||
			enableFeatureGate: true,
 | 
			
		||||
			isIngress:         false,
 | 
			
		||||
			isEgress:          true,
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			name:              "Create Egress Rule with EndPort Feature Gate enabled and with endPort defined",
 | 
			
		||||
			hasEndPort:        true,
 | 
			
		||||
			enableFeatureGate: false,
 | 
			
		||||
			isIngress:         false,
 | 
			
		||||
			isEgress:          true,
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			name:              "Create Egress Rule with EndPort Feature Gate true and with endPort undefined",
 | 
			
		||||
			hasEndPort:        false,
 | 
			
		||||
			enableFeatureGate: true,
 | 
			
		||||
			isIngress:         false,
 | 
			
		||||
			isEgress:          true,
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			name:              "Create Egress Rule with EndPort Feature Gate disabled and with endPort undefined",
 | 
			
		||||
			hasEndPort:        false,
 | 
			
		||||
			enableFeatureGate: false,
 | 
			
		||||
			isIngress:         false,
 | 
			
		||||
			isEgress:          true,
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			name:              "Create Ingress and Egress Rule with EndPort Feature Gate enabled and endPort defined",
 | 
			
		||||
			hasEndPort:        true,
 | 
			
		||||
			enableFeatureGate: true,
 | 
			
		||||
			isIngress:         true,
 | 
			
		||||
			isEgress:          true,
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			name:              "Create Ingress and Egress Rule with EndPort Feature Gate disabled and endPort defined",
 | 
			
		||||
			hasEndPort:        true,
 | 
			
		||||
			enableFeatureGate: false,
 | 
			
		||||
			isIngress:         true,
 | 
			
		||||
			isEgress:          true,
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			name:              "Create Ingress and Egress Rule with EndPort Feature Gate enabled and endPort undefined",
 | 
			
		||||
			hasEndPort:        false,
 | 
			
		||||
			enableFeatureGate: true,
 | 
			
		||||
			isIngress:         true,
 | 
			
		||||
			isEgress:          true,
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			name:              "Create Ingress and Egress Rule with EndPort Feature Gate disabled and endPort undefined",
 | 
			
		||||
			hasEndPort:        false,
 | 
			
		||||
			enableFeatureGate: false,
 | 
			
		||||
			isIngress:         true,
 | 
			
		||||
			isEgress:          true,
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			name:              "Create a null rule with EndPort Feature Gate enabled",
 | 
			
		||||
			hasEndPort:        false,
 | 
			
		||||
			enableFeatureGate: true,
 | 
			
		||||
			isIngress:         false,
 | 
			
		||||
			isEgress:          false,
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			name:              "Create a null rule with EndPort Feature Gate disabled",
 | 
			
		||||
			hasEndPort:        false,
 | 
			
		||||
			enableFeatureGate: false,
 | 
			
		||||
			isIngress:         false,
 | 
			
		||||
			isEgress:          false,
 | 
			
		||||
		},
 | 
			
		||||
	} {
 | 
			
		||||
		defer featuregatetesting.SetFeatureGateDuringTest(t, utilfeature.DefaultFeatureGate, features.NetworkPolicyEndPort, tc.enableFeatureGate)()
 | 
			
		||||
 | 
			
		||||
	// Create a Network Policy containing EndPort defined to compare with the generated by the tests
 | 
			
		||||
		expectedNewNetPol := makeNetworkPolicy(tc.isIngress, tc.isEgress,
 | 
			
		||||
			(tc.hasEndPort && tc.enableFeatureGate))
 | 
			
		||||
 | 
			
		||||
		netPol := makeNetworkPolicy(tc.isIngress, tc.isEgress, tc.hasEndPort)
 | 
			
		||||
		Strategy.PrepareForCreate(context.Background(), netPol)
 | 
			
		||||
		if !reflect.DeepEqual(netPol.Spec, expectedNewNetPol.Spec) {
 | 
			
		||||
			t.Errorf("Create: %s failed. Spec from NetworkPolicy is not equal to the expected. \nGot: %+v \nExpected: %+v",
 | 
			
		||||
				tc.name, netPol, expectedNewNetPol)
 | 
			
		||||
		}
 | 
			
		||||
 | 
			
		||||
		if netPol.Generation != 1 {
 | 
			
		||||
			t.Errorf("Create: Test %s failed. Network Policy Generation should be 1, got %d",
 | 
			
		||||
				tc.name, netPol.Generation)
 | 
			
		||||
		}
 | 
			
		||||
 | 
			
		||||
		errs := Strategy.Validate(context.Background(), netPol)
 | 
			
		||||
		if len(errs) != 0 {
 | 
			
		||||
			t.Errorf("Unexpected error from validation for created Network Policy: %v", errs)
 | 
			
		||||
		}
 | 
			
		||||
 | 
			
		||||
		// Test when an updated Network Policy drops the EndPort field even if the FG has been disabled
 | 
			
		||||
		// but the field is present
 | 
			
		||||
		oldNetPol := makeNetworkPolicy(tc.isIngress, tc.isEgress, tc.hasEndPort)
 | 
			
		||||
		updatedNetPol := makeNetworkPolicy(tc.isIngress, tc.isEgress, tc.hasEndPort)
 | 
			
		||||
		expectedUpdatedNetPol := makeNetworkPolicy(tc.isIngress, tc.isEgress, tc.hasEndPort)
 | 
			
		||||
		Strategy.PrepareForUpdate(context.Background(), updatedNetPol, oldNetPol)
 | 
			
		||||
 | 
			
		||||
		if !reflect.DeepEqual(updatedNetPol.Spec, expectedUpdatedNetPol.Spec) {
 | 
			
		||||
			t.Errorf("Update: %s failed. Spec from NetworkPolicy is not equal to the expected. \nGot: %+v \nExpected: %+v",
 | 
			
		||||
				tc.name, updatedNetPol, expectedUpdatedNetPol)
 | 
			
		||||
		}
 | 
			
		||||
 | 
			
		||||
		if updatedNetPol.Generation != 0 && !tc.enableFeatureGate {
 | 
			
		||||
			t.Errorf("Update: Test %s failed. Network Policy Generation should be 1, got %d",
 | 
			
		||||
				tc.name, updatedNetPol.Generation)
 | 
			
		||||
		}
 | 
			
		||||
 | 
			
		||||
		errs = Strategy.Validate(context.Background(), updatedNetPol)
 | 
			
		||||
		if len(errs) != 0 {
 | 
			
		||||
			t.Errorf("Unexpected error from validation for updated Network Policy: %v", errs)
 | 
			
		||||
		}
 | 
			
		||||
	}
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
func TestNetworkPolicyEndPortEnablement(t *testing.T) {
 | 
			
		||||
	// Enable the Feature Gate during the first rule creation
 | 
			
		||||
	defer featuregatetesting.SetFeatureGateDuringTest(t, utilfeature.DefaultFeatureGate, features.NetworkPolicyEndPort, true)()
 | 
			
		||||
	netPol := makeNetworkPolicy(true, true, true)
 | 
			
		||||
	// We always expect the EndPort to be present, even if the FG is disabled later
 | 
			
		||||
	expectedNetPol := makeNetworkPolicy(true, true, true)
 | 
			
		||||
	netPol := makeNetworkPolicy(true, true, false)
 | 
			
		||||
 | 
			
		||||
	Strategy.PrepareForCreate(context.Background(), netPol)
 | 
			
		||||
	if !reflect.DeepEqual(netPol.Spec, expectedNetPol.Spec) {
 | 
			
		||||
		t.Errorf("Create with enabled FG failed. Spec from NetworkPolicy is not equal to the expected. \nGot: %+v \nExpected: %+v",
 | 
			
		||||
			netPol, expectedNetPol)
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	if netPol.Generation != 1 {
 | 
			
		||||
		t.Errorf("Create with enabled FG failed. Network Policy Generation should be 1, got %d",
 | 
			
		||||
		t.Errorf("Create: Test failed. Network Policy Generation should be 1, got %d",
 | 
			
		||||
			netPol.Generation)
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
@@ -269,18 +109,15 @@ func TestNetworkPolicyEndPortEnablement(t *testing.T) {
 | 
			
		||||
		t.Errorf("Unexpected error from validation for created Network Policy: %v", errs)
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	// Now let's disable the Feature Gate, update some other field from NetPol and expect the EndPort is already present
 | 
			
		||||
	defer featuregatetesting.SetFeatureGateDuringTest(t, utilfeature.DefaultFeatureGate, features.NetworkPolicyEndPort, false)()
 | 
			
		||||
	updateNetPol, err := testUpdateEndPort(netPol)
 | 
			
		||||
	if err != nil {
 | 
			
		||||
		t.Errorf("Update with disabled FG failed. %v", err)
 | 
			
		||||
	}
 | 
			
		||||
	// And let's enable the FG again, add another from and check if the EndPort field is still present
 | 
			
		||||
	defer featuregatetesting.SetFeatureGateDuringTest(t, utilfeature.DefaultFeatureGate, features.NetworkPolicyEndPort, true)()
 | 
			
		||||
	_, err = testUpdateEndPort(updateNetPol)
 | 
			
		||||
	if err != nil {
 | 
			
		||||
		t.Errorf("Update with enabled FG failed. %v", err)
 | 
			
		||||
	updatedNetPol := makeNetworkPolicy(true, true, true)
 | 
			
		||||
	updatedNetPol.ObjectMeta.SetResourceVersion("1")
 | 
			
		||||
	Strategy.PrepareForUpdate(context.Background(), updatedNetPol, netPol)
 | 
			
		||||
 | 
			
		||||
	errs = Strategy.ValidateUpdate(context.Background(), updatedNetPol, netPol)
 | 
			
		||||
	if len(errs) != 0 {
 | 
			
		||||
		t.Errorf("Unexpected error from validation for updated Network Policy: %v", errs)
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
func TestNetworkPolicyStatusStrategy(t *testing.T) {
 | 
			
		||||
@@ -450,40 +287,3 @@ func TestNetworkPolicyStatusStrategyEnablement(t *testing.T) {
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
func testUpdateEndPort(oldNetPol *networking.NetworkPolicy) (*networking.NetworkPolicy, error) {
 | 
			
		||||
	updatedNetPol := makeNetworkPolicy(true, true, true)
 | 
			
		||||
	expectedNetPol := makeNetworkPolicy(true, true, true)
 | 
			
		||||
 | 
			
		||||
	if oldNetPol == nil {
 | 
			
		||||
		return nil, fmt.Errorf("Nil Network Policy received")
 | 
			
		||||
	}
 | 
			
		||||
	expectedGeneration := oldNetPol.GetGeneration() + 1
 | 
			
		||||
	labelValue := fmt.Sprintf("bla%d", expectedGeneration)
 | 
			
		||||
 | 
			
		||||
	updateFrom := networking.NetworkPolicyPeer{
 | 
			
		||||
		NamespaceSelector: &metav1.LabelSelector{
 | 
			
		||||
			MatchLabels: map[string]string{"e": labelValue},
 | 
			
		||||
		},
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	updatedNetPol.Spec.Ingress[0].From = append(updatedNetPol.Spec.Ingress[0].From, updateFrom)
 | 
			
		||||
	expectedNetPol.Spec.Ingress[0].From = append(expectedNetPol.Spec.Ingress[0].From, updateFrom)
 | 
			
		||||
 | 
			
		||||
	Strategy.PrepareForUpdate(context.Background(), updatedNetPol, oldNetPol)
 | 
			
		||||
	if !reflect.DeepEqual(updatedNetPol.Spec, expectedNetPol.Spec) {
 | 
			
		||||
		return nil, fmt.Errorf("Spec from NetworkPolicy is not equal to the expected. \nGot: %+v \nExpected: %+v",
 | 
			
		||||
			updatedNetPol, expectedNetPol)
 | 
			
		||||
	}
 | 
			
		||||
	if updatedNetPol.Generation != expectedGeneration {
 | 
			
		||||
		return nil, fmt.Errorf("Network Policy Generation should be %d, got %d",
 | 
			
		||||
			expectedGeneration, updatedNetPol.Generation)
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	errs := Strategy.Validate(context.Background(), updatedNetPol)
 | 
			
		||||
	if len(errs) != 0 {
 | 
			
		||||
		return nil, fmt.Errorf("Unexpected error from validation for created Network Policy: %v", errs)
 | 
			
		||||
	}
 | 
			
		||||
	return updatedNetPol, nil
 | 
			
		||||
 | 
			
		||||
}
 | 
			
		||||
 
 | 
			
		||||
@@ -1498,8 +1498,6 @@ type NetworkPolicyPort struct {
 | 
			
		||||
	// should be allowed by the policy. This field cannot be defined if the port field
 | 
			
		||||
	// is not defined or if the port field is defined as a named (string) port.
 | 
			
		||||
	// The endPort must be equal or greater than port.
 | 
			
		||||
	// This feature is in Beta state and is enabled by default.
 | 
			
		||||
	// It can be disabled using the Feature Gate "NetworkPolicyEndPort".
 | 
			
		||||
	// +optional
 | 
			
		||||
	EndPort *int32 `json:"endPort,omitempty" protobuf:"bytes,3,opt,name=endPort"`
 | 
			
		||||
}
 | 
			
		||||
 
 | 
			
		||||
@@ -158,8 +158,6 @@ type NetworkPolicyPort struct {
 | 
			
		||||
	// should be allowed by the policy. This field cannot be defined if the port field
 | 
			
		||||
	// is not defined or if the port field is defined as a named (string) port.
 | 
			
		||||
	// The endPort must be equal or greater than port.
 | 
			
		||||
	// This feature is in Beta state and is enabled by default.
 | 
			
		||||
	// It can be disabled using the Feature Gate "NetworkPolicyEndPort".
 | 
			
		||||
	// +optional
 | 
			
		||||
	EndPort *int32 `json:"endPort,omitempty" protobuf:"bytes,3,opt,name=endPort"`
 | 
			
		||||
}
 | 
			
		||||
 
 | 
			
		||||
@@ -219,7 +219,7 @@ var _ = common.SIGDescribe("Netpol API", func() {
 | 
			
		||||
		- EndPort field cannot be defined if the Port field is defined as a named (string) port.
 | 
			
		||||
		- EndPort field must be equal or greater than port.
 | 
			
		||||
	*/
 | 
			
		||||
	ginkgo.It("should support creating NetworkPolicy API with endport field [Feature:NetworkPolicyEndPort]", func() {
 | 
			
		||||
	ginkgo.It("should support creating NetworkPolicy API with endport field", func() {
 | 
			
		||||
		ns := f.Namespace.Name
 | 
			
		||||
		npClient := f.ClientSet.NetworkingV1().NetworkPolicies(ns)
 | 
			
		||||
 | 
			
		||||
 
 | 
			
		||||
		Reference in New Issue
	
	Block a user