Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

add admin and baseline network policy #9

Merged
merged 11 commits into from
Apr 25, 2024
Merged
Show file tree
Hide file tree
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
153 changes: 153 additions & 0 deletions .github/workflows/npa.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,153 @@

name: e2e_npa

on:
push:
branches:
- 'main'
tags:
- 'v*'
pull_request:
branches: [ main ]
workflow_dispatch:

env:
GO_VERSION: "1.22.0"
K8S_VERSION: "v1.29.2"
KIND_VERSION: "v0.22.0"
IMAGE_NAME: registry.k8s.io/networking/kube-network-policies
KIND_CLUSTER_NAME: kind

permissions: write-all

jobs:
build:
name: build
runs-on: ubuntu-latest
steps:
- name: Set up Go
uses: actions/setup-go@v2
with:
go-version: ${{ env.GO_VERSION }}
id: go

- name: Check out code
uses: actions/checkout@v2

- name: Build
run: |
docker build -t registry.k8s.io/networking/kube-network-policies:test -f Dockerfile .
mkdir _output
docker save registry.k8s.io/networking/kube-network-policies:test > _output/kube-network-policies-image.tar

- uses: actions/upload-artifact@v2
with:
name: test-image
path: _output/kube-network-policies-image.tar

e2e_npa:
name: e2e_npa
runs-on: ubuntu-22.04
timeout-minutes: 100
needs:
- build
strategy:
fail-fast: false
matrix:
# TODO add "dual", waiting on KEP https://github.com/kubernetes/enhancements/tree/master/keps/sig-network/3705-cloud-node-ips
ipFamily: ["ipv4", "ipv6"]
env:
JOB_NAME: "kube-network-policies-${{ matrix.ipFamily }}"
IP_FAMILY: ${{ matrix.ipFamily }}
steps:
- name: Check out code
uses: actions/checkout@v2

- name: Enable ipv4 and ipv6 forwarding
run: |
sudo sysctl -w net.ipv6.conf.all.forwarding=1
sudo sysctl -w net.ipv4.ip_forward=1

