Skip to content
Open
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
156 changes: 156 additions & 0 deletions pkg/operator/network_policy_drift_test.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,156 @@
package operator

import (
"context"
"testing"

mcfgv1 "github.com/openshift/api/machineconfiguration/v1"
"github.com/stretchr/testify/assert"
"github.com/stretchr/testify/require"
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"

ctrlcommon "github.com/openshift/machine-config-operator/pkg/controller/common"
)

func TestSyncNetworkPolicies_DriftProtection(t *testing.T) {
optr := testOperatorForNetworkPolicies(t, nil)
config := testRenderConfig()

err := optr.syncNetworkPolicies(config, nil)
require.NoError(t, err)

policy, err := optr.kubeClient.NetworkingV1().NetworkPolicies(ctrlcommon.MCONamespace).Get(
context.TODO(), "allow-machine-config-operator", metav1.GetOptions{})
require.NoError(t, err)

policy.Spec.Ingress = nil
_, err = optr.kubeClient.NetworkingV1().NetworkPolicies(ctrlcommon.MCONamespace).Update(
context.TODO(), policy, metav1.UpdateOptions{})
require.NoError(t, err)

modified, err := optr.kubeClient.NetworkingV1().NetworkPolicies(ctrlcommon.MCONamespace).Get(
context.TODO(), "allow-machine-config-operator", metav1.GetOptions{})
require.NoError(t, err)
assert.Empty(t, modified.Spec.Ingress, "ingress should be empty after manual modification")

err = optr.syncNetworkPolicies(config, nil)
require.NoError(t, err)

restored, err := optr.kubeClient.NetworkingV1().NetworkPolicies(ctrlcommon.MCONamespace).Get(
context.TODO(), "allow-machine-config-operator", metav1.GetOptions{})
require.NoError(t, err)
require.Len(t, restored.Spec.Ingress, 1, "ingress rules should be restored after resync")
}

func TestSyncNetworkPolicies_Idempotent(t *testing.T) {
optr := testOperatorForNetworkPolicies(t, nil)
config := testRenderConfig()

err := optr.syncNetworkPolicies(config, nil)
require.NoError(t, err)
firstCount := len(listNetworkPolicies(t, optr))

err = optr.syncNetworkPolicies(config, nil)
require.NoError(t, err)
secondCount := len(listNetworkPolicies(t, optr))

err = optr.syncNetworkPolicies(config, nil)
require.NoError(t, err)
thirdCount := len(listNetworkPolicies(t, optr))

assert.Equal(t, firstCount, secondCount, "policy count should be stable across syncs")
assert.Equal(t, secondCount, thirdCount, "policy count should be stable across syncs")
assert.Equal(t, 3, thirdCount, "should have exactly 3 static policies without layered pools")
}

func TestSyncNetworkPolicies_DeletionRecreation(t *testing.T) {
optr := testOperatorForNetworkPolicies(t, nil)
config := testRenderConfig()

err := optr.syncNetworkPolicies(config, nil)
require.NoError(t, err)
require.Len(t, listNetworkPolicies(t, optr), 3, "should start with 3 static policies")

err = optr.kubeClient.NetworkingV1().NetworkPolicies(ctrlcommon.MCONamespace).Delete(
context.TODO(), "allow-machine-config-operator", metav1.DeleteOptions{})
require.NoError(t, err)

policies := listNetworkPolicies(t, optr)
require.Len(t, policies, 2, "should have 2 policies after deletion")
assert.Nil(t, findPolicy(policies, "allow-machine-config-operator"), "deleted policy should be gone")

err = optr.syncNetworkPolicies(config, nil)
require.NoError(t, err)

policies = listNetworkPolicies(t, optr)
require.Len(t, policies, 3, "deleted policy should be re-created after resync")

recreated := findPolicy(policies, "allow-machine-config-operator")
require.NotNil(t, recreated, "allow-machine-config-operator must be re-created")
assert.Equal(t, "machine-config-operator", recreated.Spec.PodSelector.MatchLabels["k8s-app"])
require.Len(t, recreated.Spec.Ingress, 1, "re-created policy should have ingress rule")
require.Len(t, recreated.Spec.Ingress[0].Ports, 1)
assert.Equal(t, int32(9001), recreated.Spec.Ingress[0].Ports[0].Port.IntVal, "re-created policy should have metrics port")
require.Len(t, recreated.Spec.Egress, 1, "re-created policy should have egress rule")
}

func TestSyncNetworkPolicies_AllDeletedRecreation(t *testing.T) {
optr := testOperatorForNetworkPolicies(t, nil)
config := testRenderConfig()

err := optr.syncNetworkPolicies(config, nil)
require.NoError(t, err)
require.Len(t, listNetworkPolicies(t, optr), 3)

staticPolicies := []string{"default-deny", "allow-machine-config-operator", "allow-machine-config-controller"}
for _, name := range staticPolicies {
err = optr.kubeClient.NetworkingV1().NetworkPolicies(ctrlcommon.MCONamespace).Delete(
context.TODO(), name, metav1.DeleteOptions{})
require.NoError(t, err)
}
require.Empty(t, listNetworkPolicies(t, optr), "all policies should be deleted")

err = optr.syncNetworkPolicies(config, nil)
require.NoError(t, err)

policies := listNetworkPolicies(t, optr)
require.Len(t, policies, 3, "all static policies should be re-created after resync")

names := make([]string, len(policies))
for i, p := range policies {
names[i] = p.Name
}
for _, expected := range staticPolicies {
assert.Contains(t, names, expected, "policy %s should be re-created", expected)
}
}

func TestSyncNetworkPolicies_MOBDeletionRecreation(t *testing.T) {
pools := []*mcfgv1.MachineConfigPool{layeredPool("layered-worker")}
optr := testOperatorForNetworkPolicies(t, pools)
config := testRenderConfig()

err := optr.syncNetworkPolicies(config, nil)
require.NoError(t, err)

policies := listNetworkPolicies(t, optr)
require.Len(t, policies, 4, "should have 4 policies with layered pools")
require.NotNil(t, findPolicy(policies, "allow-machine-os-builder"), "MOB policy should exist")

err = optr.kubeClient.NetworkingV1().NetworkPolicies(ctrlcommon.MCONamespace).Delete(
context.TODO(), "allow-machine-os-builder", metav1.DeleteOptions{})
require.NoError(t, err)
require.Len(t, listNetworkPolicies(t, optr), 3, "MOB policy should be deleted")

err = optr.syncNetworkPolicies(config, nil)
require.NoError(t, err)

policies = listNetworkPolicies(t, optr)
require.Len(t, policies, 4, "MOB policy should be re-created after resync")

mobPolicy := findPolicy(policies, "allow-machine-os-builder")
require.NotNil(t, mobPolicy, "allow-machine-os-builder must be re-created")
assert.Equal(t, "machine-os-builder", mobPolicy.Spec.PodSelector.MatchLabels["k8s-app"])
require.Len(t, mobPolicy.Spec.Ingress, 1, "re-created MOB policy should have ingress rule")
require.Len(t, mobPolicy.Spec.Egress, 1, "re-created MOB policy should have egress rule")
}