This repo contains the source code of Kaloom's Kubernetes Podagent
A controller that runs on each Kubernetes’ node
To dynamically add/delete a network interface(s) into a running Pod without restarting it (e.g. vrouters, VNF usecases)
Watches Pods’ network attachment annotations using Kubernetes’ apiserver and react to changes to it:
- Finds a Pod’s network namespace from the container runtime engine
- Invokes the cni-plugin to add/del network interface dynamically into the Pod’s network namespace
Let assume we started a Pod with no network attachments (i.e. just the default network on eth0), once it's RUNNING, we added a green network attachment annotation
Let assume we have a RUNNING Pod with 2 network attachements red and green, while it's RUNNING, we deleted off the network attachments annotation list the red network attachment
./build.sh
if you're adding a new dependency package to the project you need to use gradle, otherwise running the ./build.sh script should do
gradle required java to be installed, its used to generate the dependencies (using gogradle plugin), update the gogradle.lock, build the project and update the go vendor directory if needed
-
update build.gradle
-
generate a new
gogradle.lockfile:./gradlew lock -
build the project (the
buildgradle task would trigger an update to thevendordirectory using thegogradle.lockif needed):./gradlew buildor simply
./gradlew -
submit a merge request
- updating only the vendor directory can be done with:
./gradlew vendor - to get a list of available
gradletasks:./gradlew tasks
How to deploy the podagent
kactus Kaloom's cni-plugin which knows how to works with dynamic network attachments
-
setup kactus as the system cni-plugin in your Kubernetes cluster by having its configuration the first in lexical order
-
create a Kubernetes service account, cluster role and cluster role binding for the podagent:
$
kubectl apply -f manifests/podagent-serviceaccount-and-rbac.yaml
- deploy the podagent as a daemon set:
$
kubectl apply -f manifests/podagent-ds.yamlfor docker $kubectl apply -f manifests/podagent-cs.yamlfor crio
Currently, to deploy the podagent as DaemonSet
-
selinux should not be in enforced mode (permissive mode is okay):
#
setenforce permissive#
sed -i 's/^SELINUX=.*/SELINUX=permissive/g' /etc/selinux/config -
it's run as a privileged container and requires access to Docker's
/var/run/docker.sockunix socket (Docker is the only Container Runtime Engine supported right now)
-
setup kactus as the master cni-plugin in your Kubernetes cluster
-
build the podagent rpm package
$
./scripts/build-rpm.sh
- copy and install the produced package in the step above to all the nodes in Kubernetes cluster:
$
sudo rpm -ivh podagent-*.rpm
$
sudo systemctl start podagent
$
sudo systemctl enable podagent
- create a Kubernetes service account, cluster role and cluster role binding for the podagent:
$
kubectl apply -f manifests/podagent-serviceaccount-and-rbac.yaml
- create the
podagent-kubeconfig.yamlfile:
$
./scripts/create-kubeconfig.sh
- copy the produced
/tmp/kubeconfig/podagent-kubeconfig.yamlto each node in Kubernetes cluster under/opt/kaloom/etc/
$ sudo cp /tmp/kubeconfig/podagent-kubeconfig.yaml /opt/kaloom/etc/
We will deploy a simple application (Linux alpine) with only the default network attachment (i.e. eth0 setup by the master cni-plugin).
Than add a network attachment called data which uses a bridge cni-plugin
Let first provision the data network attachment:
$
kubectl apply -f examples/data-net.yaml
Than delpoy alpine with 2 replicas:
$
kubectl run hello-multi-net --image=alpine --replicas=2 -- top
Add the data network attachment to the first pod:
$
./scripts/add-network-annotation.sh $(kubectl get pod -l run=hello-multi-net -o name | cut -d/ -f2 | head -1) data
Verify that a new network interface called net8d777f385d3d is present in the pod
$
kubectl exec -t $(kubectl get pod -l run=hello-multi-net -o name | cut -d/ -f2 | head -1) -- ip a
Verify that the pod didn't get re-started
$
kubectl get pod -l run=hello-multi-net -o wide | grep $(kubectl get pod -l run=hello-multi-net -o name | cut -d/ -f2 | head -1)
Delete the data network attachment off the first pod:
$
./scripts/del-network-annotation.sh $(kubectl get pod -l run=hello-multi-net -o name | cut -d/ -f2 | head -1) data
Verify that net8d777f385d3d is gone from the pod:
$
kubectl exec -t $(kubectl get pod -l run=hello-multi-net -o name | cut -d/ -f2 | head -1) -- ip a
Verify that the pod didn't get re-started
$
kubectl get pod -l run=hello-multi-net -o wide | grep $(kubectl get pod -l run=hello-multi-net -o name | cut -d/ -f2 | head -1)
Repeat the same thing with the second pod:
$
./scripts/add-network-annotation.sh $(kubectl get pod -l run=hello-multi-net -o name | cut -d/ -f2 | tail -1) data
- for the above example, make sure that the
data-bris present on all the nodes
$
brctl show data-br