- name: Set up environment (download dependencies)
run: |
TMP_DIR=$(mktemp -d)
# kubectl
curl -L https://dl.k8s.io/${{ env.K8S_VERSION }}/bin/linux/amd64/kubectl -o ${TMP_DIR}/kubectl
# kind
curl -Lo ${TMP_DIR}/kind https://kind.sigs.k8s.io/dl/${{ env.KIND_VERSION }}/kind-linux-amd64
# Install
sudo cp ${TMP_DIR}/kubectl /usr/local/bin/kubectl
sudo cp ${TMP_DIR}/kind /usr/local/bin/kind
sudo chmod +x /usr/local/bin/*

- name: Create multi node cluster
run: |
# output_dir
mkdir -p _artifacts
# create cluster
cat <<EOF | /usr/local/bin/kind create cluster \
--name ${{ env.KIND_CLUSTER_NAME}} \
--image kindest/node:${{ env.K8S_VERSION }} \
-v7 --wait 1m --retain --config=-
kind: Cluster
apiVersion: kind.x-k8s.io/v1alpha4
networking:
ipFamily: ${IP_FAMILY}
nodes:
- role: control-plane
- role: worker
- role: worker
EOF
# dump the kubeconfig for later
/usr/local/bin/kind get kubeconfig --name ${{ env.KIND_CLUSTER_NAME}} > _artifacts/kubeconfig.conf

- uses: actions/download-artifact@v2
with:
name: test-image

- name: Install kube-network-policies
run: |
/usr/local/bin/kubectl apply -f https://raw.githubusercontent.com/kubernetes-sigs/network-policy-api/main/config/crd/experimental/policy.networking.k8s.io_adminnetworkpolicies.yaml
/usr/local/bin/kubectl apply -f https://raw.githubusercontent.com/kubernetes-sigs/network-policy-api/main/config/crd/experimental/policy.networking.k8s.io_baselineadminnetworkpolicies.yaml
# preload kube-network-policies image
docker load --input kube-network-policies-image.tar
/usr/local/bin/kind load docker-image registry.k8s.io/networking/kube-network-policies:test --name ${{ env.KIND_CLUSTER_NAME}}
sed -i s#registry.k8s.io/networking/kube-network-policies.*#registry.k8s.io/networking/kube-network-policies:test# install-anp.yaml
/usr/local/bin/kubectl apply -f ./install-anp.yaml

- name: Get Cluster status
run: |
# wait network is ready
sleep 5
/usr/local/bin/kubectl get nodes -o wide
/usr/local/bin/kubectl get pods -A
/usr/local/bin/kubectl wait --timeout=1m --for=condition=ready pods --namespace=kube-system -l k8s-app=kube-dns
/usr/local/bin/kubectl wait --timeout=1m --for=condition=ready pods --namespace=kube-system -l app=kube-network-policies

- name: Run tests
run: |
# https://network-policy-api.sigs.k8s.io/npeps/npep-137-conformance-profiles/#integration
git clone https://github.com/kubernetes-sigs/network-policy-api.git
cd network-policy-api/
go mod download
go test -v ./conformance -run TestConformanceProfiles -args --conformance-profiles=AdminNetworkPolicy,BaselineAdminNetworkPolicy --organization=kubernetes --project=kube-network-policies --url=https://github.com/kubernetes-sigs/kube-network-policies --version=0.1.1 [email protected] --additional-info=https://github.com/kubernetes-sigs/kube-network-policies
cd -

- name: Upload Junit Reports
if: always()
uses: actions/upload-artifact@v2
with:
name: kind-junit-${{ env.JOB_NAME }}-${{ github.run_id }}
path: './_artifacts/*.xml'

- name: Export logs
if: always()
run: |
/usr/local/bin/kind export logs --name ${KIND_CLUSTER_NAME} --loglevel=debug ./_artifacts/logs

- name: Upload logs
if: always()
uses: actions/upload-artifact@v2
with:
name: kind-logs-${{ env.JOB_NAME }}-${{ github.run_id }}
path: ./_artifacts/logs
50 changes: 45 additions & 5 deletions cmd/main.go
Original file line number Diff line number Diff line change
Expand Up @@ -13,9 +13,13 @@ import (
"github.com/prometheus/client_golang/prometheus/promhttp"
"sigs.k8s.io/knftables"
"sigs.k8s.io/kube-network-policies/pkg/networkpolicy"
npaclient "sigs.k8s.io/network-policy-api/pkg/client/clientset/versioned"
npainformers "sigs.k8s.io/network-policy-api/pkg/client/informers/externalversions"
"sigs.k8s.io/network-policy-api/pkg/client/informers/externalversions/apis/v1alpha1"

utilruntime "k8s.io/apimachinery/pkg/util/runtime"
"k8s.io/client-go/informers"
v1 "k8s.io/client-go/informers/core/v1"
"k8s.io/client-go/kubernetes"
"k8s.io/client-go/rest"
"k8s.io/klog/v2"
Expand All @@ -24,13 +28,17 @@ import (
)

var (
failOpen bool
queueID int
metricsBindAddress string
failOpen bool
adminNetworkPolicy bool // AdminNetworkPolicy is alpha so keep it feature gated behind a flag
baselineAdminNetworkPolicy bool // BaselineAdminNetworkPolicy is alpha so keep it feature gated behind a flag
queueID int
metricsBindAddress string
)

func init() {
flag.BoolVar(&failOpen, "fail-open", false, "If set, don't drop packets if the controller is not running")
flag.BoolVar(&adminNetworkPolicy, "admin-network-policy", false, "If set, enable Admin Network Policy API")
flag.BoolVar(&baselineAdminNetworkPolicy, "baseline-admin-network-policy", false, "If set, enable Baseline Admin Network Policy API")
flag.IntVar(&queueID, "nfqueue-id", 100, "Number of the nfqueue used")
flag.StringVar(&metricsBindAddress, "metrics-bind-address", ":9080", "The IP address and port for the metrics server to serve on")

Expand All @@ -45,6 +53,8 @@ func main() {
klog.InitFlags(nil)
flag.Parse()

klog.Infof("flags: %v", flag.Args())

nft, err := knftables.New(knftables.InetFamily, "kube-network-policies")
if err != nil {
klog.Fatalf("Error initializing nftables: %v", err)
Expand All @@ -55,8 +65,10 @@ func main() {
}

cfg := networkpolicy.Config{
FailOpen: failOpen,
QueueID: queueID,
AdminNetworkPolicy: adminNetworkPolicy,
BaselineAdminNetworkPolicy: baselineAdminNetworkPolicy,
FailOpen: failOpen,
QueueID: queueID,
}
// creates the in-cluster config
config, err := rest.InClusterConfig()
Expand All @@ -83,6 +95,27 @@ func main() {

informersFactory := informers.NewSharedInformerFactory(clientset, 0)

var npaClient *npaclient.Clientset
var npaInformerFactory npainformers.SharedInformerFactory
var nodeInformer v1.NodeInformer
if adminNetworkPolicy || baselineAdminNetworkPolicy {
nodeInformer = informersFactory.Core().V1().Nodes()
npaClient, err = npaclient.NewForConfig(config)
if err != nil {
klog.Fatalf("Failed to create Network client: %v", err)
}
npaInformerFactory = npainformers.NewSharedInformerFactory(npaClient, 0)
}

var anpInformer v1alpha1.AdminNetworkPolicyInformer
if adminNetworkPolicy {
anpInformer = npaInformerFactory.Policy().V1alpha1().AdminNetworkPolicies()
}
var banpInformer v1alpha1.BaselineAdminNetworkPolicyInformer
if baselineAdminNetworkPolicy {
banpInformer = npaInformerFactory.Policy().V1alpha1().BaselineAdminNetworkPolicies()
}

http.Handle("/metrics", promhttp.Handler())
go func() {
err := http.ListenAndServe(metricsBindAddress, nil)
Expand All @@ -95,6 +128,10 @@ func main() {
informersFactory.Networking().V1().NetworkPolicies(),
informersFactory.Core().V1().Namespaces(),
informersFactory.Core().V1().Pods(),
nodeInformer,
npaClient,
anpInformer,
banpInformer,
cfg,
)
go func() {
Expand All @@ -103,6 +140,9 @@ func main() {
}()

informersFactory.Start(ctx.Done())
if adminNetworkPolicy || baselineAdminNetworkPolicy {
npaInformerFactory.Start(ctx.Done())
}

select {
case <-signalCh:
Expand Down
1 change: 1 addition & 0 deletions go.mod
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,7 @@ require (
k8s.io/klog/v2 v2.120.1
k8s.io/utils v0.0.0-20240310230437-4693a0247e57
sigs.k8s.io/knftables v0.0.16
sigs.k8s.io/network-policy-api v0.1.5
)

require (
Expand Down
2 changes: 2 additions & 0 deletions go.sum
Original file line number Diff line number Diff line change
Expand Up @@ -195,6 +195,8 @@ sigs.k8s.io/json v0.0.0-20221116044647-bc3834ca7abd h1:EDPBXCAspyGV4jQlpZSudPeMm
sigs.k8s.io/json v0.0.0-20221116044647-bc3834ca7abd/go.mod h1:B8JuhiUyNFVKdsE8h686QcCxMaH6HrOAZj4vswFpcB0=
sigs.k8s.io/knftables v0.0.16 h1:ZpTfNsjnidgoXdxxzcZLdSctqkpSO3QB3jo3zQ4PXqM=
sigs.k8s.io/knftables v0.0.16/go.mod h1:f/5ZLKYEUPUhVjUCg6l80ACdL7CIIyeL0DxfgojGRTk=
sigs.k8s.io/network-policy-api v0.1.5 h1:xyS7VAaM9EfyB428oFk7WjWaCK6B129i+ILUF4C8l6E=
sigs.k8s.io/network-policy-api v0.1.5/go.mod h1:D7Nkr43VLNd7iYryemnj8qf0N/WjBzTZDxYA+g4u1/Y=
sigs.k8s.io/structured-merge-diff/v4 v4.4.1 h1:150L+0vs/8DA78h1u02ooW1/fFq/Lwr+sGiqlzvrtq4=
sigs.k8s.io/structured-merge-diff/v4 v4.4.1/go.mod h1:N8hJocpFajUSSeSJ9bOZ77VzejKZaXsTtZo4/u7Io08=
sigs.k8s.io/yaml v1.4.0 h1:Mk1wCc2gy/F0THH0TAp1QYyJNzRm2KCLy3o5ASXVI5E=
Expand Down
100 changes: 100 additions & 0 deletions install-anp.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,100 @@
---
kind: ClusterRole
apiVersion: rbac.authorization.k8s.io/v1
metadata:
name: kube-network-policies
rules:
- apiGroups:
- ""
resources:
- pods
- namespaces
- nodes
verbs:
- list
- watch
- apiGroups:
- "networking.k8s.io"
resources:
- networkpolicies
verbs:
- list
- watch
- apiGroups:
- "policy.networking.k8s.io"
resources:
- adminnetworkpolicies
- baselineadminnetworkpolicies
verbs:
- list
- watch
---
kind: ClusterRoleBinding
apiVersion: rbac.authorization.k8s.io/v1
metadata:
name: kube-network-policies
roleRef:
apiGroup: rbac.authorization.k8s.io
kind: ClusterRole
name: kube-network-policies
subjects:
- kind: ServiceAccount
name: kube-network-policies
namespace: kube-system
---
apiVersion: v1
kind: ServiceAccount
metadata:
name: kube-network-policies
namespace: kube-system
---
apiVersion: apps/v1
kind: DaemonSet
metadata:
name: kube-network-policies
namespace: kube-system
labels:
tier: node
app: kube-network-policies
k8s-app: kube-network-policies
spec:
selector:
matchLabels:
app: kube-network-policies
template:
metadata:
labels:
tier: node
app: kube-network-policies
k8s-app: kube-network-policies
spec:
hostNetwork: true
dnsPolicy: ClusterFirst
nodeSelector:
kubernetes.io/os: linux
tolerations:
- operator: Exists
effect: NoSchedule
serviceAccountName: kube-network-policies
containers:
- name: kube-network-policies
image: registry.k8s.io/networking/kube-network-policies:v0.1.0
command: ["/bin/netpol"]
args: ["-v=2", "-admin-network-policy=true", "-baseline-admin-network-policy=true"]
volumeMounts:
- name: lib-modules
mountPath: /lib/modules
readOnly: true
resources:
requests:
cpu: "100m"
memory: "50Mi"
securityContext:
privileged: true
capabilities:
add: ["NET_ADMIN"]
volumes:
- name: lib-modules
hostPath:
path: /lib/modules
---
Loading
Loading