Compare commits

...

415 Commits

Author SHA1 Message Date
Moshe Levi
f530d3eb84 fix kubeletSocket scope (#941)
The kubeletSocket in the function is scoping the const kubeletSocket
which causing resource api to fail with

"stat /var/lib/kubelet/pod-resources/.sock: no such file or directory"

Signed-off-by: Moshe Levi <moshele@nvidia.com>

Signed-off-by: Moshe Levi <moshele@nvidia.com>
2022-10-26 22:25:38 +09:00
Doug Smith
e43ed9274e Merge pull request #939 from s1061123/fix/server
Fix multus-daemon in case of user given config
2022-10-24 16:03:48 -04:00
yulng
f52aa691d6 Add "EOF" to the Cat command, otherwise the operation will fail (#932) (#934)
Add EOF to the Cat command, otherwise the operation will fail
2022-10-25 00:57:09 +09:00
Tomofumi Hayashi
46daed0654 Fix multus-daemon in case of user given config
This fix the issue #931 to refining server startup code including
file copy and channel processing, with simplification.
2022-10-25 00:46:40 +09:00
yulng
e9bb5e5f48 Add "EOF" to the Cat command, otherwise the operation will fail (#932)
Add EOF to the Cat command, otherwise the operation will fail
2022-10-23 14:58:08 +09:00
Doug Smith
fa8a6e6880 Merge pull request #925 from s1061123/dev/rc-api
Support IPs, MAC and cni-args in delegate API
2022-10-14 11:34:12 -04:00
Tomofumi Hayashi
6f90a0f075 Support IPs, MAC and cni-args in delegate API 2022-10-15 00:12:17 +09:00
Doug Smith
efa8c62ec4 Merge pull request #930 from s1061123/fix/mod-ver
Fix kubelet version in go.mod
2022-10-14 11:07:58 -04:00
Tomofumi Hayashi
7c619d64a6 Fix kubelet version in go.mod
fix #928
2022-10-14 23:32:26 +09:00
Eoghan Russell
1aac2431b8 Fix broken link in README (#919) 2022-09-26 23:26:25 +09:00
Doug Smith
f372831536 Merge pull request #915 from s1061123/fix/delegate-api
Fix deleate API to load conflist
2022-09-20 13:19:58 -04:00
Tomofumi Hayashi
3e97437e31 Fix deleate API to load conflist 2022-09-21 01:56:53 +09:00
Miguel Duarte Barroso
b1aba95892 Idiomatic config unit tests (#908)
* gomega, unit tests: use `HaveLen` matcher

The `HaveLen` matcher provides a better error msg when the test fails,
resulting in easier debugging.

Signed-off-by: Miguel Duarte Barroso <mdbarroso@redhat.com>

* gomega, unit tests: use `BeEmpty` matcher

The `BeEmpty` matcher is more idiomatic, and results in better error
msgs when the test fails.

Signed-off-by: Miguel Duarte Barroso <mdbarroso@redhat.com>

* gomega, unit tests: use `BeTrue` and `BeFalse` matchers

These matchers are more idiomatic.

Signed-off-by: Miguel Duarte Barroso <mdbarroso@redhat.com>

Signed-off-by: Miguel Duarte Barroso <mdbarroso@redhat.com>
2022-09-19 10:22:08 -04:00
Doug Smith
371123659b Merge pull request #906 from TimFroidcoeur/fix_multiple_default_gw
fix multiple default gw
2022-09-01 16:18:38 -04:00
Tim Froidcoeur
8da20f38ea fix multiple default gw
when the configuration specifies both an IPv4 and IPv6 default route,
the IsFilterV4Gateway and IsFilterV6Gateway flags should both be false,
to allow the gateway configuration.
The logic in CheckGatewayConfig would do the inverse, setting both to
true in case of both IPv4 and IPv6 gateway.

Fixes: d52f2b6a ("Update libcni cache when default-route net selection
is used")
Signed-off-by: Tim Froidcoeur <tim.froidcoeur@tessares.net>
2022-09-01 16:50:19 +02:00
Doug Smith
d93a3bb736 Merge pull request #899 from jklare/jk_readme_thick_plugin
rephrase readme section describing thin vs thick plugin
2022-08-26 15:11:52 -04:00
Doug Smith
e882d51b3c Merge pull request #903 from s1061123/dev/fedora-image
[WIP]Change container image to python:slim from centos
2022-08-26 14:35:23 -04:00
Tomofumi Hayashi
db7cc6bc80 Change container image to fedora from centos
This change introduce fedora container for multus image.
2022-08-27 02:57:58 +09:00
Doug Smith
33c0d1bd86 Merge pull request #900 from s1061123/fix/image-tag
Fix container tags for thick plugin
2022-08-25 11:29:17 -04:00
Tomofumi Hayashi
12c6c91586 Fix container tags for thick plugin 2022-08-25 23:07:32 +09:00
Jan Klare
2f12b5ce99 rephrase readme section describing thin vs thick plugin
Signed-off-by: Jan Klare <jan.klare@bisdn.de>
2022-08-24 14:45:26 +02:00
Doug Smith
0c515497d7 recommends thick plugin in quickstart (#894) 2022-08-24 20:23:33 +09:00
Doug Smith
68a9593f84 Merge pull request #897 from s1061123/fix/add-disclaimers
Update deployment yaml
2022-08-22 13:35:21 -04:00
Tomofumi Hayashi
95c4d0c1c5 Update deployment yaml
This change adds note section in deployment yaml to explicitly
mention the scope of this yaml.
2022-08-23 01:19:24 +09:00
Doug Smith
5498080119 Merge pull request #893 from k8snetworkplumbingwg/feature/multus-4.0
Feature/multus 4.0
2022-08-18 16:48:02 -04:00
Tomofumi Hayashi
3d9cec4ec9 Merge remote-tracking branch 'origin/master' into feature/multus-4.0 2022-08-19 00:07:30 +09:00
Tomofumi Hayashi
505ab4567c Add delegate API in multus-daemon (#890)
This changes introduce delegate API function in multus-daemon.
This API will be consumed from other programs for hot-plug
interface into running pod. This change also cleanups server
code to split into client code and server code to easy to import
from other golang code.
2022-08-10 00:45:23 +09:00
Doug Smith
8dee74d7b9 Merge pull request #870 from s1061123/dev/doc-modified
Add 4.0 document
2022-08-01 11:19:02 -04:00
Doug Smith
fba6d66720 Merge pull request #886 from s1061123/update-libcni
Bump libcni to fetch the bugfix
2022-07-29 11:06:14 -04:00
Tomofumi Hayashi
7f7bb354c5 Bump libcni to fetch the bugfix
This change introduces https://github.com/containernetworking/cni/pull/904
to fix the issue.
2022-07-29 20:31:57 +09:00
Doug Smith
f4c0adf54c Merge pull request #881 from chrisplo/detect-python3
Detect python3
2022-07-22 09:48:40 -04:00
Chris Plock
ac6757b9cc Detect python3
fixes https://github.com/k8snetworkplumbingwg/multus-cni/issues/880
2022-07-15 15:13:27 -07:00
Doug Smith
70c970cd6e Merge pull request #878 from tomkukral/print-kubeconfig
write output file for generated kubeconfig
2022-07-12 08:39:17 -04:00
Doug Smith
3deb079546 Merge pull request #876 from s1061123/dev/update-golang
Update golang version to 1.18.x
2022-07-11 16:11:44 -04:00
Doug Smith
9cb6fb57bf Merge pull request #877 from s1061123/dev/refine-build
Refine build-go.sh and update 'version' output
2022-07-11 16:10:31 -04:00
Tomáš Kukrál
95adff55b0 write output file for generated kubeconfig
This change will make debugging easier in cases when non-default
location is used and user forgot to mount new directory.
2022-07-08 14:02:51 +02:00
Tomofumi Hayashi
99dd6678d5 Refine build-go.sh and update 'version' output 2022-07-07 01:44:13 +09:00
Tomofumi Hayashi
6f5fdf64c7 Update golang version to 1.18.x 2022-07-07 00:31:25 +09:00
Tomofumi Hayashi
9d67fbd520 Add 4.0 document 2022-06-27 22:12:23 +09:00
Doug Smith
ca8c9c5791 Merge pull request #864 from s1061123/default-route-pointer
Use *[]net.IP for 'default-route' network selection element.
2022-06-21 15:47:09 -04:00
Doug Smith
18a660ebc7 Merge pull request #867 from mmirecki/downwardapi
Fix missing device-info in networks-status annotation for chained plugins
2022-06-21 14:38:29 -04:00
mmirecki
358f09bfe2 Merge remote-tracking branch 'upstream/master' into downwardapi 2022-06-21 20:14:34 +02:00
Tomofumi Hayashi
107624ccff Use *[]net.IP for 'default-route' network selection element. 2022-06-22 02:12:08 +09:00
Doug Smith
13eb83a01c Merge pull request #868 from s1061123/fix/revive-err
Fix revive error
2022-06-21 11:26:44 -04:00
Tomofumi Hayashi
dc57189cf9 Fix revive error 2022-06-21 23:39:18 +09:00
Doug Smith
3cda380ad1 Merge pull request #865 from s1061123/fix/m40-revive-err
Fix revive's error
2022-06-21 10:24:15 -04:00
mmirecki
2bf8dae9a8 Fix missing device-info in networks-status annotation for chained plugins 2022-06-21 14:47:04 +02:00
Tomofumi Hayashi
2993671acd Fix revive's error 2022-06-21 00:58:24 +09:00
Tomofumi Hayashi
a735987501 Merge remote-tracking branch 'origin/master' into feature/multus-4.0 2022-06-14 18:04:33 +09:00
Doug Smith
8bbb594dad Merge pull request #862 from s1061123/fix/cmddel-nostatus-update
Skip status update in CmdDel if getPod is failed
2022-06-13 13:22:17 -04:00
Tomofumi Hayashi
fcc8e44f14 Skip status update in CmdDel if getPod is failed
This change skips to update pod's network-status annotation
when getPod is failed at the beginning of CmdDel. If getPod is
failed, K8s api gets stucked in many cases, hence pod update
might be failed in most cases.
2022-06-14 02:14:43 +09:00
Doug Smith
3572647e5b Merge pull request #860 from s1061123/dev/add-ut
Add unit-test to increase test coverage
2022-06-10 10:39:20 -04:00
Doug Smith
2eb5d2f653 Merge pull request #857 from s1061123/dev/metrics
Add metrics support
2022-06-10 10:38:34 -04:00
疯狂的小企鹅
be56f8dc30 Fixed that in.Delegates may remain in the CmdDel (#859)
Co-authored-by: jinda.ljd <jinda.ljd@alibaba-inc.com>
2022-06-08 21:03:14 +09:00
Tomofumi Hayashi
580b72a5b2 Add unit-test to increase test coverage 2022-06-08 13:49:17 +09:00
Tomofumi Hayashi
a77d3cbedb Merge remote-tracking branch 'origin/master' into feature/multus-4.0 2022-06-06 23:37:59 +09:00
Miguel Duarte Barroso
d2a4b832f2 config, logging: correct the logging parameters (#856)
The logging parameters were listing using uppercase, which is wrong. 

According to multus configuration, they should be in camelCase - [0] and [1].

[0] - 779170a48e/pkg/types/types.go (L45)
[1] - 779170a48e/pkg/types/types.go (L46)
2022-06-06 22:33:05 +09:00
Tomofumi Hayashi
9f3e6b0da0 Add metrics support
This change introduces prometheus metric exporter support for
multus-daemon, thick plugin.
2022-06-04 00:45:37 +09:00
Tomofumi Hayashi
df903a757e Merge remote-tracking branch 'origin/master' into feature/multus-4.0 2022-06-02 18:04:49 +09:00
Nikhil Simha
779170a48e Added hyperlink for logging (#851)
* Added hyperlink for logging

This may make it easier for users to find info on logging parameters since there isn't a dedicated docs page for it.

* Fixed hyperlink

Linked to proper section
2022-05-26 09:33:22 -04:00
Doug Smith
5ee0274b5b Bumps net-attach-def client library to v1.1.1 (#846)
This accounts for CNI v1.0 formatted IP address information (no longer requires version field)
2022-05-12 22:58:23 +09:00
Doug Smith
42a2642852 Merge pull request #844 from danielmellado/fix-images-docs
Fix wrong location for daemonset in readme
2022-05-10 11:42:14 -04:00
Daniel Mellado
b5323e4144 Fix wrong location for daemonset in readme
This PR fixes an outdated reference in the docs where
multus-daemonset.yml was expected to be found under the images folder.
2022-05-10 17:06:47 +02:00
Tomofumi Hayashi
485642c18f Merge remote-tracking branch 'origin/master' into feature/multus-4.0 2022-05-07 00:36:30 +09:00
Doug Smith
dcbc215b93 The cachefile name should be the delegate configuration name (#841)
It was previously using the net-attach-def name, which doesn't align with the cache file. Causing default-route selection to not succeed.
2022-05-07 00:06:37 +09:00
Doug Smith
5ede36fb43 Merge pull request #839 from s1061123/dev/refine-k8s-lib
Refine Kubernetes APIs
2022-05-04 13:27:00 -04:00
Tomofumi Hayashi
16bd359bc0 Update k8s api to v1.22.8 2022-04-28 22:55:55 +09:00
Tomofumi Hayashi
c6fa047212 Remove k8s.io/kubernetes dependency from multus
Fix #675
2022-04-26 18:22:36 +09:00
Tomofumi Hayashi
59415ad0d6 Merge remote-tracking branch 'origin/master' into feature/multus-4.0 2022-04-26 16:46:16 +09:00
Dan Williams
ecc1482d50 types: fix usage of strings.Split() for parsing CNI_ARGS (#836)
* types: fix usage of strings.Split() for parsing CNI_ARGS

strings.Split() returns a slice, in this case with two elements of
the key and value. As such we shouldn't range over the slice when
the code is expecting a 2-element slice of key/value.

Otherwise we get errors for valid CNI_ARGS like:

2022-04-22T11:53:54Z [error] CreateCNIRuntimeConf: CNI_ARGS K8S_POD_NAMESPACE=openshift-etcd K8S_POD_NAMESPACE 17 is not recognized as CNI arg, skipped
2022-04-22T11:53:54Z [error] CreateCNIRuntimeConf: CNI_ARGS K8S_POD_NAMESPACE=openshift-etcd openshift-etcd 14 is not recognized as CNI arg, skipped

Fixes: d7d2a99ab5b8 ("Replace setenv with runtimeConfig set")

Signed-off-by: Dan Williams <dcbw@redhat.com>

* types/conf: fix handling of CNI_ARGS additions to rt.Args

We want to set the CNI_ARGS value in rt.Args if the existing value
is empty, not if the key doesn't exist yet. Since the rt.Args array
is pre-created with the K8S args keys, empty values of those keys
couldn't be overwritten with the previous scheme that just checked
if the key existed.

If the CNI_ARGS key wasn't found in rt.Args then add it; previously
a typo ("isExists != false") prevented that with inverted logic.

Signed-off-by: Dan Williams <dcbw@redhat.com>
2022-04-26 00:13:09 +09:00
Doug Smith
b34486308c Merge pull request #834 from s1061123/fix/sriov
Fix sr-iov support
2022-04-25 09:51:23 -04:00
Nikhil Simha
dd15abc9b1 Added a static pod e2e test. (#835)
* Added bash e2e test for static pods. Checks for net1 interface on pod.

Signed-off-by: nicklesimba <simha.nikhil@gmail.com>

* Enable static pod test in CI

Signed-off-by: nicklesimba <simha.nikhil@gmail.com>

* Addressed review comments

Signed-off-by: nicklesimba <simha.nikhil@gmail.com>
2022-04-22 00:35:39 +09:00
Tomofumi Hayashi
10fcc49f4d Merge remote-tracking branch 'origin/master' into feature/multus-4.0 2022-04-19 00:18:38 +09:00
jinglina
706de7c2c6 delete type conversion (#833) 2022-04-18 22:34:40 +09:00
Doug Smith
ea0df58e7c Merge pull request #831 from s1061123/update-golang
Update golang version to 1.17
2022-04-18 09:33:43 -04:00
Tomofumi Hayashi
4670f1f240 Fix sr-iov support
Fix thick plugin daemonset to add volume mapping required for
sr-iov and fix code to update network status.
In addition, fix checkpoint structures to support K8s without
kubelet pod resources API.

fix #665 and #778
2022-04-18 21:28:13 +09:00
Tomofumi Hayashi
4ada0c3ae8 Update golang version to 1.17 2022-04-14 23:30:30 +09:00
Doug Smith
13e4b3a1c4 Merge pull request #828 from s1061123/dev/chroot
Add chroot option in multus-daemon
2022-04-13 15:38:56 -04:00
Tomofumi Hayashi
282b40a503 Add chroot option in multus-daemon
This change introduces 'chroot' option in multus-daemon to execute
delegate CNI with host filesystem context.
2022-04-13 19:36:53 +09:00
Tomofumi Hayashi
bf4d6c716c Merge remote-tracking branch 'origin/master' into feature/multus-4.0 2022-04-12 21:42:19 +09:00
Tomofumi Hayashi
77ed17b392 Fix letter 2022-04-12 15:06:44 +09:00
Cyclinder
6bcb6bf403 add some flags for customize the log settings (#817) 2022-04-12 00:22:48 +09:00
Doug Smith
588ee8f192 Fixes log message on CNI Check (#825) 2022-04-11 20:35:47 +09:00
Cyclinder
ce533f01cc update e2e tools version for kind and cni-plugins (#830) 2022-04-11 14:08:22 +09:00
Tomofumi Hayashi
579d83f359 Merge remote-tracking branch 'origin' into feature/multus-4.0 2022-04-06 00:42:23 +09:00
Tomofumi Hayashi
51c39205a8 Remove error handling for getPod to force to proceed cmdDel.
In cmdDel, CNI Spec mentioned that plugin should proceed cmdDel
without any error, hence the change removes error returning
at cmdDel.

fix #822
2022-04-06 00:34:53 +09:00
Tomofumi Hayashi
4180f88442 Refine multus-daemon config 2022-04-06 00:34:53 +09:00
Tomofumi Hayashi
d1046fa1c9 Fix install binary for thick plugin 2022-04-06 00:34:53 +09:00
Tomofumi Hayashi
0a144e597a Fix thick plugin to run kind-e2e test 2022-04-06 00:34:53 +09:00
Tomofumi Hayashi
2f5af62a92 Refine unit test in pkg/multus
Some of tests are duplicated hence deduped. In addition, sort
these unit tests based on cniVersion.
2022-04-06 00:34:53 +09:00
Cyclinder
80693bde62 fix the usage of flag "overrideNetworkName" (#805) 2022-04-06 00:34:53 +09:00
Doug Smith
3abb21a80c crio: mount /run rslave (#802)
to prevent "unknown FS magic on "/var/run/netns/*": 1021994" errors

Signed-off-by: Peter Hunt <pehunt@redhat.com>

Co-authored-by: Peter Hunt <pehunt@redhat.com>
2022-04-06 00:34:53 +09:00
Doug Smith
e7aaf8f5d5 only warn when netns can't be opened (#803) 2022-04-06 00:34:53 +09:00
Tomofumi Hayashi
93ec0c121e Support CNI 1.0.0
Fix #792
2022-04-06 00:34:53 +09:00
Tomofumi Hayashi
ecc98be9c6 Split multus unit tests into several files
To simplify multus unit tests, split it into several files,
based on testing CNI version.
2022-04-06 00:34:53 +09:00
Tomofumi Hayashi
b8d4d46462 check version incompatibility (#762) (#798)
* multus: entrypoint: disallow incompatible cni versions

When top level CNI version is 0.4.0 or more, nested CNI version
can't be less than 0.4.0 since these are incompatible. This
closes issue #737.

Signed-off-by: Balazs Nemeth <bnemeth@redhat.com>

* multus: thick: disallow incompatible cni versions

Similarly to disallowing incompatible versions in entrypoint.sh,
add the same logic in go for the thick plugin.

Signed-off-by: Balazs Nemeth <bnemeth@redhat.com>

* multus: add unit test for incompatible cni versions

Signed-off-by: Balazs Nemeth <bnemeth@redhat.com>

Co-authored-by: Balazs Nemeth <bnemeth@redhat.com>
2022-04-06 00:34:53 +09:00
Tomofumi Hayashi
869b94ffaa Simplify e2e scripts (#795) 2022-04-06 00:34:53 +09:00
Tomofumi Hayashi
d4a30c383d Make binary file and directory name consistent
This change make binary file and directory name consistent.
In addition, change the package name cni to server because cni
is a bit umbiguous for cni plugin's repository.
2022-04-06 00:34:53 +09:00
Tomofumi Hayashi
d4a3ea4fd0 Replace setenv with runtimeConfig set (#785)
setenv refers environment variables, which is unique in process,
not unique to go routine. Hence it may causes some issue in multi
threaded case, hence it is replaced with libcni's runtimeConfig
value set to set these variables at libcni side, after process
fork.
2022-04-06 00:34:53 +09:00
Miguel Duarte Barroso
fb31217e2c thick-plugin: refactor multus
Multus is refactored as a thick plugin, featuring 2 main components:
  - a server listening to a unix domain socket, running in a pod
  - a shim, a binary on the host that will send JSON requests built from
    its environment / stdin values to the aforementioned server.

The pod where the multus daemon is running must share the host's PID
namespace.

Signed-off-by: Miguel Duarte Barroso <mdbarroso@redhat.com>

react to maintainers review

Signed-off-by: Miguel Duarte Barroso <mdbarroso@redhat.com>

thick, deployment: update the daemonset spec

Signed-off-by: Miguel Duarte Barroso <mdbarroso@redhat.com>

thick, config: validate the cni config passed by the runtime

Without this patch, we're blindly trusting anything sent by the server.
This way, we assure the requests arriving at the multus controller are
valid before hand.

Signed-off-by: Miguel Duarte Barroso <mdbarroso@redhat.com>

thick: model client / server config

Also add a new command line parameter on the multus controller, pointing
it to the server configuration.

Signed-off-by: Miguel Duarte Barroso <mdbarroso@redhat.com>

SQUASH candidate, thick, config: cleanup the configuration

Signed-off-by: Miguel Duarte Barroso <mdbarroso@redhat.com>

multus: use args.args instead of an env variable

CNI is already filling the args structure; we should consume that
rather than rely on the environment variables.

Signed-off-by: Miguel Duarte Barroso <mdbarroso@redhat.com>

unit tests: remove weird tests that check an impossible scenario

Signed-off-by: Miguel Duarte Barroso <mdbarroso@redhat.com>

docs, thick: document the thick plugin variant

Signed-off-by: Miguel Duarte Barroso <mdbarroso@redhat.com>

thick, server, multus: re-use common types

Signed-off-by: Miguel Duarte Barroso <mdbarroso@redhat.com>
2022-04-06 00:34:52 +09:00
Doug Smith
0453b52097 Merge pull request #823 from s1061123/fix/cmddel
Remove error handling for getPod to force to proceed cmdDel.
2022-04-04 15:41:36 -04:00
Tomofumi Hayashi
2d53334211 Remove error handling for getPod to force to proceed cmdDel.
In cmdDel, CNI Spec mentioned that plugin should proceed cmdDel
without any error, hence the change removes error returning
at cmdDel.

fix #822
2022-04-05 02:29:41 +09:00
Cyclinder
45428a53ce fix the usage of flag "overrideNetworkName" (#805) 2022-03-04 16:01:21 +09:00
Doug Smith
6c12dc8c4f crio: mount /run rslave (#802)
to prevent "unknown FS magic on "/var/run/netns/*": 1021994" errors

Signed-off-by: Peter Hunt <pehunt@redhat.com>

Co-authored-by: Peter Hunt <pehunt@redhat.com>
2022-03-04 02:02:37 +09:00
Doug Smith
7559625a38 only warn when netns can't be opened (#803) 2022-03-04 02:02:24 +09:00
Balazs Nemeth
450e1d3414 check version incompatibility (#762)
* multus: entrypoint: disallow incompatible cni versions

When top level CNI version is 0.4.0 or more, nested CNI version
can't be less than 0.4.0 since these are incompatible. This
closes issue #737.

Signed-off-by: Balazs Nemeth <bnemeth@redhat.com>

* multus: thick: disallow incompatible cni versions

Similarly to disallowing incompatible versions in entrypoint.sh,
add the same logic in go for the thick plugin.

Signed-off-by: Balazs Nemeth <bnemeth@redhat.com>

* multus: add unit test for incompatible cni versions

Signed-off-by: Balazs Nemeth <bnemeth@redhat.com>
2022-02-28 21:50:39 +09:00
Tomofumi Hayashi
6dd45f38f9 Replace setenv with runtimeConfig set (#785)
setenv refers environment variables, which is unique in process,
not unique to go routine. Hence it may causes some issue in multi
threaded case, hence it is replaced with libcni's runtimeConfig
value set to set these variables at libcni side, after process
fork.
2022-02-21 23:55:33 +09:00
Doug Smith
843147aca0 Merge pull request #775 from s1061123/fix/773
Suppress uid mismatch error/warning in case of static pod
2022-02-07 12:44:04 -05:00
Miguel Duarte Barroso
191b8cb0ec e2e tests: always pull new multus images (#783)
Currently, the local workflow is far from optimal, since for every
change on the multus images the developers are required to redeploy
the kind cluster.

A more efficient workflow would be to build a local image, upload it to
the kind cluster, and finally re-deploy (delete & re-provision) the
daemonset, which would be running the new version.

For this flow to be possible, the multus container `imagePullPolicy`
must be set to `Always` - [0] - otherwise, the image is not updated.

[0] - https://kubernetes.io/docs/concepts/containers/images/#updating-images

Signed-off-by: Miguel Duarte Barroso <mdbarroso@redhat.com>
2022-01-26 21:37:03 +09:00
Miguel Duarte Barroso
9e79b79a89 multus, e2e tests: allow event sending to k8s API (#776)
Signed-off-by: Miguel Duarte Barroso <mdbarroso@redhat.com>
2022-01-20 23:50:16 +09:00
Tomofumi Hayashi
2e474f4c95 Suppress uid mismatch error/warning in case of static pod
In static pod case, kube api returns mirror pod UID hence
uid must be mismatched. This fix suppress error/warning message
in such case.

Fix #773
2022-01-15 23:17:53 +09:00
Doug Smith
27a86dafbc Merge pull request #779 from nicklesimba/patch-3
Update development.md
2022-01-14 11:10:03 -05:00
Nikhil Simha
daf96bffb3 Update development.md
Fixed doc for how to test
2022-01-14 10:59:29 -05:00
Doug Smith
7a53c910f2 Merge pull request #774 from nicklesimba/patch-2
Update quickstart.md
2022-01-11 13:59:45 -05:00
Nikhil Simha
38b1cd1cec Update quickstart.md
Specified location of 00-multus.conf for clarity
2022-01-11 13:57:48 -05:00
Sho Shimizu
6adb4dc4c4 Add toleration against NoExecute (#768) 2022-01-07 00:06:19 +09:00
Miguel Duarte Barroso
12df5bda72 run gofmt on the code (#772)
Signed-off-by: Miguel Duarte Barroso <mdbarroso@redhat.com>
2022-01-05 01:33:58 +09:00
Doug Smith
ed18a1f175 Merge pull request #764 from s1061123/fix/default-route
Update libcni cache when default-route net selection is used
2021-12-15 12:28:40 -05:00
Tomofumi Hayashi
d52f2b6a45 Update libcni cache when default-route net selection is used
To keep consistency between actual network and CNI result in cache,
update libcni cache when multus add/del default routes by
`default-route` network selection.
2021-12-15 01:57:51 +09:00
Doug Smith
4d9731bd3a Merge pull request #757 from maiqueb/fix-flaky-config-regen-test
flaky: fix delegate CNI conf updates unit test
2021-12-14 10:06:01 -05:00
Miguel Duarte Barroso
0da5449854 thick, config regen, test: fix test
The test was just checking that a READ/WRITE fsnotify.Event for
the multus configuration was being seen; this patch changes this
behavior, and assures that the delegateCNI configuration update results
in turn on the update of the multus configuration file.

Signed-off-by: Miguel Duarte Barroso <mdbarroso@redhat.com>
2021-12-14 10:10:15 +01:00
Miguel Duarte Barroso
653c4b481d thick, config regen, tests: use a unique path for multus config
Using a unique path for the config generation will lessen the
amount of events caught by the test that checks if the multus
configuration must be re-generated as a result a default cluster
configuration update.

Signed-off-by: Miguel Duarte Barroso <mdbarroso@redhat.com>
2021-12-09 14:46:36 +01:00
Doug Smith
b9d0d93d6e Pod UID mismatches should only warn on CNI DEL (#763) 2021-11-23 17:52:45 +09:00
Balazs Nemeth
84fde9d711 Update images/README.md (#761) 2021-11-19 21:22:34 +09:00
Doug Smith
4e0e65044b Merge pull request #758 from maiqueb/fix-legacy-entrypoint-e2e-tests
CI, e2e tests: fix legacy
2021-11-15 08:18:59 -05:00
Miguel Duarte Barroso
70660236a8 CI, e2e tests: fix legacy
Our CI is currently mistakenly executing the thick img on the e2e
legacy lanes. Furthermore, the e2e daemonset spec provided features
(and uses) the kubeconfig / multus conf generation binaries
provided only on the thick image.

This commit addresses these by enabling the e2e `setup_cluster.sh`
script user to specify the path to the desired deployment
configuration.

Github workflows are updated accordingly.

Signed-off-by: Miguel Duarte Barroso <mdbarroso@redhat.com>
2021-11-15 12:38:26 +01:00
Moritz Kröger
130db696ca Update quickstart.md (#754)
* Update quickstart.md

removed unnecassary dollarsign since it kills the quick copy functionality of Code in Github

* Update README.md

* Update quickstart.md

* Update how-to-use.md

Co-authored-by: Doug Smith <douglaskippsmith@gmail.com>
2021-11-12 00:24:06 +09:00
Doug Smith
ada145ca5f Merge pull request #753 from s1061123/fix/cni-bin-dir
Added --cni-bin-dir and --multus-bin-file for regression
2021-11-11 00:00:46 +09:00
Tomofumi Hayashi
25c46c84b8 Added --cni-bin-dir and --multus-bin-file for regression 2021-11-08 17:40:54 +09:00
Etienne Champetier
32c952e501 Fixup thick deployment, make images thiner (#747)
* deployment, thick: only use thick image

Signed-off-by: Etienne Champetier <e.champetier@ateme.com>

* images: only keep binaries and LICENSE

Signed-off-by: Etienne Champetier <e.champetier@ateme.com>
2021-11-02 14:20:37 +09:00
Tomofumi Hayashi
7091831a00 Remove dependency of go-dproxy (#746)
This change removes to dependency of go-dproxy from multus to
reducing library dependencies.
2021-10-28 12:15:11 -04:00
Tomofumi Hayashi
1e43784d4c Change the sort of image push. 2021-10-28 23:04:07 +09:00
Miguel Duarte Barroso
42fde2292d deployment, thick: remove extra multus-cni-config mountpoint (#745)
This volume was removed since multus now requires the default cluster
network CNI configuration to be available. As such, the volume as
removed, but we unfortunately forgot to remove to remove the volume
mount.

Signed-off-by: Miguel Duarte Barroso <mdbarroso@redhat.com>
2021-10-28 09:37:35 -04:00
Miguel Duarte Barroso
8ba2accb9f Replace entrypoint script with initcontainers (#718)
* build: install the multus binary in an init container

Signed-off-by: Miguel Duarte Barroso <mdbarroso@redhat.com>

* build: generate kubeconfig via go

Signed-off-by: Miguel Duarte Barroso <mdbarroso@redhat.com>

* build: generate multus cni configuration via golang

Signed-off-by: Miguel Duarte Barroso <mdbarroso@redhat.com>

* build: provide a docker img for daemon based deployments

We will have 2 different images (only on amd64 archs):
- legacy entrypoint script based
- daemonized process

The `image-build` docker action is updated, to build these 2 images.

There will be 2 different deployment specs, along with e2e test
lanes, one for each of the aforementioned alternatives.

Signed-off-by: Miguel Duarte Barroso <mdbarroso@redhat.com>

* build: delegate CNI config watch loop via golang

For the thick-plugin alternative, provide the watch loop for
configuration regeneration via a golang binary.

Over time, this binary is expected to run the control loop to watch
out for pod updates.

To enable current multus users to chose when they upgrade to this new
deployment setup, these changes are provided in separate multus images,
having a different yaml spec files. Both of these alternatives are
tested e2e, since a new lane is introduced.

The following libraries are introduced, along with the motivation for
adding them:
- dproxy: allows traversing the default network configuration arbitrarily,
  similar to what an X path / JSON path tool provides.
  Repo is available at [0].
- fsnotify: watch for changes in the default CNI configuration file.
  Repo is available at [1].

The config map providing the default network CNI configuration is not
copied over, since originally, the user was not required to install a
default network CNI plugin first, but, nowadays, this is a required
step of multus.

As such, it is no longer required to provide a default CNI
configuration.

[0] - https://github.com/koron/go-dproxy
[1] - https://github.com/fsnotify/fsnotify

Signed-off-by: Miguel Duarte Barroso <mdbarroso@redhat.com>

* run gofmt

Signed-off-by: Miguel Duarte Barroso <mdbarroso@redhat.com>

* refactor: make the builder pattern more idiomatic to golang

Signed-off-by: Miguel Duarte Barroso <mdbarroso@redhat.com>

* build: update github actions to release new imgs

Signed-off-by: Miguel Duarte Barroso <mdbarroso@redhat.com>
2021-10-27 08:42:37 -04:00
Dan Williams
b56dd5f67f multus: test Pod UID scenarios when both passed and not passed by runtime
Because the tests fake out the OS exec functionality, the environment that
would usually be passed to a plugin instead gets passed as a string array
to the ExecPlugin() function in the tests. But when verifying the expected
environment this function was looking at the actual OS environment rather
than the passed string array. Fix that.

Use that to test various cases of the pod UID being passed to plugins.

Signed-off-by: Dan Williams <dcbw@redhat.com>
2021-10-26 01:20:43 +09:00
Dan Williams
e8e99f1771 multus: log error marshaling delegate netconf
Fixes an unused variable warning too.

Signed-off-by: Dan Williams <dcbw@redhat.com>
2021-10-26 01:20:43 +09:00
Dan Williams
cb19a22cb9 multus: fail if given pod UID does not match Kube API pod UID
If the runtime passes a pod UID via K8S_POD_UID (which both CRIO and
containerd do as of mid-2021) then fail if the pod we get from the
Kube API has a different UID. This would indicate that the pod was
deleted and recreated while Multus was attempting to set up
networking for the old pod instance's sandbox, and it's pointless
to continue setting up a sandbox for a dead pod instance.

Also pass the pod UID through to plugins so they can perform
additional checking and validation on the pods they get from the
Kube API.

Signed-off-by: Dan Williams <dcbw@redhat.com>
2021-10-26 01:20:43 +09:00
Miguel Duarte Barroso
392726842f e2e tests: allow podman OCI
Signed-off-by: Miguel Duarte Barroso <mdbarroso@redhat.com>
2021-10-20 20:58:32 +09:00
Tomofumi Hayashi
76c31b0861 Fix version string in '-v' option
Due to change the file layout, previous version command does not
work. This change fix it.
2021-10-15 00:07:20 +09:00
Doug Smith
51a74efe57 Merge pull request #729 from s1061123/dev/update-layout
Change file layout and mention the supported Kubernetes version
2021-09-29 10:19:02 -04:00
Tomofumi Hayashi
bf0b37e010 Change file layout and mention the supported Kubernetes version 2021-09-28 22:40:51 +09:00
Doug Smith
efdc0a5c7d Merge pull request #724 from s1061123/downgrade-k8s-vendor
Downgrade Kubernetes vendor version
2021-09-17 14:46:50 -04:00
Tomofumi Hayashi
ae4a28b689 Downgrade Kubernetes vendor version
Multus community decide that multus support the Kubernetes that
Kubernetes community supports, so changed vendor code to the
oldest version of currently supported.
2021-09-17 22:48:12 +09:00
Doug Smith
e1b0698eb2 Merge pull request #723 from s1061123/update-go-version
Update golang version (at least >= 1.16)
2021-09-15 08:13:42 -04:00
Tomofumi Hayashi
35fdb29385 Update golang version (at least >= 1.16)
Currently golang community supports 1.16 and later, hence, need
to update golang version in our build pipeline. This change
updates golang version to 1.17/1.16.
2021-09-14 16:53:35 +09:00
张祖建
a28f5cb56c Fix typos
Signed-off-by: 张祖建 <zhangzujian.7@gmail.com>
2021-09-14 00:25:01 +09:00
Doug Smith
ad257698ef Merge pull request #712 from nicklesimba/patch-1
Update quickstart.md
2021-08-25 16:48:33 -04:00
Nikhil Simha
8b3bbf38c8 Update quickstart.md
There is a typo in the expected resulting annotations
2021-08-25 13:27:18 -04:00
Doug Smith
a506d7606c Merge pull request #696 from cgchinmay/fix_entrypoint
Use MULTUS_MASTER_CNI_FILE_NAME as MASTER_PLUGIN as is, if specified
2021-07-16 15:25:51 -04:00
Chinmay Gadgil
7e44bb6d21 Use MULTUS_MASTER_CNI_FILE_NAME as MASTER_PLUGIN as is, if specified 2021-07-12 10:30:20 -07:00
Tomofumi Hayashi
9b45d4b211 Merge branch 'master' of https://github.com/k8snetworkplumbingwg/multus-cni 2021-07-08 22:52:30 +09:00
Doug Smith
f77c591d69 Merge pull request #695 from cgchinmay/update_golang_version
Update golang version for installing packages
2021-07-08 09:52:03 -04:00
Tomofumi Hayashi
8c9f409032 Fix github action 2021-07-08 22:52:02 +09:00
Chinmay Gadgil
0724c2b9b0 Update golang version for installing packages 2021-07-06 22:56:21 -07:00
Miguel Duarte Barroso
085870c4b5 Export poll[Interval|Timeout] as constants
Thus not repeating ourselves, nor shadowing the global variables
that had the same name (pollInterval / pollTimeout).

Signed-off-by: Miguel Duarte Barroso <mdbarroso@redhat.com>
2021-06-26 00:06:30 +09:00
Miguel Duarte Barroso
26ef3c3eb4 Cut the retry interval and timeout by half on pod retrieval
Signed-off-by: Miguel Duarte Barroso <mdbarroso@redhat.com>
2021-06-26 00:06:30 +09:00
Miguel Duarte Barroso
1eeab9b589 Retry pod retrieval on multiple error types
Also retry on the following error types (cmd ADD/DEL):
- IsInternalError
- IsConnectionReset
- IsConnectionRefused

Signed-off-by: Miguel Duarte Barroso <mdbarroso@redhat.com>
2021-06-26 00:06:30 +09:00
Doug Smith
7f5620db76 Merge pull request #689 from maiqueb/fix-missing-cni-version-example
examples: missing cni version on version without delegates
2021-06-23 12:57:56 -04:00
Miguel Duarte Barroso
1e29a6b50c examples: missing cni version on version without delegates
Signed-off-by: Miguel Duarte Barroso <mdbarroso@redhat.com>
2021-06-23 18:23:30 +02:00
Peng Liu
d09cc8e581 Use the default socket path in GetResourceClient when unspecified
Signed-off-by: Peng Liu <pliu@redhat.com>
2021-06-08 23:05:54 +09:00
xieyanker
cd23938191 Update calico daemonset's url 2021-06-02 21:32:08 +09:00
xieyanker
3b8aa66765 Fix typo 2021-06-02 21:31:37 +09:00
Doug Smith
37adefba51 Merge pull request #679 from xieyanker/master_cni_file
Support the specific cni file name
2021-06-02 08:08:05 -04:00
xieyanker
ec30b99534 Update how-to-use --multus-master-cni-file-name 2021-06-02 14:24:41 +08:00
xieyanker
a53233028b Update ORG_PATH for test-go.sh 2021-06-01 21:58:05 +09:00
xieyanker
492ffec8c8 Support the specific cni file name 2021-05-29 15:29:37 +08:00
Doug Smith
c25a39c5a3 Merge pull request #672 from s1061123/dev/update-lib
Update vendor package
2021-05-26 14:04:02 -04:00
Tomofumi Hayashi
3f1031e7b4 Update vendor package 2021-05-27 02:25:34 +09:00
Tomofumi Hayashi
2339c11a15 Remove global variables from kubletclient
Fixes #673
2021-05-27 01:45:15 +09:00
Sho SHIMIZU
2ba3d3cda2 Describe additional condition when using clusterNetwork
When configuring `clsuterNetwork` in Multus CNI config, the value
for `clusterNetwork` needs to match the value for `name` key in
the file `clusterNetwork` setting refers to. This condition is
undocumented in doc/configuration.md. This PR adds description
on the condition for users to understand `clusterNetwork` config
more clearly.

Signed-off-by: Sho SHIMIZU <sho.shimizu@gmail.com>
2021-05-24 22:11:30 +09:00
dougbtv
6abe8ee06b The kubeconfig creation should be an atomic operation 2021-05-13 22:40:06 +09:00
Doug Smith
a03b3e8c41 Merge pull request #666 from s1061123/fix/update-nad-lib
Update net-attach-def client library
2021-05-12 12:11:14 -04:00
Tomofumi Hayashi
753d18740a Update net-attach-def client library 2021-05-11 01:29:26 +09:00
Doug Smith
1a0fa953f9 Merge pull request #661 from xieyanker/patch-1
update 30-multus.conf to 00-multus.conf
2021-04-29 09:39:45 -04:00
xieyanker
bd57d31780 update 30-multus.conf to 00-multus.conf 2021-04-28 15:50:41 +08:00
Doug Smith
91a7d22e2b Merge pull request #657 from s1061123/dev/add-cluster-net-name
Add cluster network name in pod network annotation
2021-04-20 15:01:55 -04:00
Doug Smith
8d555dba24 Merge pull request #658 from e0ne/fix-typo
Fix typo: s/Lauch/Launch
2021-04-20 15:01:00 -04:00
Ivan Kolodyazhny
e566760a45 Fix typo: s/Lauch/Launch 2021-04-20 21:18:04 +03:00
Tomofumi Hayashi
cd7492f79b Add cluster network name in pod network annotation
This addresses #656
2021-04-19 23:20:36 +09:00
Bjorn Svensson
9e3ad2ea1e Correcting Dockerfile path for manual e2e tests
Signed-off-by: Björn Svensson <bjorn.a.svensson@est.tech>
2021-04-19 17:34:30 +09:00
Doug Smith
a52680b3bf Merge pull request #651 from s1061123/dev/add-arm32
Add arm32v7 container image support
2021-04-07 11:37:00 -04:00
Tomofumi Hayashi
78cf9fced8 Add arm32v7 container image support
Currently multus-cni releases arm32 binary as release tar ball.
This changes also introduce container image for easy deployment.
Fix #639
2021-04-04 04:23:39 +09:00
dougbtv
905b5d0e42 Github action for closing stale issues 2021-04-03 18:12:58 +09:00
dougbtv
0ef8c27a67 [docs] Adds release policy 2021-04-01 22:53:15 +09:00
Doug Smith
e603d8dbb0 Merge pull request #644 from s1061123/dev/cleanup-dev-info
Skip to call device-info related function if not required
2021-04-01 09:52:17 -04:00
Tomofumi Hayashi
9e96c38ebe Skip to call device-info related function if not required
The case withot DeviceInfo/ResourceName, we could skip functions
related to device info. This change skips to call these functions
if delegates does not have DeviceInfo/ResourceName.
2021-04-01 03:55:57 +09:00
Doug Smith
ad6f57f14d Merge pull request #643 from s1061123/fix/no-network-error
[WIP] Change nil instead of error in case of no network annotation
2021-03-31 12:14:56 -04:00
Tomofumi Hayashi
479e2bd78e Change nil instead of error in case of no network annotation
fix #642
2021-03-31 23:06:55 +09:00
Doug Smith
ae56437297 Merge pull request #638 from s1061123/dev/use-non-default-libcni-cache
Change libcni's cache directory from default for multus delegates
2021-03-29 17:05:05 -04:00
Doug Smith
dc4d6e6764 Merge pull request #636 from s1061123/fix/error-on-syntax-error
Return error on annotation parsing error
2021-03-29 09:23:27 -04:00
Tomofumi Hayashi
75acc10312 Change libcni's cache directory from default for multus delegates
This changes CNI cache directory to non default places to avoid
conflicts among CNI runtimes.
2021-03-27 04:12:10 +09:00
Tomofumi Hayashi
8d7308e6bb Return error on annotation parsing error
Fix #635
2021-03-26 01:31:01 +09:00
Doug Smith
c4b9534529 Merge pull request #634 from s1061123/fix/delete_old_main
Delete main from pkg/multus because now it was moved to cmd/main.go
2021-03-24 17:02:45 -04:00
Tomofumi Hayashi
c8e63996c8 Delete main from pkg/multus because now it was moved to cmd/main.go 2021-03-25 03:02:50 +09:00
dougbtv
5d98a0e0eb Updates Readinessindicator error message to be actionable by users 2021-03-24 04:19:44 +09:00
Doug Smith
343a4e3687 Merge pull request #629 from s1061123/fix/change-org-name
Fix/change org name
2021-03-17 15:36:17 -04:00
Doug Smith
feb52328d2 Merge pull request #627 from s1061123/fix/change-image-url
Change image url to ghcr.io
2021-03-16 14:50:00 -04:00
Tomofumi Hayashi
118cc629cf Update organization name due to ownership change 2021-03-16 16:24:49 +09:00
Tomofumi Hayashi
784fecfa02 Change image url to ghcr.io 2021-03-13 05:05:17 +09:00
Doug Smith
f6298a3a29 Merge pull request #626 from s1061123/dev/use-ghcr
Change github action to use ghcr.io
2021-03-12 14:51:45 -05:00
Tomofumi Hayashi
20049dedfe Change github action to use ghcr.io 2021-03-13 04:38:21 +09:00
Doug Smith
20a5d5f34a Merge pull request #625 from e0ne/example-pod
Fix link to an example pod with SRIOV network
2021-03-12 14:33:59 -05:00
Ivan Kolodyazhny
b97c443a56 Fix link to an example pod with SRIOV network 2021-03-11 16:48:04 +02:00
Doug Smith
40a0faed5e Merge pull request #624 from s1061123/dev/bump-libcni
Bump libcni version
2021-03-10 15:53:14 -05:00
Tomofumi Hayashi
5feb1343cd Bump libcni version 2021-03-11 04:50:21 +09:00
Yun Zhou
dc9315f125 Provide the option to not to log via STDERR
Today, Multus will always log via STDERR, and these logs will then
logged by the Kubelet. If we also choose to have Multus log to a file by
setting the LogFile option in the CNI configuration, the same logs will
be logged twice.

This commit provide the option to disable logging to STDERR.

Signed-off-by: Yun Zhou <yunz@nvidia.com>
2021-03-10 17:13:12 +09:00
Kennelly, Martin
5141eab28a Fix invite to NPWG slack
Readding NPWG slack invite mechanism.

Signed-off-by: Kennelly, Martin <martin.kennelly@intel.com>
2021-03-02 04:39:51 +09:00
Doug Smith
c1166d2d3d Merge pull request #617 from s1061123/fix/check-tty
Conditional check for tty/non-tty in case of wait (i.e. read)
2021-02-25 10:22:17 -05:00
Tomofumi Hayashi
de463cca0d Conditional check for tty/non-tty in case of wait (i.e. read)
Fix #615.
2021-02-26 00:18:06 +09:00
Tomofumi Hayashi
02ad030899 Fix CI info 2021-02-24 15:32:46 +09:00
Doug Smith
e80696dc8e Merge pull request #613 from s1061123/dev/update-gh-actions
Update github actions CI pipeline including lint error fix
2021-02-23 10:05:55 -05:00
Tomofumi Hayashi
9bfb9b9b67 Update github actions CI pipeline including lint error fix 2021-02-23 20:01:34 +09:00
Doug Smith
a0d292a0e8 Merge pull request #606 from dougbtv/bump-protobuf
Bump protobuf to v1.3.2
2021-02-18 14:56:41 -05:00
dougbtv
fe42962eb5 [deps][vendor] Updates gogo/protobuf 2021-02-18 11:29:20 -05:00
Kennelly, Martin
094dcbe2c2 Update Slack URL in README following renaming
Signed-off-by: Kennelly, Martin <martin.kennelly@intel.com>
2021-02-18 23:42:26 +09:00
dougbtv
8bbd3fdcf2 Change to sleep infinity & read and omit & wait on sleep n (e.g. not infinity) 2021-02-18 23:42:00 +09:00
Doug Smith
e728da78bc Merge pull request #611 from yoheiueda/s390x
Add s390x support
2021-02-18 09:39:40 -05:00
Yohei Ueda
9824963f79 Add s390x support
This PR updates the GitHub Actions workflows to build multus
container images for the IBM Z architecture (s390x), and also
adds daemonsets for s390x nodes.

entrypoint.sh uses python3 when it is available, since centos images
are not available for s390x, and python2 is not installed by default
on debian-based images.

Signed-off-by: Yohei Ueda <yohei@jp.ibm.com>
2021-02-18 01:40:33 -05:00
Doug Smith
cd9efbf703 Merge pull request #607 from amorenoz/bug/runtime
conf: do not modify global runtimeconfig when merging
2021-02-16 14:23:34 -05:00
Adrian Moreno
91e4efcd68 conf: make a copy of global RuntimeConfig on merge
When we call mergeRuntimeConfig, the global RuntimeConfig gets
overwritten with the result of the merging, thus affecting the
subsequent delegates.

Do not modify the global RuntimeConfig and instead make a copy
when merging it.

Also, if a value has been provided for CNIDeviceInfoFile in the
delegate's runtimeconfig, overwrite it to avoid possible name
colissions.

Signed-off-by: Adrian Moreno <amorenoz@redhat.com>
2021-02-11 20:39:41 +01:00
dougbtv
63734fc026 Adds a trap for SIGTERM in entrypoint script 2021-02-10 04:57:07 +09:00
Doug Smith
bd90c262f6 Merge pull request #603 from s1061123/fix/graceperiod
Add grace period to missing deployment template
2021-01-29 08:40:48 -05:00
Tomofumi Hayashi
d093709f94 Add grace period to missing deployment template 2021-01-28 15:25:45 +09:00
dougbtv
f6df613c32 Pods in daemonset should have grace period reduced.
Otherwise, it can take a long time for the daemonset to stop, and there's no real reason it needs to hang out for a long time.
2021-01-28 15:22:27 +09:00
dougbtv
d4e8699825 The readme links need to be updated after directory change.
This updates the links to point to "doc/" instead of "docs/"
2020-12-17 05:23:14 +09:00
Nikhil Simha
62abb002dd Restructured multus to use Go standard project layout. 2020-12-16 22:38:10 +09:00
Doug Smith
bd9f2e9700 Merge pull request #595 from Mmduh-483/capabilities-entry-fail
Fix entrypoint fail to read capabilities in non chain plugin config
2020-12-14 08:28:41 -05:00
Mamduh Alassi
09190bce3e Fix entrypoint fail to read capabilities in non chain plugin config
entrypoint script fails with error when try reading capabilities in
non chain plugin config file when using "--multus-conf-file=auto"

Signed-off-by: Mamduh Alassi <mamduhala@mellanox.com>
2020-12-14 12:58:35 +02:00
Doug Smith
24386abae3 Merge pull request #553 from venuiyer/vi-multus
Allow the default-route to be empty
2020-12-10 09:45:53 -05:00
dougbtv
476c738c13 Allows specifying "global namespaces" when using namespace isolation 2020-12-10 23:40:18 +09:00
Doug Smith
e924318e18 Merge pull request #577 from Billy99/billy99-device-info
Add DeviceInfo Data to NetworkStatus Annotation
2020-12-01 13:50:26 -05:00
dougbtv
cfa0d64925 Multus should exit zero on DEL when cache file is missing and pod cannot be found.
Otherwise, this can cause a pod to not be fully deleted, its sandbox may remain as the DEL continues to be retried due to exiting non-zero every time.

See: https://bugzilla.redhat.com/show_bug.cgi?id=1900835
2020-11-25 22:11:17 +09:00
Billy McFall
ae797801b1 Remove Multus version of NetworkStatus
NetworkStatus was moved to network-attachment-definition-client in previous
merges and the Multus version of the structure was left behind, and not
being used.

Signed-off-by: Billy McFall <22157057+Billy99@users.noreply.github.com>
2020-11-19 16:38:42 -05:00
Billy McFall
f826461b06 Add DeviceInfo Data to Network Status Annotation
Signed-off-by: Billy McFall <22157057+Billy99@users.noreply.github.com>
2020-11-19 16:38:42 -05:00
Billy McFall
fb557ab20f Add CNIDeviceFile in RuntimeConfig
DPDeviceFile is used by Device Plugins to pass device data to CNIs, as defined
in the device-info-spec. The name of the DPDeviceFile is defined by the
device-info-spec as:
 <ResourceName>-<DeviceID>-device.json

If the DPDeviceFile exists, the NPWG implementation makes a copy of the file
and passes the name of the file to the delegate CNI via capabilityArgs as
CNIDeviceFile. If the DPDeviceFile does not exist, the filename is still
passed to the CNI. The CNI can create the file and popluate it if a device
is created within the CNI.

The name of the CNIDeviceFile is not defined by device-info-spec, but to
ensure the name does not clash it is formed by the following unique triplet:
[networkName, PodUUID, ifName]

k8snetworkplumbingwg/network-attachment-definition-client repo has utility
functions to abstract some of this functionality so it can be reused across
Device Plugins, NPWG implementations and CNIs.

Signed-off-by: Billy McFall <22157057+Billy99@users.noreply.github.com>
2020-11-19 16:38:30 -05:00
Billy McFall
fd3f485e63 Add deviceID support in runtimeConfig
Signed-off-by: Billy McFall <22157057+Billy99@users.noreply.github.com>
2020-11-19 16:34:29 -05:00
Billy McFall
665c43a2cd Merge RuntimeConf on delPlugins
RuntimeConfig depends on the delegate configuration. The Netconf runtime
information should be merged with the delegate config and the result
added to each command that is sent to the delegates. That was being done
for all commands except for delPlugins.

Do not export MergeCNIRuntimeConfig and call it from
CreateCNIRuntimeConf that now accepts a delegate ptr.

Call it from delPlugins for each delegate

Signed-off-by: Billy McFall <22157057+Billy99@users.noreply.github.com>
2020-11-19 16:34:15 -05:00
Billy McFall
2cd91b6bad Update vendor for network-attachment-definition-client update
Signed-off-by: Billy McFall <22157057+Billy99@users.noreply.github.com>
2020-11-19 16:06:54 -05:00
Billy McFall
e064679967 Point to latest network-attachment-definition-client
Move Multus to use latest network-attachment-definition-client repo which
contains the device-info-spec changes.

Signed-off-by: Billy McFall <22157057+Billy99@users.noreply.github.com>
2020-11-19 16:06:54 -05:00
Doug Smith
6a23d65fea Merge pull request #583 from aojea/cmdadddel
clarify cmdAdd error
2020-11-19 10:45:04 -05:00
Antonio Ojea
1b58bed5a6 clarify cmdAdd error
it can happen that a CNI Add operation is canceled because the
runtime sends a CNI Del too fast, so the pod was already deleted
when multus try to set the network status annotations.

Since multus is an executable and can not persist state, it can't
track the CNI requests that are done in parallel, but it can
assume that, if it was able to get the pod from the API, and in a
subsequent request the pod no longer exists, it is because it was
deleted.

Signed-off-by: Antonio Ojea <aojea@redhat.com>
2020-11-19 10:30:12 +01:00
Doug Smith
957e26674a Merge pull request #573 from rhdojun/patch-1
Update quickstart.md
2020-11-12 09:35:38 -05:00
Doug Smith
36d3874c4c Merge pull request #571 from Billy99/billy99-k8s-rebase
Bump kubernetes dependencies to v0.18.3
2020-10-27 15:36:55 -04:00
rhdojun
4bfc2b14f2 Update quickstart.md
Felt like the line wasn't finished yet.
2020-10-27 13:12:34 +01:00
Billy McFall
f62529d4ff Update source for k8s bump to v0.18.3
Signed-off-by: Billy McFall <22157057+Billy99@users.noreply.github.com>
2020-10-23 15:49:49 -04:00
Billy McFall
36b5edff29 Update vendor, go.mod and go.sum for k8s bump to v0.18.3
Signed-off-by: Billy McFall <22157057+Billy99@users.noreply.github.com>
2020-10-23 10:55:54 -04:00
Billy McFall
c8739f64b9 Run 'go fmt' on code base.
Signed-off-by: Billy McFall <22157057+Billy99@users.noreply.github.com>
2020-10-23 10:43:23 -04:00
Doug Smith
bc95a19c5d Merge pull request #559 from s1061123/fix/remove-travis
Remove travis.yml because CI is now switched to github/actions
2020-09-15 20:06:16 -04:00
Tomofumi Hayashi
0e4b8be1e7 Remove travis.yml because CI is now switched to github/actions 2020-09-15 16:47:14 +09:00
Doug Smith
d13e06a5df Merge pull request #556 from s1061123/add-default-route-e2e
Add e2e tests for default-route annotation
2020-09-14 13:31:45 -04:00
Tomofumi Hayashi
ff3ee290c9 Add e2e tests for default-route annotation 2020-09-14 12:56:12 +09:00
Shane Utt
8cc60f7dd8 Add ARM64 to images
This PR takes the existing ARM64v8 build
and creates Daemonsets in the install images
to deploy it for ARM based K8s clusters.

Fixes #554

Signed-off-by: Shane Utt <shaneutt@linux.com>
2020-09-14 12:47:34 +09:00
venu iyer
292d9a9af3 Allow the default-route to be empty
In
https://docs.google.com/document/d/1Ny03h6IDVy_e_vmElOqR7UdTPAG_RNydhVE1Kx54kFQ,
section 4.1.2.1.9,

"
4.1.2.1.9 “default-route” Default route selection for a particular attachment

This optional key with value of type string-array is used to explicitly select
which attachment will receive the default route. The value of items in the
“default-route” array are intended to be gateways, e.g. an IP address to which
packets that do not match any other routes are sent. This key must only be set
on one item in the Network Attachment Selection Annotation. This list may be empty.
"

However en empty list will fail currently; this change accommodates an
empty "default-route" by retaining the default route added by the
delegate.

Signed-off-by: venugopal iyer <venugopali@nvidia.com>
2020-09-08 14:53:25 -07:00
Doug Smith
2a01aec396 Merge pull request #552 from intel/fix/e2e
Update e2e
2020-09-03 13:50:14 -04:00
Tomofumi Hayashi
17b24d5fd5 Update e2e
This change contains following:
 - update kind version to 0.8.1
 - update setup script due to update
 - add teardown script
 - update README
2020-09-04 02:20:35 +09:00
Doug Smith
2dab3225de Merge pull request #550 from s1061123/fix/image-url
Specify image repo URL explicitly
2020-08-31 08:36:41 -04:00
Tomofumi Hayashi
95cc1902c0 Specify image repo URL explicitly
This fix supplies domain for container image repo because
in some runtime configuration, 'docker.io' is not specified as
default container repository url.
2020-08-31 14:58:10 +09:00
Mamduh Alassi
36f2fd64e0 Use latest image version 3.6 in daemonset files 2020-08-20 22:35:19 +09:00
Doug Smith
be492e1778 Merge pull request #545 from clementnuss/master
Pull underlying capabilities up to 00-multus.conf
2020-08-06 09:37:02 -04:00
Clément Nussbaumer
4c271a57d5 Pull underlying capabilities up to 00-multus.conf
Using Python, we analyze the content of the master plugin configuration,
and we integrate any capabilities from the underlying chained plugins
declaration. We only pull enabled capabilties from the underlying
(chained) plugin definitions.

Fixes intel#544

Signed-off-by: <Clement.Nussbaumer@Swisscom.com>
2020-08-05 10:29:05 +02:00
Doug Smith
e15f97860f Merge pull request #541 from s1061123/fix/crd
Fix CRD yaml file for right explan information
2020-07-28 10:39:13 -04:00
Tomofumi Hayashi
78669323d2 Fix CRD yaml file for right explan information 2020-07-28 11:56:08 +09:00
Doug Smith
c85b79f5ff Merge pull request #536 from s1061123/fix/update-vendor
Update vendors
2020-07-21 20:17:50 -04:00
Tomofumi Hayashi
801e1e8940 Update vendors 2020-07-22 09:15:24 +09:00
Doug Smith
41fefbb001 Merge pull request #522 from s1061123/fix/del-error-fix
Fix/del error fix
2020-07-21 17:13:33 -04:00
Tomofumi Hayashi
4eb6ae1553 Fix error handling on cmdDel
Fix #519
2020-07-21 14:52:07 +09:00
Doug Smith
b5211cb0d2 Merge pull request #534 from bmwiedemann/date
Allow to override build date with SOURCE_DATE_EPOCH
2020-07-09 09:52:28 -04:00
Bernhard M. Wiedemann
29df24fa6c Allow to override build date with SOURCE_DATE_EPOCH
in order to make builds reproducible.
See https://reproducible-builds.org/ for why this is good
and https://reproducible-builds.org/specs/source-date-epoch/
for the definition of this variable.

This date call only works with GNU date.

Also use UTC to be independent of timezone.
2020-07-08 05:08:11 +02:00
Doug Smith
e4a8c9f639 Merge pull request #530 from rktidwell/master
build: Enable -mod build flag to be toggled via environment variable
2020-07-06 08:49:58 -04:00
Adrian Chiris
2796202d8c Add infinibandGUID runtime config to delegate netconf
This commit extend the various network conf methods
to translate `infiniband-guid` network attachment configuration
to `infinibandGUID` CNI runtime config.

- Update relevant methods in types package
- Update unit tests
2020-06-26 14:55:21 +09:00
Adrian Chiris
46be700cb5 Struct updates
- Add `infinibandGUID` CNI runtime config
- Add `infiniband-guid` Network attachment attribute
- Reflect infiniband guid request in Delegate network config
2020-06-26 14:55:21 +09:00
Ryan Tidwell
a167d54608 build: Enable -mod build flag to be toggled via environment variable
This change will enable builds to be performed with the option of
passing the -mod flag to 'go build'. This can be done by optionally
setting the MODMODE environment variable prior to building.

For example, toggling the -mod setting for the build can be
accomplished as follows:

```
$ MODMODE=vendor ./build
```

Signed-off-by: Ryan Tidwell <rtidwell@suse.com>
2020-06-24 16:11:19 -05:00
Shahar Klein
ecb79330c0 Add support for log rotation
When using debug level the log files tends to fill up quickly.
Add support for log rotation using lumberjack, simple and easy to use
log rotation module.

Signed-off-by: Shahar Klein <sklein@nvidia.com>
2020-06-17 15:31:19 +09:00
Doug Smith
3882e405ef Merge pull request #515 from s1061123/fix/namespace-in-status
Fix network status name/namespace to compliant with multi-net-spec
2020-06-09 15:08:23 -04:00
Doug Smith
5e15ff18f8 Merge pull request #518 from dougbtv/readme-typo
README typo for roll-YOUR-own
2020-06-09 15:07:49 -04:00
dougbtv
28bb98f78b README typo for roll-YOUR-own 2020-06-09 15:07:19 -04:00
Tomofumi Hayashi
e7c8977423 Fix network status name/namespace to compliant with multi-net-spec
This fix changes network status name to net-attach-def name with
namespace, to compliant with k8s npwg's multi-net-spec.
2020-06-09 12:43:49 +09:00
Doug Smith
fff8e490b9 Merge pull request #511 from s1061123/fix/error-on-fail
Change the error handling for kubernetes client
2020-06-08 09:14:02 -04:00
dougbtv
809a16fbed Adds code of conduct 2020-06-05 09:18:10 +09:00
Tomofumi Hayashi
f5dcb9d8be Change the error handling for kubernetes client
This change adds retry to wait a bit if kubernetes client
returns service unavailable.

This fixes #492
2020-06-01 23:17:42 +09:00
Doug Smith
fdd7d30095 Merge pull request #507 from s1061123/dev/update-example
Simplify examples directory
2020-05-28 09:59:10 -04:00
Tomofumi Hayashi
c976f6bceb Add deviceid in clusterNetwork 2020-05-28 10:00:29 +09:00
Tomofumi Hayashi
8131923b14 Simplify examples directory 2020-05-19 21:29:19 +09:00
Tomofumi Hayashi
4eac660359 Introduce gopkg.in for go module
This change introduces gopkg.in to allow everyone to use multus
code as library. Currently multus-cni uses version 'v3', hence
it hits go modules limitation, as #504 describes.

This change fix #504 with gopkg.in.
2020-05-15 21:33:26 +09:00
dougbtv
ec5fd6c923 Move pre-1.16 Kubernetes assets to a deprecated folder (to later remove) 2020-05-08 09:50:33 +09:00
Doug Smith
b8540e190d Merge pull request #455 from cucosion/feature/gkeexample
Daemonset for Google Kubernetes Engine for kubernetes cluster version…
2020-04-30 09:44:45 -04:00
Doug Smith
a4c2b67784 Merge pull request #497 from s1061123/fix/improve-cni-logs
[WIP] Fix/improve cni logs
2020-04-30 08:43:09 -04:00
Tomofumi Hayashi
b2439f8279 Simplify error message in case of delegating CNI error
This fix removes redundant error messages and try to simplify
if the error comes from delegating CNI plugins.
2020-04-30 18:02:05 +09:00
dougbtv
c8fc357f05 Adds development docs note regarding issue policy 2020-04-30 10:59:26 +09:00
dougbtv
92beb4bcdc Sets the Kubernetes API calls timeout to 60 seconds 2020-04-23 10:47:11 +09:00
dougbtv
931c12531d Allows namespaceIsolation to allow pods in any namespace refer to the default namespace 2020-04-22 09:08:11 +09:00
Doug Smith
8dba1f4a37 Merge pull request #487 from redhat-nfvpe/dev/test
Skip docker push action if REPOSITORY_PASS is not set
2020-04-21 08:56:08 -04:00
Tomofumi Hayashi
aeaf78a310 Skip docker push action if REPOSITORY_PASS is not set 2020-04-21 21:54:44 +09:00
Tomofumi Hayashi
ab073f88cd Add error message in case of unexpected situation
To troubleshooting #481, adds error message for further analysis.
2020-04-21 21:42:57 +09:00
Ted Yu
1df1e4f530 Check Pod parameter against nil before calling Eventf
Signed-off-by: Ted Yu <yuzhihong@gmail.com>
2020-04-21 00:12:36 +09:00
dougbtv
81297f5b74 Updates Dockerfile to golang 1.13 (specifying version) 2020-04-20 21:44:17 +09:00
dougbtv
3ddc6250de Fix pre 1.16 api version for CRDs 2020-04-17 17:10:20 +09:00
dougbtv
8fff5aac60 Add description fields to NetworkAttachmentDefinition CRD 2020-04-16 02:01:40 +09:00
Doug Smith
6ccf03e8b3 Merge pull request #473 from ashish-billore/master
Error log for network-attachment-definition
2020-04-02 09:46:00 -04:00
dougbtv
c0891354ff Adds readinessindicatorfile check on CNI DEL 2020-04-02 22:40:09 +09:00
ashish-billore
ea95133ef4 Error log for network-attachment-definition
Corrected the error for missing network-attachment-definition
updated test for this error.
2020-04-02 17:40:32 +09:00
Doug Smith
5931d24639 Merge pull request #469 from ashish-billore/patch-2
Update quickstart.md
2020-03-30 08:40:33 -04:00
Ashish Billore
055f74fc61 Update quickstart.md 2020-03-30 14:02:35 +09:00
Mamduh Alassi
14fb6be109 Use latest image version 3.4.1 in daemonset file 2020-03-27 00:21:21 +09:00
ICucos
b6bfb75af0 Daemonset for Google Kubernetes Engine for kubernetes cluster version pre 1.16. To be able to start cluster with version 1.15 i used "gcloud container clusters create cl-name --zone europe-west1-b --num-nodes=2 --machine-type=n1-standard-8 --image-type ubuntu --enable-network-policy --cluster-version=1.15.9-gke.24". !!!!important to start the cluster with --enable-network-policy that will enable CNI in kublet 2020-03-25 13:03:44 +02:00
Tomofumi Hayashi
7f50f5f175 Fix CI workflow 2020-03-23 23:49:05 +09:00
Doug Smith
ea72e56fab Merge pull request #462 from s1061123/dev/add-arm64v8-ci
Add arm64 build in CI workflow
2020-03-23 09:52:25 -04:00
Tomofumi Hayashi
055a7568ad Logging improvement (UID, net-attach-def)
This change adds pod UID and net-attach-def name in verbose log
and sends kubernetes event when net-attach-def is not found.
2020-03-23 21:32:33 +09:00
Tomofumi Hayashi
c7cd0ef822 Add arm64 build in CI workflow 2020-03-23 13:00:50 +09:00
Trevor Tao
f885b38332 Add Dockerfile for building image on arm64
Add Dockerfile.arm64 for building Multus image on arm64.

Actually it's multi-arch capable and works for
amd64 platform too if used.

Signed-off-by: Trevor Tao <trevor.tao@arm.com>
2020-03-19 22:41:27 +09:00
Trevor Tao
cd1a76f919 Add Dockerfile for building image on arm64
Add Dockerfile.arm64 for building Multus image on arm64.

Actually it's multi-arch capable and works for
amd64 platform too if used.

Signed-off-by: Trevor Tao <trevor.tao@arm.com>
2020-03-19 22:41:27 +09:00
Tomofumi Hayashi
079c853eba Add Kubernetes event log when the pod is launched 2020-03-16 22:08:03 +09:00
Tomofumi Hayashi
bfaf22964b Fix goreleaser file for build-release error 2020-03-16 21:58:41 +09:00
ICucos
1bc8064a5b Daemonset for Google Kubernetes Engine for kubernetes cluster version 1.16 +. To be able to start cluster with version 1.16 i used rapid channel "gcloud beta container clusters create cluster --zone europe-west1-b --num-nodes=1 --machine-type=n1-standard-8 --image-type ubuntu --enable-network-policy --release-channel=rapid --enable-autorepair" 2020-03-16 13:19:36 +02:00
Tomofumi Hayashi
eaf6ff6e20 Update vendor file to fix #426 2020-03-13 12:16:49 +09:00
Adrian Chiris
5577822b36 Pass DeviceID to each plugin in configuration list
Until today, it was hardcoded that DeviceID will only be
injected for the first CNI in the chain.

This commit modifies multus to pass DeviceID to each network
configuration element in a network configuration list.
This will  allow multiple CNI's to act on DeviceID when CNI
plugins are being chained for a specific network.

The change is required to allow CNI's to ensure network
isolation (introduced in kernel >= 5.2.0 see [1]) for RDMA devices
when exist.

e.g for SR-IOV network:
sriov-cni moves network device associated with the provided DeviceID
to to the container's network namespace.
An "RDMA cni" would do the same for the corresponding RDMA device when
RDMA traffic is desired on the network.

[1] https://patchwork.kernel.org/cover/10810451/
2020-03-12 23:48:03 +09:00
Periyasamy Palanisamy
32fe803221 Log message after logger initialization
In cmdCheck and cmdDelete debug messages are logged even before logger
is initialized with its log level and file (done in types.LoadNetConf).
Because of this those debug messages are not logged into the file.

Signed-off-by: Periyasamy Palanisamy <periyasamy.palanisamy@est.tech>
2020-03-05 23:48:15 +09:00
Doug Smith
1412caafbd Merge pull request #446 from s1061123/no-config-invalidation
Removes configuration invalidation
2020-03-02 10:08:45 -05:00
Tomofumi Hayashi
bdece11192 Removes configuration invalidation 2020-02-28 12:43:49 +09:00
Doug Smith
32952b929c Merge pull request #442 from s1061123/dev/kind-e2e
[WIP]Add e2e test with kind in CI pipeline
2020-02-20 09:35:25 -05:00
dougbtv
1042a5e25f Changes wait.ExponentialBackoff to wait.PollImmediate and exposes readinessindicatorfile via entrypoint parameter 2020-02-19 10:03:43 +09:00
dougbtv
9774ddade1 [docs] Updates quickstart to use alpine image 2020-02-13 17:09:37 +09:00
Tomofumi Hayashi
76c458228e Add e2e test with kind in CI pipeline 2020-02-13 17:02:22 +09:00
dougbtv
4fdaf3f427 [bugfix] Fixes unnecessary wait when readinessindicatorfile is not present 2020-02-13 01:04:28 +09:00
Tomofumi Hayashi
8334b73296 Add Github Actions for CI pipeline, to be replace with travis 2020-02-12 22:57:04 +09:00
groclawski
3e601c6ffe double word fix 2020-02-11 00:04:04 +09:00
Tomofumi Hayashi
9c35b5ccf2 Fix travis CI 2020-02-10 16:01:18 +09:00
Tomofumi Hayashi
da9da81be9 Fix travis ci error 2020-01-25 01:18:32 +09:00
Doug Smith
36f630fd39 Merge pull request #431 from s1061123/dev/container-march-images
Support container multi architecture image with manifest
2020-01-23 09:40:07 -05:00
Tomofumi Hayashi
dfd19e5b10 Support container multi architecture image with manifest 2020-01-21 02:48:10 +09:00
Doug Smith
c534b7d364 Uses atomic operation for writing config file (#430) 2020-01-17 16:10:46 -05:00
Michael C. Cambria
c35c4b7e97 Add CNI Check support (#427)
Add tests for CNI version 0.4.0
2020-01-13 09:57:21 -05:00
Tomofumi Hayashi
b2bf154328 Fix travis ci (#421)
This change update travis pipeline as following:
 - cleanup unused parameters/stages
 - add condition based on parameter (now user can use travis CI
   in cloned repo)
 - suppress ppc64 deployment because amd64 also build ppc images
   and other arch (fixes #418)
2019-12-11 15:41:36 -05:00
Tomofumi Hayashi
9874c14e23 Replace multus code with NPWG client library code 2019-12-10 14:38:09 +09:00
Tomofumi Hayashi
f4f2f65d1d Use NPWG client library to manipulate net-attach-defs
This change introduce NPWG client library functions to manipulate
net-attach-defs. This also requires to change k8sclient and unit
test code as well.
2019-12-10 14:38:09 +09:00
Shravan Vallala
cb3f59e7e7 Server URL in multus kubeconfig at /etc/cni/net.d/multus.d/multus.kubeconfig
is not properly setup for IPv6 installs

Fix:

If the API server host is IPv6 address then the server url should
include square braces to separate the IP address and port correctly
2019-12-10 09:09:37 +09:00
Shravan Vallala
a3712815fd Server URL in multus kubeconfig at
/etc/cni/net.d/multus.d/multus.kubeconfig is not properly setup for IPv6
installs

Fix:

If the API server host is IPv6 address then the server url should
include square braces to separate the IP address and port correctly
2019-12-10 09:09:37 +09:00
Doug Smith
230f314877 Bump daemonset tag to v3.4 (#417) 2019-12-03 12:38:10 -08:00
Tomofumi Hayashi
a314f90dda Fix unit test to track on updated error message 2019-11-15 08:31:49 -05:00
dougbtv
ecc474a264 Skips binary copy in entrypoint with new parameter 2019-11-07 23:24:04 +08:00
Dan Williams
c7f957194b multus: print pod namespace/name in cmdAdd/cmdDel error messages
Signed-off-by: Dan Williams <dcbw@redhat.com>
2019-11-06 10:04:47 -05:00
dougbtv
8c76fd62e0 Adds cursory unit test for default-route and cleans lint (and one errant test) 2019-10-29 13:34:24 -04:00
dougbtv
3a9dd7ed76 Properly uses default-route in annotation to set the gateway. Fixes network status results. 2019-10-29 13:34:24 -04:00
Tomofumi Hayashi
165e23b72c Support gateway in NetworkSelectionElement
Changes config JSON from gateway to default-route, adds Readme, fixes lint

Co-authored-by: dougbtv <dosmith@redhat.com>
2019-10-29 13:34:24 -04:00
Michal Rostecki
84c348ce18 build: Allow to define VERSION and COMMIT without git
Previously the build script required git to be used and installed which
did not allow to build Multus from a tarball which doesn't contain .git
directory. That made packaging of Multus hard.

Example usage after the change if you do not want to use git:

```
$ VERSION=v3.3 COMMIT=ba33df ./build
```

Signed-off-by: Michal Rostecki <mrostecki@opensuse.org>
2019-10-29 09:06:44 -04:00
Tomofumi Hayashi
8bdb7104d7 Update k8s npwg repo name due to its change 2019-10-29 09:06:27 -04:00
Tim Rozet
3fbfe40e12 Fixes K8sNetworkPlumbingWG package capitalization
Migrates package to use capitalized name, also cleans up dependencies.

Signed-off-by: Tim Rozet <trozet@redhat.com>
2019-10-21 10:42:49 -04:00
Tim Rozet
e8baccff16 Removes duplicate NetworkAttachment CRD ref
The CRD is now defined in the NetworkPlumbingWG org, along with
generated libs for client, listers, informers, and deep copy functions.
Therefore remove the duplicate definition here, and use the standard
definition.

Signed-off-by: Tim Rozet <trozet@redhat.com>
2019-10-21 10:42:49 -04:00
Tomofumi Hayashi
2745e46ed8 Support 'cni-args' in NetworkSelectionElement 2019-10-21 21:33:07 +09:00
Tomofumi Hayashi
adec211ae1 Support CNI RuntimeConfig for portmap/bandwidth/ip/mac
This changes introduce CNI RuntimeConfig for portmap, bandwidth,
ip and mac for latest specification. IP and Mac is previously
applied through CNI_ARGS, but it is changed to RuntimeConfig
for now.
2019-10-16 09:20:11 -04:00
Tomofumi Hayashi
0a2f7b18d3 Improve error/debug message
This diff changes error message with fixed format for easy-to-read
for users.
2019-10-10 10:32:45 -04:00
Tomofumi Hayashi
f4431cd010 Update CRD's version to v1 2019-10-10 08:58:27 -04:00
Tomofumi Hayashi
731eeb3a78 Change API version (RBAC to v1, CRD to v1) and add crio-pre1.16.yml 2019-10-10 08:58:27 -04:00
dougbtv
ec3348c155 Updates daemonset for Kube 1.16, also docs and adds pre-1.16 daemonset 2019-10-10 08:58:27 -04:00
tdorsey
13d4157eb4 Fix more typos 2019-09-20 11:45:10 +09:00
tdorsey
c60332e637 Fix minor grammatical errors 2019-09-20 11:45:10 +09:00
dougbtv
31ae5a77c0 [entrypoint] Adds --additional-bin-dir option to entrypoint to generate binDir configuration option 2019-09-19 22:38:07 +09:00
dougbtv
32afefbb34 Appends binDir to CNI_PATH so that invoke.DelegateAdd/Del can find CNI plugins in alternate paths 2019-09-19 00:28:18 +09:00
dougbtv
83556f49bd [dockerfile] Use ENV GO111MODULE=off when building from openshift/origin-release:golang-1.10 2019-09-02 16:55:04 +09:00
dougbtv
e2f75d4ee5 [entrypoint] Adds script parameter to optionally rename source CNI config file to .old 2019-08-31 11:23:34 +09:00
dougbtv
56f42e0b51 [deps] Update grpc for CVE-2019-9511 https://nvd.nist.gov/vuln/detail/CVE-2019-9511 2019-08-30 14:54:37 +09:00
dougbtv
59a267363d [entrypoint] Adds one-shot CRIO restart, plus renames source CNI config to .old when not using the watch loop 2019-08-29 10:33:30 -04:00
Tomofumi Hayashi
c8a59dbb78 Bumpup CNI repo version 2019-08-27 10:14:16 +09:00
nicklesimba
d9d72c7a4f Added coveralls badge (#363) 2019-08-23 09:42:51 -04:00
Tomofumi Hayashi
05df28a58c Remove UnmarshalJSON() for NetworkSelectionElement (#362)
To support non-string variable in NetworkSelectionElement, remove
UnmarshalJSON(). interfaceRequest json is still supported in the
changes.
2019-08-22 11:19:06 -04:00
dougbtv
b2e1098ab5 [entrypoint] Adds CRIO restart
Co-authored-by: s1061123 <tohayash@redhat.com>
2019-08-21 15:09:44 +09:00
dougbtv
b38ab9771c [entrypoint] Adds --cleanup-config-on-exit to the entrypoint 2019-08-21 15:09:44 +09:00
nicklesimba
7763f1593b Added tests to k8sclient.go (#357)
* Improved coverage of checkpoint.go to 96.4%

* Improved coverage of checkpoint.go to 96.4%

* Fixed unit tests in checkpoint_test.go and conf_test.go

* Removed unnecessary comments

* improved conf code coverage by an amount that is greater than 0!

* improved coverage, but line 144 of conf.go needs a look

* Added unit tests to multus and types, also fixed a bug in conf.go

* increased code coverage in multus.go and conf.go, also added bug fixes and formatting

* hopefully resolved merge conflicts

* addressed all comments in review

* changed 'thejohn' to '_not_type' for readability

* Added network status annotations section to quickstart and added more unit tests

* added more tests to k8sclient.go

* added another test to k8sclient.go

* Added new function to testing.go and cleaned up tests
2019-08-20 13:54:08 -04:00
nicklesimba
9085c84672 Unit tests and update to quickstart guide (#354)
* Added a test for GetLoggingLevel

* Added up to 96% coverage for checkpoint.go

* Improved coverage of checkpoint.go to 96.4%

* Improved coverage of checkpoint.go to 96.4%

* Adding changes so i will have them saved for my remote fork thingy

* Fixed unit tests in checkpoint_test.go and conf_test.go

* Removed unnecessary comments

* improved conf code coverage by an amount that is greater than 0!

* improved coverage, but line 144 of conf.go needs a look

* Added unit tests to multus and types, also fixed a bug in conf.go

* added label to import types/020 in types.go

* hopefully resolved merge conflicts

* increased code coverage in multus.go and conf.go, also added bug fixes and formatting

* addressed all comments in review

* Updated testing.go with better comments

* changed 'thejohn' to '_not_type' for readability

* added additional unit tests

* added tests to kubeletclient.go

* added more unit tests to k8sclient.go and kubeletclient.go

* Added network status annotations section to quickstart and added more unit tests

* made changes to tests based on code review
2019-08-05 15:04:35 -04:00
Tomofumi Hayashi
6e8fac54a0 Increase memory resource in ppc64le case. 2019-07-31 22:03:15 +09:00
Tomofumi Hayashi
587bd8df32 Multi architecture image and CI job
Fix #305
2019-07-30 07:59:30 +09:00
giovanism
3568756adb Implement custom NetworkSelectionElement Unmarshaler
This Unmarshaler bring back support for pre v3.2 "interfaceRequest"
property.

Signed-off-by: giovanism <giovanism@outlook.co.id>
2019-07-30 07:59:05 +09:00
giovanism
b117d61ce6 Update doc mentioning interface selection element
Signed-off-by: giovanism <giovanism@outlook.co.id>
2019-07-30 07:59:05 +09:00
Nikhil
a1b852b5bf hopefully resolved merge conflicts 2019-07-26 22:10:51 +09:00
Nikhil
aeb7870c3f changed 'thejohn' to '_not_type' for readability 2019-07-26 22:10:51 +09:00
Nikhil
3c6812e438 Updated testing.go with better comments 2019-07-26 22:10:51 +09:00
Nikhil
971396edf6 addressed all comments in review 2019-07-26 22:10:51 +09:00
Nikhil
989daf4091 hopefully resolved merge conflicts 2019-07-26 22:10:51 +09:00
Nikhil
d4a7aae89c increased code coverage in multus.go and conf.go, also added bug fixes and formatting 2019-07-26 22:10:51 +09:00
Tomofumi Hayashi
074bd27c18 Add daemonset for crio again
This change introduces multus-daemonset-crio again to support crio.
The change also introduce '--override-network-name' to use previous
master name in CNI json for multus CNI json.
2019-07-01 16:36:43 +09:00
Nikhil
deeb7d9a8f Removed unnecessary comments 2019-06-28 10:15:21 +09:00
Nikhil
f5524e0b9c Fixed unit tests in checkpoint_test.go and conf_test.go 2019-06-28 10:15:21 +09:00
Nikhil
b0e3b05b3c Adding changes so i will have them saved for my remote fork thingy 2019-06-28 10:15:21 +09:00
Nikhil
3853c6c377 Improved coverage of checkpoint.go to 96.4% 2019-06-28 10:15:21 +09:00
Nikhil
a1c575d12e Improved coverage of checkpoint.go to 96.4% 2019-06-28 10:15:21 +09:00
Nikhil
89d3b3e0b5 Added up to 96% coverage for checkpoint.go 2019-06-28 10:15:21 +09:00
Nikhil
22b992ebe3 Added a test for GetLoggingLevel 2019-06-28 10:15:21 +09:00
Tomofumi Hayashi
2fe42c11c7 Fix golint error and make it enable again in travis 2019-06-26 09:30:46 +09:00
Tomofumi Hayashi
33f077ce1b Change .goreleaser.yml to support go module build 2019-06-24 16:50:30 +09:00
Tomofumi Hayashi
d134ac8485 Support GOPATH mode build/test for its transitional situation 2019-06-24 16:50:30 +09:00
Tomofumi Hayashi
ac21a96804 Revert vendor directory to support old golang (GOPATH mode)
gomodule is still in progress to migrate for now, hence multus
team decide to keep vendor directory to support build without
gomodule.
2019-06-24 16:50:30 +09:00
Tomofumi Hayashi
de1c1c78e9 Migrate go modules from glide 2019-06-24 16:50:30 +09:00
Tomofumi Hayashi
df58b74329 Add help text for '--cni-version' 2019-06-21 11:29:11 -04:00
dougbtv
1f8b44c575 changes sleep in docs to example that uses a trap INT 2019-06-10 21:35:15 +09:00
Nikhil
aaaad9d481 Add verbose loggingLevel option to configuration documentation 2019-06-10 21:34:00 +09:00
Tomofumi Hayashi
7a531b5f74 CNIVersion fix for conflist
This change introduces two fix about CNIVersion. One is to add CNIVersion into
delegated CNI conflist in case of DEL if CNIVersion is missing. ParseVersion() in libcni
checks cniVersion as mandatory field and sometimes user/daemonset miss it.
The latest flannel daemonset yaml (of flannel github) does not have CNIVersion, for example.
This change adds CNIVersion from multus config if cniVersion is missing (empty) in delegated
CNI config.

In addition, this fix also adds '--cni-version' in entrypoint.sh to add cniVersion in multus
config in case of '--multus-conf-file=auto'.
2019-05-30 10:01:58 -04:00
Tomofumi Hayashi
f00ac9bfc8 Continue to process cmdDel() in case of no network namespace
K8s with docker runtime, cmdDel() is invoked with empty network
namespace in case of restart node. Currently multus just returns
but CNI spec mention that we should invoke CNI plugin to cleanup.

This PR deletes "return nil" and proceeds to invoke CNI plugins
DEL. Fix #323.
2019-05-30 09:56:44 -04:00
Tomofumi Hayashi
e723aabca8 Update libcni to 0.7.0 (Spec ver 0.4.0) 2019-05-17 06:59:48 +09:00
Zenghui Shi
6c23cad08d add test cases for device id assignment 2019-05-16 10:05:12 -04:00
Zenghui Shi
91d9964d07 assign device id to pciBusID in delegated config
This allows host-device plugin to recognize
Device PCI address passed from Multus.
It is related to the change in host-device which
enables use of device pci address as a config option:
https://github.com/containernetworking/plugins/pull/300
2019-05-16 10:05:12 -04:00
dougbtv
1a32c636ff [entrypoint][docs] Adds --multus-autoconfig-dir and entrypoint documentation 2019-05-16 10:04:26 -04:00
Doug Smith
1d4ac10f3d [docs] Updates the README.md to reflect the need for a default network and removes Flannel reference. 2019-05-16 10:02:47 -04:00
Doug Smith
9b587c6089 [delete] removes flannel and crio daemonset 2019-05-16 10:02:47 -04:00
Doug Smith
ce11203f5c Remove Flannel from default installation method in favor of auto-configuration 2019-05-16 10:02:47 -04:00
Dan Williams
d863864323 entrypoint.sh: add timestamps to log messages; log autogenerated config file
Example:

2019-05-09T15:41:20-05:00 Generating Multus configuration file ...
2019-05-09T15:41:20-05:00 Attemping to find master plugin configuration, attempt 0
2019-05-09T15:41:20-05:00 Attemping to find master plugin configuration, attempt 1
2019-05-09T15:41:20-05:00 Attemping to find master plugin configuration, attempt 10
2019-05-09T15:41:20-05:00 Attemping to find master plugin configuration, attempt 15
2019-05-09T15:41:20-05:00 Attemping to find master plugin configuration, attempt 20
2019-05-09T15:41:20-05:00 Config file created @ /host/etc/cni/net.d/00-multus.conf
{ "name": "multus-cni-network", "type": "multus", "namespaceIsolation": true, "logLevel": "verbose", "kubeconfig": "/etc/kubernetes/cni/net.d/multus.d/multus.kubeconfig", "delegates": [ { "cniVersion": "0.3.1", "name": "openshift-sdn", "type": "openshift-sdn" } ] }
2019-05-09T15:41:20-05:00 Entering sleep... (success)
2019-05-10 09:32:48 -04:00
dougbtv
e6964dc4b4 [bugfix] Skipped clearing the network status annotation if the pod sandbox is not found 2019-05-03 09:46:52 -04:00
dougbtv
bf61002b4c [build] Adds CGO_ENABLED=0 and -tags no_openssl to build script 2019-04-19 00:55:36 +09:00
Tomofumi Hayashi
f11c851d97 Check ConfList in delete network by cache
This change adds ConfList check in get delegates from cache,
to delete network gracefully.
2019-04-07 21:32:35 -07:00
Kahou Lei
69ac1a5935 Rephrase note 2019-04-03 12:29:59 -04:00
Kahou Lei
d7fd3a6770 Add pod cidr indication in quickstart doc
The flannel yaml in the example is using 10.244.0.0/16. If user bootstraps
a k8s cluster with different pod cidr, pod traffic will not go thru the flannel
vxlan tunnel.
2019-04-03 12:29:59 -04:00
Casares, Francisco M
7656080a53 Enable Rolling Update on defined DaemonSets
With RollingUpdate update strategy, after you update a DaemonSet template, old DaemonSet pods will be killed, and new DaemonSet pods will be created automatically, in a controlled fashion.
2019-03-26 18:51:22 +00:00
Abdul Halim
175f7b2f04 fix missing deviceID in NetConfList
This patch fixes the issue described in #289 where deviceID for
delegate plugin was not adding properly if the plugin conf inside
NetConfList.

Change-Id: I1d221f6b0e60a5b888b8e823611dfe12635e6897
Signed-off-by: Abdul Halim <abdul.halim@intel.com>
2019-03-26 12:39:44 +00:00
Abdul Halim
d3c92b4aa2 add kubelet client for Pod resource info
This change introduces kubelet client to get allocated device
information of a Pod from newly added Kubelet grpc service.
For more information please see:
[kubernetes/kubernetes#70508](https://github.com/kubernetes/kubernetes/pull/70508)

Change-Id: I11e58ccdd52662601f445fa24c7d55c225441efc
Signed-off-by: Abdul Halim <abdul.halim@intel.com>
2019-03-22 09:50:53 -04:00
Abdul Halim
8ee7eb335e update vendor dependencies for kubelet client
adding new imported package dependencies in vendor which is required
for Kubelet Pod Resource api client.

Change-Id: If6c74598e12af5f8659df69371e72dd064823f49
2019-03-22 09:50:53 -04:00
dougbtv
c319f6b52c [travis] Updates Travis to tag master builds as :latest, and adds version tagged images to daemonsets 2019-03-22 12:13:54 +09:00
6735 changed files with 706175 additions and 1683956 deletions

24
.github/workflows/build.yml vendored Normal file
View File

@@ -0,0 +1,24 @@
on: [push, pull_request]
name: Build
jobs:
build:
strategy:
matrix:
go-version: [1.17.x, 1.18.x]
goarch: [386, amd64, arm, arm64, ppc64le, s390x]
os: [ubuntu-latest] #, macos-latest, windows-latest]
runs-on: ${{ matrix.os }}
steps:
- name: Install Go
uses: actions/setup-go@v2
with:
go-version: ${{ matrix.go-version }}
- name: Checkout code
uses: actions/checkout@v2
- name: Build
env:
GOARCH: ${{ matrix.goarch }}
GOOS: ${{ matrix.goos }}
run: ./hack/build-go.sh

128
.github/workflows/image-build.yml vendored Normal file
View File

@@ -0,0 +1,128 @@
name: Image build
on: [pull_request]
jobs:
build-amd64:
name: Image build/amd64 thin plugin
runs-on: ubuntu-latest
steps:
- name: Check out code into the Go module directory
uses: actions/checkout@v2
- name: Set up Docker Buildx
uses: docker/setup-buildx-action@v1
- name: Build container image
uses: docker/build-push-action@v2
with:
context: .
push: false
tags: ghcr.io/${{ github.repository }}:latest-amd64
file: images/Dockerfile
build-amd64-thick:
name: Image build/amd64 thick plugin
runs-on: ubuntu-latest
steps:
- name: Check out code into the Go module directory
uses: actions/checkout@v2
- name: Set up Docker Buildx
uses: docker/setup-buildx-action@v1
- name: Build container image
uses: docker/build-push-action@v2
with:
context: .
push: false
tags: ghcr.io/${{ github.repository }}:latest-amd64-thick
file: images/Dockerfile.thick
build-arm64:
name: Image build/arm64
runs-on: ubuntu-latest
steps:
- name: Check out code into the Go module directory
uses: actions/checkout@v2
- name: Set up Docker Buildx
uses: docker/setup-buildx-action@v1
- name: Build container image
uses: docker/build-push-action@v2
with:
context: .
push: false
tags: ghcr.io/${{ github.repository }}:latest-arm64
file: images/Dockerfile.arm64
build-arm32:
name: Image build/arm32
runs-on: ubuntu-latest
steps:
- name: Check out code into the Go module directory
uses: actions/checkout@v2
- name: Set up Docker Buildx
uses: docker/setup-buildx-action@v1
- name: Build container image
uses: docker/build-push-action@v2
with:
context: .
push: false
tags: ghcr.io/${{ github.repository }}:latest-arm32
file: images/Dockerfile.arm32
build-ppc64le:
name: Image build/ppc64le
runs-on: ubuntu-latest
steps:
- name: Check out code into the Go module directory
uses: actions/checkout@v2
- name: Set up Docker Buildx
uses: docker/setup-buildx-action@v1
- name: Build container image
uses: docker/build-push-action@v2
with:
context: .
push: false
tags: ghcr.io/${{ github.repository }}:latest-ppc64le
file: images/Dockerfile.ppc64le
build-s390:
name: Image build/s390x
runs-on: ubuntu-latest
steps:
- name: Check out code into the Go module directory
uses: actions/checkout@v2
- name: Set up Docker Buildx
uses: docker/setup-buildx-action@v1
- name: Build container image
uses: docker/build-push-action@v2
with:
context: .
push: false
tags: ghcr.io/${{ github.repository }}:latest-s390x
file: images/Dockerfile.s390x
build-origin:
name: Image build/origin
runs-on: ubuntu-latest
steps:
- name: Check out code into the Go module directory
uses: actions/checkout@v2
- name: Set up Docker Buildx
uses: docker/setup-buildx-action@v1
- name: Build container image
uses: docker/build-push-action@v2
with:
context: .
push: false
tags: ghcr.io/${{ github.repository }}:latest-origin
file: images/Dockerfile.openshift

255
.github/workflows/image-push-master.yml vendored Normal file
View File

@@ -0,0 +1,255 @@
name: Image push for master
on:
push:
branches:
- master
jobs:
push-amd64:
name: Image push/amd64
runs-on: ubuntu-latest
steps:
- name: Check out code into the Go module directory
uses: actions/checkout@v2
- name: Set up Docker Buildx
uses: docker/setup-buildx-action@v1
- name: Login to GitHub Container Registry
if: github.repository_owner == 'k8snetworkplumbingwg'
uses: docker/login-action@v1
with:
registry: ghcr.io
username: ${{ github.repository_owner }}
password: ${{ secrets.GITHUB_TOKEN }}
- name: Push container image
if: github.repository_owner == 'k8snetworkplumbingwg'
uses: docker/build-push-action@v2
with:
context: .
push: true
tags: |
ghcr.io/${{ github.repository }}:latest-amd64
ghcr.io/${{ github.repository }}:snapshot-amd64
file: images/Dockerfile
- name: Push container image for daemon based deployment
if: github.repository_owner == 'k8snetworkplumbingwg'
uses: docker/build-push-action@v2
with:
context: .
push: true
tags: |
ghcr.io/${{ github.repository }}:latest-thick-amd64
ghcr.io/${{ github.repository }}:snapshot-thick-amd64
file: images/Dockerfile.thick
push-arm64:
name: Image push/arm64
runs-on: ubuntu-latest
steps:
- name: Check out code into the Go module directory
uses: actions/checkout@v2
- name: Set up Docker Buildx
uses: docker/setup-buildx-action@v1
- name: Login to GitHub Container Registry
if: github.repository_owner == 'k8snetworkplumbingwg'
uses: docker/login-action@v1
with:
registry: ghcr.io
username: ${{ github.repository_owner }}
password: ${{ secrets.GITHUB_TOKEN }}
- name: Push container image
if: github.repository_owner == 'k8snetworkplumbingwg'
uses: docker/build-push-action@v2
with:
context: .
push: true
tags: |
ghcr.io/${{ github.repository }}:latest-arm64
ghcr.io/${{ github.repository }}:snapshot-arm64
file: images/Dockerfile.arm64
push-arm32:
name: Image push/arm32
runs-on: ubuntu-latest
steps:
- name: Check out code into the Go module directory
uses: actions/checkout@v2
- name: Set up Docker Buildx
uses: docker/setup-buildx-action@v1
- name: Login to GitHub Container Registry
if: github.repository_owner == 'k8snetworkplumbingwg'
uses: docker/login-action@v1
with:
registry: ghcr.io
username: ${{ github.repository_owner }}
password: ${{ secrets.GITHUB_TOKEN }}
- name: Push container image
if: github.repository_owner == 'k8snetworkplumbingwg'
uses: docker/build-push-action@v2
with:
context: .
push: true
tags: |
ghcr.io/${{ github.repository }}:latest-arm32
ghcr.io/${{ github.repository }}:snapshot-arm32
file: images/Dockerfile.arm32
push-ppc64le:
name: Image push/ppc64le
runs-on: ubuntu-latest
steps:
- name: Check out code into the Go module directory
uses: actions/checkout@v2
- name: Set up Docker Buildx
uses: docker/setup-buildx-action@v1
- name: Login to GitHub Container Registry
if: github.repository_owner == 'k8snetworkplumbingwg'
uses: docker/login-action@v1
with:
registry: ghcr.io
username: ${{ github.repository_owner }}
password: ${{ secrets.GITHUB_TOKEN }}
- name: Push container image
if: github.repository_owner == 'k8snetworkplumbingwg'
uses: docker/build-push-action@v2
with:
context: .
push: true
tags: |
ghcr.io/${{ github.repository }}:latest-ppc64le
ghcr.io/${{ github.repository }}:snapshot-ppc64le
file: images/Dockerfile.ppc64le
push-s390x:
name: Image push/s390x
runs-on: ubuntu-latest
steps:
- name: Check out code into the Go module directory
uses: actions/checkout@v2
- name: Set up Docker Buildx
uses: docker/setup-buildx-action@v1
- name: Login to GitHub Container Registry
if: github.repository_owner == 'k8snetworkplumbingwg'
uses: docker/login-action@v1
with:
registry: ghcr.io
username: ${{ github.repository_owner }}
password: ${{ secrets.GITHUB_TOKEN }}
- name: Push container image
if: github.repository_owner == 'k8snetworkplumbingwg'
uses: docker/build-push-action@v2
with:
context: .
push: true
tags: |
ghcr.io/${{ github.repository }}:latest-s390x
ghcr.io/${{ github.repository }}:snapshot-s390x
file: images/Dockerfile.s390x
push-origin:
name: Image push/origin
runs-on: ubuntu-latest
steps:
- name: Check out code into the Go module directory
uses: actions/checkout@v2
- name: Set up Docker Buildx
uses: docker/setup-buildx-action@v1
- name: Login to GitHub Container Registry
if: github.repository_owner == 'k8snetworkplumbingwg'
uses: docker/login-action@v1
with:
registry: ghcr.io
username: ${{ github.repository_owner }}
password: ${{ secrets.GITHUB_TOKEN }}
- name: Push container image
if: github.repository_owner == 'k8snetworkplumbingwg'
uses: docker/build-push-action@v2
with:
context: .
push: true
tags: |
ghcr.io/${{ github.repository }}:latest-origin
ghcr.io/${{ github.repository }}:snapshot-origin
file: images/Dockerfile.openshift
push-manifest:
needs: [push-amd64, push-arm64, push-ppc64le, push-s390x]
runs-on: ubuntu-latest
env:
REPOSITORY: ghcr.io/${{ github.repository }}
steps:
- name: Set up Docker Buildx
uses: docker/setup-buildx-action@v1
- name: Login to GitHub Container Registry
if: github.repository_owner == 'k8snetworkplumbingwg'
uses: docker/login-action@v1
with:
registry: ghcr.io
username: ${{ github.repository_owner }}
password: ${{ secrets.GITHUB_TOKEN }}
- name: Create manifest for multi-arch images
if: github.repository_owner == 'k8snetworkplumbingwg'
run: |
# snapshot-thick
# get artifacts from previous steps
docker pull ${{ env.REPOSITORY }}:snapshot-thick-amd64
docker manifest create ${{ env.REPOSITORY }}:snapshot-thick ${{ env.REPOSITORY }}:snapshot-thick-amd64
docker manifest annotate ${{ env.REPOSITORY }}:snapshot-thick ${{ env.REPOSITORY }}:snapshot-thick-amd64 --arch amd64
docker manifest push ${{ env.REPOSITORY }}:snapshot-thick
# latest-thick
# get artifacts from previous steps
docker pull ${{ env.REPOSITORY }}:latest-thick-amd64
docker manifest create ${{ env.REPOSITORY }}:latest-thick ${{ env.REPOSITORY }}:latest-thick-amd64
docker manifest annotate ${{ env.REPOSITORY }}:latest-thick ${{ env.REPOSITORY }}:latest-thick-amd64 --arch amd64
docker manifest push ${{ env.REPOSITORY }}:latest-thick
# snapshot
# get artifacts from previous steps
docker pull ${{ env.REPOSITORY }}:snapshot-amd64
docker pull ${{ env.REPOSITORY }}:snapshot-arm64
docker pull ${{ env.REPOSITORY }}:snapshot-arm32
docker pull ${{ env.REPOSITORY }}:snapshot-ppc64le
docker pull ${{ env.REPOSITORY }}:snapshot-s390x
docker manifest create ${{ env.REPOSITORY }}:snapshot ${{ env.REPOSITORY }}:snapshot-amd64 ${{ env.REPOSITORY }}:snapshot-arm64 ${{ env.REPOSITORY }}:snapshot-arm32 ${{ env.REPOSITORY }}:snapshot-ppc64le ${{ env.REPOSITORY }}:snapshot-s390x
docker manifest annotate ${{ env.REPOSITORY }}:snapshot ${{ env.REPOSITORY }}:snapshot-amd64 --arch amd64
docker manifest annotate ${{ env.REPOSITORY }}:snapshot ${{ env.REPOSITORY }}:snapshot-arm64 --arch arm64
docker manifest annotate ${{ env.REPOSITORY }}:snapshot ${{ env.REPOSITORY }}:snapshot-arm32 --arch arm
docker manifest annotate ${{ env.REPOSITORY }}:snapshot ${{ env.REPOSITORY }}:snapshot-ppc64le --arch ppc64le
docker manifest annotate ${{ env.REPOSITORY }}:snapshot ${{ env.REPOSITORY }}:snapshot-s390x --arch s390x
docker manifest push ${{ env.REPOSITORY }}:snapshot
# latest
# get artifacts from previous steps
docker pull ${{ env.REPOSITORY }}:latest-amd64
docker pull ${{ env.REPOSITORY }}:latest-arm64
docker pull ${{ env.REPOSITORY }}:latest-arm32
docker pull ${{ env.REPOSITORY }}:latest-ppc64le
docker pull ${{ env.REPOSITORY }}:latest-s390x
docker manifest create ${{ env.REPOSITORY }}:latest ${{ env.REPOSITORY }}:latest-amd64 ${{ env.REPOSITORY }}:latest-arm64 ${{ env.REPOSITORY }}:latest-arm32 ${{ env.REPOSITORY }}:latest-ppc64le ${{ env.REPOSITORY }}:latest-s390x
docker manifest annotate ${{ env.REPOSITORY }}:latest ${{ env.REPOSITORY }}:latest-amd64 --arch amd64
docker manifest annotate ${{ env.REPOSITORY }}:latest ${{ env.REPOSITORY }}:latest-arm64 --arch arm64
docker manifest annotate ${{ env.REPOSITORY }}:latest ${{ env.REPOSITORY }}:latest-arm32 --arch arm
docker manifest annotate ${{ env.REPOSITORY }}:latest ${{ env.REPOSITORY }}:latest-ppc64le --arch ppc64le
docker manifest annotate ${{ env.REPOSITORY }}:latest ${{ env.REPOSITORY }}:latest-s390x --arch s390x
docker manifest push ${{ env.REPOSITORY }}:latest

303
.github/workflows/image-push-release.yml vendored Normal file
View File

@@ -0,0 +1,303 @@
name: Image push release
on:
push:
tags:
- v*
jobs:
push-amd64:
name: Image push/amd64
runs-on: ubuntu-latest
steps:
- name: Check out code into the Go module directory
uses: actions/checkout@v2
- name: Set up Docker Buildx
uses: docker/setup-buildx-action@v1
- name: Login to GitHub Container Registry
if: github.repository_owner == 'k8snetworkplumbingwg'
uses: docker/login-action@v1
with:
registry: ghcr.io
username: ${{ github.repository_owner }}
password: ${{ secrets.GITHUB_TOKEN }}
- name: Docker meta
id: docker_meta
uses: crazy-max/ghaction-docker-meta@v1
with:
images: ghcr.io/${{ github.repository }}
tag-latest: false
- name: Push container image
if: github.repository_owner == 'k8snetworkplumbingwg'
uses: docker/build-push-action@v2
with:
context: .
push: true
tags: |
ghcr.io/${{ github.repository }}:stable-amd64
${{ steps.docker_meta.outputs.tags }}-amd64
file: images/Dockerfile
- name: Push container image for daemon based deployment
if: github.repository_owner == 'k8snetworkplumbingwg'
uses: docker/build-push-action@v2
with:
context: .
push: true
tags: |
ghcr.io/${{ github.repository }}:stable-thick-amd64
${{ steps.docker_meta.outputs.tags }}-thick-amd64
file: images/Dockerfile.thick
push-arm64:
name: Image push/arm64
runs-on: ubuntu-latest
steps:
- name: Check out code into the Go module directory
uses: actions/checkout@v2
- name: Set up Docker Buildx
uses: docker/setup-buildx-action@v1
- name: Login to GitHub Container Registry
if: github.repository_owner == 'k8snetworkplumbingwg'
uses: docker/login-action@v1
with:
registry: ghcr.io
username: ${{ github.repository_owner }}
password: ${{ secrets.GITHUB_TOKEN }}
- name: Docker meta
id: docker_meta
uses: crazy-max/ghaction-docker-meta@v1
with:
images: ghcr.io/${{ github.repository }}
tag-latest: false
- name: Push container image
if: github.repository_owner == 'k8snetworkplumbingwg'
uses: docker/build-push-action@v2
with:
context: .
push: true
tags: |
ghcr.io/${{ github.repository }}:stable-arm64
${{ steps.docker_meta.outputs.tags }}-arm64
file: images/Dockerfile.arm64
push-arm32:
name: Image push/arm32
runs-on: ubuntu-latest
steps:
- name: Check out code into the Go module directory
uses: actions/checkout@v2
- name: Set up Docker Buildx
uses: docker/setup-buildx-action@v1
- name: Login to GitHub Container Registry
if: github.repository_owner == 'k8snetworkplumbingwg'
uses: docker/login-action@v1
with:
registry: ghcr.io
username: ${{ github.repository_owner }}
password: ${{ secrets.GITHUB_TOKEN }}
- name: Docker meta
id: docker_meta
uses: crazy-max/ghaction-docker-meta@v1
with:
images: ghcr.io/${{ github.repository }}
tag-latest: false
- name: Push container image
if: github.repository_owner == 'k8snetworkplumbingwg'
uses: docker/build-push-action@v2
with:
context: .
push: true
tags: |
ghcr.io/${{ github.repository }}:stable-arm32
${{ steps.docker_meta.outputs.tags }}-arm32
file: images/Dockerfile.arm32
push-ppc64le:
name: Image push/ppc64le
runs-on: ubuntu-latest
steps:
- name: Check out code into the Go module directory
uses: actions/checkout@v2
- name: Set up Docker Buildx
uses: docker/setup-buildx-action@v1
- name: Login to GitHub Container Registry
if: github.repository_owner == 'k8snetworkplumbingwg'
uses: docker/login-action@v1
with:
registry: ghcr.io
username: ${{ github.repository_owner }}
password: ${{ secrets.GITHUB_TOKEN }}
- name: Docker meta
id: docker_meta
uses: crazy-max/ghaction-docker-meta@v1
with:
images: ghcr.io/${{ github.repository }}
tag-latest: false
- name: Push container image
if: github.repository_owner == 'k8snetworkplumbingwg'
uses: docker/build-push-action@v2
with:
context: .
push: true
tags: |
ghcr.io/${{ github.repository }}:stable-ppc64le
${{ steps.docker_meta.outputs.tags }}-ppc64le
file: images/Dockerfile.ppc64le
push-s390x:
name: Image push/s390x
runs-on: ubuntu-latest
steps:
- name: Check out code into the Go module directory
uses: actions/checkout@v2
- name: Set up Docker Buildx
uses: docker/setup-buildx-action@v1
- name: Login to GitHub Container Registry
if: github.repository_owner == 'k8snetworkplumbingwg'
uses: docker/login-action@v1
with:
registry: ghcr.io
username: ${{ github.repository_owner }}
password: ${{ secrets.GITHUB_TOKEN }}
- name: Docker meta
id: docker_meta
uses: crazy-max/ghaction-docker-meta@v1
with:
images: ghcr.io/${{ github.repository }}
tag-latest: false
- name: Push container image
if: github.repository_owner == 'k8snetworkplumbingwg'
uses: docker/build-push-action@v2
with:
context: .
push: true
tags: |
ghcr.io/${{ github.repository }}:stable-s390x
${{ steps.docker_meta.outputs.tags }}-s390x
file: images/Dockerfile.s390x
push-origin:
name: Image push/origin
runs-on: ubuntu-latest
steps:
- name: Check out code into the Go module directory
uses: actions/checkout@v2
- name: Set up Docker Buildx
uses: docker/setup-buildx-action@v1
- name: Login to GitHub Container Registry
if: github.repository_owner == 'k8snetworkplumbingwg'
uses: docker/login-action@v1
with:
registry: ghcr.io
username: ${{ github.repository_owner }}
password: ${{ secrets.GITHUB_TOKEN }}
- name: Docker meta
id: docker_meta
uses: crazy-max/ghaction-docker-meta@v1
with:
images: ghcr.io/${{ github.repository }}
tag-latest: false
- name: Push container image
if: github.repository_owner == 'k8snetworkplumbingwg'
uses: docker/build-push-action@v2
with:
context: .
push: true
tags: |
ghcr.io/${{ github.repository }}:stable-origin
${{ steps.docker_meta.outputs.tags }}-origin
file: images/Dockerfile.openshift
push-manifest:
needs: [push-amd64, push-arm64, push-ppc64le, push-s390x]
runs-on: ubuntu-latest
env:
REPOSITORY: ghcr.io/${{ github.repository }}
steps:
- name: Set up Docker Buildx
uses: docker/setup-buildx-action@v1
- name: Docker meta
id: docker_meta
uses: crazy-max/ghaction-docker-meta@v1
with:
images: ghcr.io/${{ github.repository }}
tag-latest: false
- name: Login to GitHub Container Registry
if: github.repository_owner == 'k8snetworkplumbingwg'
uses: docker/login-action@v1
with:
registry: ghcr.io
username: ${{ github.repository_owner }}
password: ${{ secrets.GITHUB_TOKEN }}
- name: Create manifest for multi-arch images
if: github.repository_owner == 'k8snetworkplumbingwg'
run: |
# <tag>-thick
# get artifacts from previous steps
docker pull ${{ steps.docker_meta.outputs.tags }}-thick-amd64
docker manifest create ${{ steps.docker_meta.outputs.tags }}-thick ${{ steps.docker_meta.outputs.tags }}-thick-amd64
docker manifest annotate ${{ steps.docker_meta.outputs.tags }}-thick ${{ steps.docker_meta.outputs.tags }}-thick-amd64 --arch amd64
docker manifest push ${{ steps.docker_meta.outputs.tags }}-thick
# stable-thick
# get artifacts from previous steps
docker pull ${{ env.REPOSITORY }}:stable-thick-amd64
docker manifest create ${{ env.REPOSITORY }}:stable-thick ${{ env.REPOSITORY }}:stable-thick-amd64
docker manifest annotate ${{ env.REPOSITORY }}:stable-thick ${{ env.REPOSITORY }}:stable-thick-amd64 --arch amd64
docker manifest push ${{ env.REPOSITORY }}:stable-thick
# <tag>
# get artifacts from previous steps
docker pull ${{ steps.docker_meta.outputs.tags }}-amd64
docker pull ${{ steps.docker_meta.outputs.tags }}-arm64
docker pull ${{ steps.docker_meta.outputs.tags }}-arm32
docker pull ${{ steps.docker_meta.outputs.tags }}-ppc64le
docker pull ${{ steps.docker_meta.outputs.tags }}-s390x
docker manifest create ${{ steps.docker_meta.outputs.tags }} ${{ steps.docker_meta.outputs.tags }}-amd64 ${{ steps.docker_meta.outputs.tags }}-arm64 ${{ steps.docker_meta.outputs.tags }}-arm32 ${{ steps.docker_meta.outputs.tags }}-ppc64le ${{ steps.docker_meta.outputs.tags }}-s390x
docker manifest annotate ${{ steps.docker_meta.outputs.tags }} ${{ steps.docker_meta.outputs.tags }}-amd64 --arch amd64
docker manifest annotate ${{ steps.docker_meta.outputs.tags }} ${{ steps.docker_meta.outputs.tags }}-arm64 --arch arm64
docker manifest annotate ${{ steps.docker_meta.outputs.tags }} ${{ steps.docker_meta.outputs.tags }}-arm32 --arch arm
docker manifest annotate ${{ steps.docker_meta.outputs.tags }} ${{ steps.docker_meta.outputs.tags }}-ppc64le --arch ppc64le
docker manifest annotate ${{ steps.docker_meta.outputs.tags }} ${{ steps.docker_meta.outputs.tags }}-s390x --arch s390x
docker manifest push ${{ steps.docker_meta.outputs.tags }}
# stable
# get artifacts from previous steps
docker pull ${{ env.REPOSITORY }}:stable-amd64
docker pull ${{ env.REPOSITORY }}:stable-arm64
docker pull ${{ env.REPOSITORY }}:stable-arm32
docker pull ${{ env.REPOSITORY }}:stable-ppc64le
docker pull ${{ env.REPOSITORY }}:stable-s390x
docker manifest create ${{ env.REPOSITORY }}:stable ${{ env.REPOSITORY }}:stable-amd64 ${{ env.REPOSITORY }}:stable-arm64 ${{ env.REPOSITORY }}:stable-arm32 ${{ env.REPOSITORY }}:stable-ppc64le ${{ env.REPOSITORY }}:stable-s390x
docker manifest annotate ${{ env.REPOSITORY }}:stable ${{ env.REPOSITORY }}:stable-amd64 --arch amd64
docker manifest annotate ${{ env.REPOSITORY }}:stable ${{ env.REPOSITORY }}:stable-arm64 --arch arm64
docker manifest annotate ${{ env.REPOSITORY }}:stable ${{ env.REPOSITORY }}:stable-arm32 --arch arm
docker manifest annotate ${{ env.REPOSITORY }}:stable ${{ env.REPOSITORY }}:stable-ppc64le --arch ppc64le
docker manifest annotate ${{ env.REPOSITORY }}:stable ${{ env.REPOSITORY }}:stable-s390x --arch s390x
docker manifest push ${{ env.REPOSITORY }}:stable

87
.github/workflows/kind-e2e.yml vendored Normal file
View File

@@ -0,0 +1,87 @@
name: e2e-kind
on: [push, pull_request]
jobs:
e2e-kind:
runs-on: ubuntu-latest
strategy:
matrix:
include:
- docker-file: images/Dockerfile.thick
cni-version: "0.3.1"
multus-manifest: multus-daemonset-thick.yml
- docker-file: images/Dockerfile
cni-version: "0.3.1"
multus-manifest: multus-daemonset.yml
- docker-file: images/Dockerfile.thick
cni-version: "0.4.0"
multus-manifest: multus-daemonset-thick.yml
- docker-file: images/Dockerfile
cni-version: "0.4.0"
multus-manifest: multus-daemonset.yml
# need to wait kind to support CNI 1.0.0 (now kind 0.11 supports up to 0.4.0)
# - docker-file: images/Dockerfile.thick
# cni-version: "1.0.0"
# multus-manifest: multus-thick-daemonset.yml
# - docker-file: images/Dockerfile
# cni-version: "1.0.0"
# multus-manifest: multus-daemonset.yml
if: >
(( github.event.pull_request.head.repo.owner.login != github.event.pull_request.base.repo.owner.login ) &&
github.event_name == 'pull_request' ) || (github.event_name == 'push' && github.event.commits != '[]' )
steps:
- name: Check out code into the Go module directory
uses: actions/checkout@v2
- name: Setup python
uses: actions/setup-python@v2
with:
python-version: 3.x
- name: Setup j2cli
run: |
pip3 install --user --upgrade j2cli
j2 --version
- name: Setup registry
run: docker run -d --restart=always -p "5000:5000" --name "kind-registry" registry:2
- name: Build latest-amd64
run: docker build -t localhost:5000/multus:e2e -f ${{ matrix.docker-file }} .
- name: Push to local registry
run: docker push localhost:5000/multus:e2e
- name: Get kind/kubectl/koko
working-directory: ./e2e
run: ./get_tools.sh
- name: generate yaml files
working-directory: ./e2e
run: env CNI_VERSION=${{ matrix.cni-version }} ./generate_yamls.sh
- name: Setup cluster
working-directory: ./e2e
run: MULTUS_MANIFEST=${{ matrix.multus-manifest }} ./setup_cluster.sh
- name: Test simple pod
working-directory: ./e2e
run: ./test-simple-pod.sh
- name: Test macvlan1
working-directory: ./e2e
run: ./test-simple-macvlan1.sh
- name: Test static pod
working-directory: ./e2e
run: ./test-static-pod.sh
- name: Test default route1
working-directory: ./e2e
run: ./test-default-route1.sh
- name: cleanup cluster and registry
run: |
kind delete cluster
docker kill kind-registry
docker rm kind-registry

26
.github/workflows/release.yml vendored Normal file
View File

@@ -0,0 +1,26 @@
name: Release binaries
on:
push:
tags:
- 'v*'
jobs:
goreleaser:
runs-on: ubuntu-latest
steps:
- name: Checkout
uses: actions/checkout@v2
with:
fetch-depth: 0
- name: Set up Go
uses: actions/setup-go@v2
with:
go-version: 1.17.x
- name: Run GoReleaser
uses: goreleaser/goreleaser-action@v2
with:
version: latest
args: release --rm-dist
env:
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}

15
.github/workflows/stale-issues-prs.yml vendored Normal file
View File

@@ -0,0 +1,15 @@
name: 'Close stale issues and PRs'
on:
schedule:
- cron: '30 1 * * *'
jobs:
stale:
runs-on: ubuntu-latest
steps:
- uses: actions/stale@v3
with:
stale-issue-message: 'This issue is stale because it has been open 90 days with no activity. Remove stale label or comment or this will be closed in 7 days.'
stale-pr-message: 'This pull request is stale because it has been open 90 days with no activity. Remove stale label or comment or this will be closed in 7 days.'
days-before-stale: 90
days-before-close: 7

48
.github/workflows/test.yml vendored Normal file
View File

@@ -0,0 +1,48 @@
on: [push, pull_request]
name: Test
jobs:
test:
strategy:
matrix:
go-version: [1.17.x, 1.18.x]
os: [ubuntu-latest]
runs-on: ${{ matrix.os }}
steps:
- name: Install Go
uses: actions/setup-go@v2
with:
go-version: ${{ matrix.go-version }}
- name: Checkout code
uses: actions/checkout@v2
- name: Run Revive Action by pulling pre-built image
uses: docker://morphy/revive-action:v2
with:
exclude: "./vendor/..."
- name: Run go fmt
run: go fmt ./...
#run: diff -u <(echo -n) <(gofmt -d -s .)
- name: Run go vet
run: go vet ./...
- name: Test
run: sudo ./hack/test-go.sh
- name: Send coverage
uses: shogo82148/actions-goveralls@v1
with:
path-to-profile: coverage.out
flag-name: Go-${{ matrix.go }}
parallel: true
# notifies that all test jobs are finished.
finish:
needs: test
runs-on: ubuntu-latest
steps:
- uses: shogo82148/actions-goveralls@v1
with:
parallel-finished: true

7
.gitignore vendored
View File

@@ -1,9 +1,16 @@
# Binary output dir
bin/
e2e/bin/
e2e/yamls/
# GOPATH created by the build script
gopath/
# Editor paths
.swp*
.swo*
.idea*
# Test outputs
*.out
*.test

View File

@@ -1,10 +1,15 @@
# This is an example goreleaser.yaml file with some sane defaults.
# Make sure to check the documentation at http://goreleaser.com
env:
- GO111MODULE=on
before:
hooks:
- go mod download
builds:
-
env:
- CGO_ENABLED=0
main: ./multus/
main: ./cmd/
goos:
- linux
goarch:
@@ -12,11 +17,16 @@ builds:
- amd64
- arm
- arm64
archive:
wrap_in_directory: true
- s390x
ldflags:
- -X gopkg.in/k8snetworkplumbingwg/multus-cni.v3/pkg/multus.version={{ .Tag }} -X gopkg.in/k8snetworkplumbingwg/multus-cni.v3/pkg/multus.commit={{ .Commit }} -X gopkg.in/k8snetworkplumbingwg/multus-cni.v3/pkg/multus.date={{ .Date }}
archives:
- wrap_in_directory: true
checksum:
name_template: 'checksums.txt'
snapshot:
name_template: "{{ .Tag }}-snapshot"
release:
draft: true
#release:
# draft: true
changelog:
skip: true

View File

@@ -1,20 +1,31 @@
os: linux
language: go
# see https://docs.travis-ci.com/user/reference/overview/#Virtualization-environments
# for the detail
# sudo: requried
dist: trusty
dist: bionic
services:
- docker
go:
- 1.11.x
- 1.13.x
env:
global:
- REGISTRY_USER=${REGISTRY_USER}
- GO111MODULE=on
- REGISTRY_USER=${REGISTRY_USER:-nfvpe}
- REGISTRY_PASS=${REGISTRY_PASS}
- MULTUS_GOPATH=${PWD}/gopath
- REPOSITORY_NAME=${REPOSITORY_NAME}
- REPOSITORY_USER=${REPOSITORY_USER}
- DOCKER_CLI_EXPERIMENTAL="enabled"
- secure: "${REGISTRY_SECURE}"
jobs:
- TARGET=amd64
- TARGET=ppc64le
before_install:
- if [ "${REPOSITORY_NAME}" = "" ]; then export REPOSITORY_NAME=multus; fi
- sudo apt-get update -qq
- go get github.com/mattn/goveralls
@@ -23,66 +34,83 @@ install:
before_script:
# Make gopath... to run golint/go fmt/go vet
- |-
if [ ! -h gopath/src/github.com/intel/multus-cni ]; then
mkdir -p gopath/src/github.com/intel
ln -s ../../../.. gopath/src/github.com/intel/multus-cni || exit 255
fi
- env GOPATH=${MULTUS_GOPATH} golint gopath/src/github.com/intel/multus-cni/multus/... | grep -v ALL_CAPS | xargs -r false
- env GOPATH=${MULTUS_GOPATH} go fmt gopath/src/github.com/intel/multus-cni/...
- go tool vet */*.go
# Suppress golint for fixing lint later.
- golint ./... | grep -v vendor | grep -v ALL_CAPS | xargs -r false
- go fmt ./...
- go vet ./...
# - gocyclo -over 15 ./multus
script:
- ./build
- sudo ./test.sh
- |-
GOV_GOPATH=${PWD}/gopath
pushd gopath/src/github.com/intel/multus-cni
env GOPATH=${GOV_GOPATH} ${GOPATH}/bin/goveralls -coverprofile=coverage.out -service=travis-ci
popd
- mkdir -p ${TRAVIS_BUILD_DIR}/dist
- tar cvfz ${TRAVIS_BUILD_DIR}/dist/multus-cni_amd64.tar.gz --warning=no-file-changed --exclude="dist" --exclude="vendor" .
- docker build -t nfvpe/multus .
- GOARCH="${TARGET}" ./hack/build-go.sh
- |
if [ "${TARGET}" == "amd64" ]; then
sudo env PATH=${PATH} ./scripts/test.sh
goveralls -coverprofile=coverage.out -service=travis-ci
docker build -t ${REPOSITORY_USER}/${REPOSITORY_NAME}:latest-amd64 .
docker build -t ${REPOSITORY_USER}/${REPOSITORY_NAME}:latest-ppc64le -f Dockerfile.ppc64le .
docker build -t ${REPOSITORY_USER}/${REPOSITORY_NAME}-origin:latest -f Dockerfile.openshift .
fi
deploy:
# Release on versioned tag (e.g. v1.0)
- provider: script
skip_cleanup: true
script: curl -sL https://git.io/goreleaser | bash
#cleanup: false
script: curl -sL https://git.io/goreleaser
on:
tags: true
all_branches: true
condition: "$TRAVIS_TAG =~ ^v[0-9].*$"
condition: "$TARGET = amd64 && $TRAVIS_TAG =~ ^v[0-9].*$ && ! -z $GITHUB_TOKEN && $TRAVIS_OS_NAME = linux"
# Push images to Dockerhub on tag
- provider: script
cleanup: false
script: >
bash -c '
docker tag nfvpe/multus nfvpe/multus:$TRAVIS_TAG;
docker tag ${REPOSITORY_USER}/${REPOSITORY_NAME}:latest-amd64 ${REPOSITORY_USER}/${REPOSITORY_NAME}:latest;
docker tag ${REPOSITORY_USER}/${REPOSITORY_NAME}:latest-amd64 ${REPOSITORY_USER}/${REPOSITORY_NAME}:stable;
docker tag ${REPOSITORY_USER}/${REPOSITORY_NAME}:latest-amd64 ${REPOSITORY_USER}/${REPOSITORY_NAME}:stable-amd64;
docker tag ${REPOSITORY_USER}/${REPOSITORY_NAME}:latest-amd64 ${REPOSITORY_USER}/${REPOSITORY_NAME}:$TRAVIS_TAG;
docker tag ${REPOSITORY_USER}/${REPOSITORY_NAME}:latest-ppc64le ${REPOSITORY_USER}/${REPOSITORY_NAME}:stable-ppc64le;
docker login -u "$REGISTRY_USER" -p "$REGISTRY_PASS";
docker push nfvpe/multus;
docker push nfvpe/multus:$TRAVIS_TAG;
echo foo'
docker push ${REPOSITORY_USER}/${REPOSITORY_NAME}:latest-amd64;
docker push ${REPOSITORY_USER}/${REPOSITORY_NAME}:latest-ppc64le;
docker push ${REPOSITORY_USER}/${REPOSITORY_NAME}:stable-amd64;
docker push ${REPOSITORY_USER}/${REPOSITORY_NAME}:stable-ppc64le;
docker push ${REPOSITORY_USER}/${REPOSITORY_NAME}:$TRAVIS_TAG;
export DOCKER_CLI_EXPERIMENTAL="enabled";
docker manifest create ${REPOSITORY_USER}/${REPOSITORY_NAME}:latest ${REPOSITORY_USER}/${REPOSITORY_NAME}:latest-amd64 ${REPOSITORY_USER}/${REPOSITORY_NAME}:latest-ppc64le;
docker manifest annotate ${REPOSITORY_USER}/${REPOSITORY_NAME}:latest ${REPOSITORY_USER}/${REPOSITORY_NAME}:latest-amd64 --arch amd64;
docker manifest annotate ${REPOSITORY_USER}/${REPOSITORY_NAME}:latest ${REPOSITORY_USER}/${REPOSITORY_NAME}:latest-ppc64le --arch ppc64le;
docker manifest push ${REPOSITORY_USER}/${REPOSITORY_NAME}:latest;
docker manifest create ${REPOSITORY_USER}/${REPOSITORY_NAME}:stable ${REPOSITORY_USER}/${REPOSITORY_NAME}:stable-amd64 ${REPOSITORY_USER}/${REPOSITORY_NAME}:stable-ppc64le;
docker manifest annotate ${REPOSITORY_USER}/${REPOSITORY_NAME}:stable ${REPOSITORY_USER}/${REPOSITORY_NAME}:stable-amd64 --arch amd64;
docker manifest annotate ${REPOSITORY_USER}/${REPOSITORY_NAME}:stable ${REPOSITORY_USER}/${REPOSITORY_NAME}:stable-ppc64le --arch ppc64le;
docker manifest push ${REPOSITORY_USER}/${REPOSITORY_NAME}:stable;
echo done'
on:
tags: true
all_branches: true
condition: "$TRAVIS_TAG =~ ^v[0-9].*$"
condition: "$TRAVIS_TAG =~ ^v[0-9].*$ && -n $REGISTRY_USER && -n $REGISTRY_PASS && -n $REPOSITORY_NAME && -n $REPOSITORY_USER"
# Push images to Dockerhub on merge to master
- provider: script
on:
branch: master
condition: "-n $REGISTRY_USER && -n $REGISTRY_PASS && -n $REPOSITORY_NAME && -n $REPOSITORY_USER"
script: >
bash -c '
docker tag nfvpe/multus nfvpe/multus:snapshot;
docker tag ${REPOSITORY_USER}/:latest-amd64 ${REPOSITORY_USER}/${REPOSITORY_NAME}:snapshot;
docker tag ${REPOSITORY_USER}/${REPOSITORY_NAME}:latest-amd64 ${REPOSITORY_USER}/${REPOSITORY_NAME}:snapshot-amd64;
docker tag ${REPOSITORY_USER}/${REPOSITORY_NAME}:latest-ppc64le ${REPOSITORY_USER}/${REPOSITORY_NAME}:snapshot-ppc64le;
docker login -u "$REGISTRY_USER" -p "$REGISTRY_PASS";
docker push nfvpe/multus:snapshot;
echo foo'
after_success:
# put build tgz to bintray
- curl -T ${TRAVIS_BUILD_DIR}/dist/multus-cni_amd64.tar.gz -u${BINTRAY_USER}:${BINTRAY_APIKEY} https://api.bintray.com/content/redhat-nfvpe/multus-cni-crd-snapshots/snapshot/snapshot-${TRAVIS_COMMIT}/multus-cni_amd64-${TRAVIS_COMMIT}.tar.gz
# publish uploaded file
- curl -X POST -u${BINTRAY_USER}:${BINTRAY_APIKEY} https://api.bintray.com/content/redhat-nfvpe/multus-cni-crd-snapshots/snapshot/snapshot-${TRAVIS_COMMIT}/publish
# put it in bintray download list
- sleep 20
- "curl -X PUT -H 'Accept: application/json' -H 'Content-type: application/json' -u${BINTRAY_USER}:${BINTRAY_APIKEY} https://api.bintray.com/file_metadata/redhat-nfvpe/multus-cni-crd-snapshots/multus-cni_amd64-${TRAVIS_COMMIT}.tar.gz -d '{\"list_in_downloads\":true}'"
docker push ${REPOSITORY_USER}/${REPOSITORY_NAME}:snapshot-amd64;
docker push ${REPOSITORY_USER}/${REPOSITORY_NAME}:snapshot-ppc64le;
docker push ${REPOSITORY_USER}/${REPOSITORY_NAME}:latest-amd64;
docker push ${REPOSITORY_USER}/${REPOSITORY_NAME}:latest-ppc64le;
docker manifest create ${REPOSITORY_USER}/${REPOSITORY_NAME}:snapshot ${REPOSITORY_USER}/${REPOSITORY_NAME}:snapshot-amd64 ${REPOSITORY_USER}/${REPOSITORY_NAME}:snapshot-ppc64le;
docker manifest annotate ${REPOSITORY_USER}/${REPOSITORY_NAME}:snapshot ${REPOSITORY_USER}/${REPOSITORY_NAME}:snapshot-amd64 --arch amd64;
docker manifest annotate ${REPOSITORY_USER}/${REPOSITORY_NAME}:snapshot ${REPOSITORY_USER}/${REPOSITORY_NAME}:snapshot-ppc64le --arch ppc64le;
docker manifest push ${REPOSITORY_USER}/${REPOSITORY_NAME}:snapshot;
docker manifest create ${REPOSITORY_USER}/${REPOSITORY_NAME}:latest ${REPOSITORY_USER}/${REPOSITORY_NAME}:latest-amd64 ${REPOSITORY_USER}/${REPOSITORY_NAME}:latest-ppc64le;
docker manifest annotate ${REPOSITORY_USER}/${REPOSITORY_NAME}:latest ${REPOSITORY_USER}/${REPOSITORY_NAME}:latest-amd64 --arch amd64;
docker manifest annotate ${REPOSITORY_USER}/${REPOSITORY_NAME}:latest ${REPOSITORY_USER}/${REPOSITORY_NAME}:latest-ppc64le --arch ppc64le;
docker manifest push ${REPOSITORY_USER}/${REPOSITORY_NAME}:latest;
echo done'

130
CODE_OF_CONDUCT.md Normal file
View File

@@ -0,0 +1,130 @@
# Multus CNI Contributor Covenant Code of Conduct
## Our Pledge
We as members, contributors, and leaders pledge to make participation in our
community a harassment-free experience for everyone, regardless of age, body
size, visible or invisible disability, ethnicity, sex characteristics, gender
identity and expression, level of experience, education, socio-economic status,
nationality, personal appearance, race, religion, or sexual identity
and orientation.
We pledge to act and interact in ways that contribute to an open, welcoming,
diverse, inclusive, and healthy community.
## Our Standards
Examples of behavior that contributes to a positive environment for our
community include:
* Demonstrating empathy and kindness toward other people
* Being respectful of differing opinions, viewpoints, and experiences
* Giving and gracefully accepting constructive feedback
* Accepting responsibility and apologizing to those affected by our mistakes,
and learning from the experience
* Focusing on what is best not just for us as individuals, but for the
overall community
Examples of unacceptable behavior include:
* The use of sexualized language or imagery, and sexual attention or
advances of any kind
* Trolling, insulting or derogatory comments, and personal or political attacks
* Public or private harassment
* Publishing others' private information, such as a physical or email
address, without their explicit permission
* Other conduct which could reasonably be considered inappropriate in a
professional setting
## Enforcement Responsibilities
Community leaders are responsible for clarifying and enforcing our standards of
acceptable behavior and will take appropriate and fair corrective action in
response to any behavior that they deem inappropriate, threatening, offensive,
or harmful.
Community leaders have the right and responsibility to remove, edit, or reject
comments, commits, code, wiki edits, issues, and other contributions that are
not aligned to this Code of Conduct, and will communicate reasons for moderation
decisions when appropriate.
## Scope
This Code of Conduct applies within all community spaces, and also applies when
an individual is officially representing the community in public spaces.
Examples of representing our community include using an official e-mail address,
posting via an official social media account, or acting as an appointed
representative at an online or offline event.
## Enforcement
Instances of abusive, harassing, or otherwise unacceptable behavior may be
reported to the community leaders responsible for enforcement at
[The Multus Slack Page](https://intel-corp.herokuapp.com/).
All complaints will be reviewed and investigated promptly and fairly. Or you
may specifically contact Doug Smith (dosmith@redhat.com) via email.
All community leaders are obligated to respect the privacy and security of the
reporter of any incident.
## Enforcement Guidelines
Community leaders will follow these Community Impact Guidelines in determining
the consequences for any action they deem in violation of this Code of Conduct:
### 1. Correction
**Community Impact**: Use of inappropriate language or other behavior deemed
unprofessional or unwelcome in the community.
**Consequence**: A private, written warning from community leaders, providing
clarity around the nature of the violation and an explanation of why the
behavior was inappropriate. A public apology may be requested.
### 2. Warning
**Community Impact**: A violation through a single incident or series
of actions.
**Consequence**: A warning with consequences for continued behavior. No
interaction with the people involved, including unsolicited interaction with
those enforcing the Code of Conduct, for a specified period of time. This
includes avoiding interactions in community spaces as well as external channels
like social media. Violating these terms may lead to a temporary or
permanent ban.
### 3. Temporary Ban
**Community Impact**: A serious violation of community standards, including
sustained inappropriate behavior.
**Consequence**: A temporary ban from any sort of interaction or public
communication with the community for a specified period of time. No public or
private interaction with the people involved, including unsolicited interaction
with those enforcing the Code of Conduct, is allowed during this period.
Violating these terms may lead to a permanent ban.
### 4. Permanent Ban
**Community Impact**: Demonstrating a pattern of violation of community
standards, including sustained inappropriate behavior, harassment of an
individual, or aggression toward or disparagement of classes of individuals.
**Consequence**: A permanent ban from any sort of public interaction within
the community.
## Attribution
This Code of Conduct is adapted from the [Contributor Covenant][homepage],
version 2.0, available at
https://www.contributor-covenant.org/version/2/0/code_of_conduct.html.
Community Impact Guidelines were inspired by [Mozilla's code of conduct
enforcement ladder](https://github.com/mozilla/diversity).
[homepage]: https://www.contributor-covenant.org
For answers to common questions about this code of conduct, see the FAQ at
https://www.contributor-covenant.org/faq. Translations are available at
https://www.contributor-covenant.org/translations.

View File

@@ -1,22 +0,0 @@
# This Dockerfile is used to build the image available on DockerHub
FROM centos:centos7
# Add everything
ADD . /usr/src/multus-cni
ENV INSTALL_PKGS "git golang"
RUN rpm --import https://mirror.go-repo.io/centos/RPM-GPG-KEY-GO-REPO && \
curl -s https://mirror.go-repo.io/centos/go-repo.repo | tee /etc/yum.repos.d/go-repo.repo && \
yum install -y $INSTALL_PKGS && \
rpm -V $INSTALL_PKGS && \
cd /usr/src/multus-cni && \
./build && \
yum autoremove -y $INSTALL_PKGS && \
yum clean all && \
rm -rf /tmp/*
WORKDIR /
ADD ./images/entrypoint.sh /
ENTRYPOINT ["/entrypoint.sh"]

View File

@@ -1,20 +0,0 @@
# This dockerfile is specific to building Multus for OpenShift
FROM openshift/origin-release:golang-1.10 as builder
ADD . /usr/src/multus-cni
WORKDIR /usr/src/multus-cni
RUN ./build
FROM openshift/origin-base
RUN mkdir -p /usr/src/multus-cni/images && mkdir -p /usr/src/multus-cni/bin
COPY --from=builder /usr/src/multus-cni/images/70-multus.conf /usr/src/multus-cni/images
COPY --from=builder /usr/src/multus-cni/bin/multus /usr/src/multus-cni/bin
ADD ./images/entrypoint.sh /
LABEL io.k8s.display-name="Multus CNI" \
io.k8s.description="This is a component of OpenShift Container Platform and provides a meta CNI plugin." \
io.openshift.tags="openshift" \
maintainer="Doug Smith <dosmith@redhat.com>"
ENTRYPOINT ["/entrypoint.sh"]

View File

@@ -1,8 +1,8 @@
# Multus-CNI
![multus-cni Logo](https://github.com/intel/multus-cni/blob/master/doc/images/Multus.png)
![multus-cni Logo](https://github.com/k8snetworkplumbingwg/multus-cni/blob/master/docs/images/Multus.png)
[![Travis CI](https://travis-ci.org/intel/multus-cni.svg?branch=master)](https://travis-ci.org/intel/multus-cni/builds)[![Go Report Card](https://goreportcard.com/badge/github.com/intel/multus-cni)](https://goreportcard.com/report/github.com/intel/multus-cni)
[![Build](https://github.com/k8snetworkplumbingwg/multus-cni/actions/workflows/build.yml/badge.svg)](https://github.com/k8snetworkplumbingwg/multus-cni/actions/workflows/build.yml)[![Test](https://github.com/k8snetworkplumbingwg/multus-cni/actions/workflows/test.yml/badge.svg)](https://github.com/k8snetworkplumbingwg/multus-cni/actions/workflows/test.yml)[![Go Report Card](https://goreportcard.com/badge/github.com/k8snetworkplumbingwg/multus-cni)](https://goreportcard.com/report/github.com/k8snetworkplumbingwg/multus-cni)[![Coverage Status](https://coveralls.io/repos/github/k8snetworkplumbingwg/multus-cni/badge.svg)](https://coveralls.io/github/k8snetworkplumbingwg/multus-cni)
Multus CNI enables attaching multiple network interfaces to pods in Kubernetes.
@@ -18,36 +18,49 @@ Multus is one of the projects in the [Baremetal Container Experience kit](https:
Here's an illustration of the network interfaces attached to a pod, as provisioned by Multus CNI. The diagram shows the pod with three interfaces: `eth0`, `net0` and `net1`. `eth0` connects kubernetes cluster network to connect with kubernetes server/services (e.g. kubernetes api-server, kubelet and so on). `net0` and `net1` are additional network attachments and connect to other networks by using [other CNI plugins](https://kubernetes.io/docs/concepts/extend-kubernetes/compute-storage-net/network-plugins/) (e.g. vlan/vxlan/ptp).
![multus-pod-image](doc/images/multus-pod-image.svg)
![multus-pod-image](docs/images/multus-pod-image.svg)
## Quickstart Installation Guide
Multus may be deployed as a Daemonset, and is provided in this guide along with Flannel. Flannel is deployed as a pod-to-pod network that is used as our "default network" (a network interface that every pod will be created with). Each network attachment is made in addition to this default network.
The quickstart installation method for Multus requires that you have first installed a Kubernetes CNI plugin to serve as your pod-to-pod network, which we refer to as your "default network" (a network interface that every pod will be created with). Each network attachment created by Multus will be in addition to this default network interface. For more detail on installing a default network CNI plugins, refer to our [quick-start guide](docs/quickstart.md).
Firstly, clone this GitHub repository. We'll apply files to `kubectl` from this repo.
Clone this GitHub repository, we'll apply a daemonset which installs Multus using to `kubectl` from this repo. From the root directory of the clone, apply the daemonset YAML file:
We apply these files as such:
For thin-plugin (i.e. standalone implementation) case:
```
$ cat ./images/{multus-daemonset.yml,flannel-daemonset.yml} | kubectl apply -f -
cat ./deployments/multus-daemonset.yml | kubectl apply -f -
```
This will configure your systems to be ready to use Multus CNI, but, to get started with adding additional interfaces to your pods, refer to our complete [quick-start guide](doc/quickstart.md)
For [thick-plugin](docs/thick-plugin.md) (i.e. client/server implementation) case:
## Additional installation Options
```
cat ./deployments/multus-daemonset-thick.yml | kubectl apply -f -
```
This will configure your systems to be ready to use Multus CNI, but, to get started with adding additional interfaces to your pods, refer to our complete [quick-start guide](docs/quickstart.md)
## Thin Plugin v.s Thick Plugin
With the multus 4.0 release, we introduce a new client/server style plugin deployment. This new deployment is called ['thick plugin'](docs/thick-plugin.md), in contrast to the previous deployment, which is now called 'thin plugin'. The new thick plugin consists of two binaries, multus-daemon and multus-shim CNI plugin. The 'multus-daemon' will be deployed to all nodes as local agent and supports additional features, such as metrics, which were not available with the 'thin plugin' deployment before. Due to those additional features, the 'thick plugin' comes with the trade-off of consuming more resources than the 'thin plugin'.
## Additional Installation Options
- Install via daemonset using the quick-start guide, above.
- Download binaries from [release page](https://github.com/intel/multus-cni/releases)
- Download binaries from [release page](https://github.com/k8snetworkplumbingwg/multus-cni/releases)
- By Docker image from [Docker Hub](https://hub.docker.com/r/nfvpe/multus/tags/)
- Or, roll-you-own and build from source
- See [Development](doc/development.md)
- Or, roll-your-own and build from source
- See [Development](docs/development.md)
## Comprehensive Documentation
- [How to use](doc/how-to-use.md)
- [Configuration](doc/configuration.md)
- [Development](doc/development.md)
- [How to use](docs/how-to-use.md)
- [Quick Start Guide](docs/quickstart.md)
- [Configuration](docs/configuration.md)
- [Development and Support Information](docs/development.md)
- [Thick Plugin](docs/thick-plugin.md)
## Contact Us
For any questions about Multus CNI, feel free to ask a question in #general in the [Intel-Corp Slack](https://intel-corp.herokuapp.com/), or open up a GitHub issue.
For any questions about Multus CNI, feel free to ask a question in #general in the [NPWG Slack](https://npwg-team.slack.com/), or open up a GitHub issue. Request an invite to NPWG slack [here](https://intel-corp.herokuapp.com/).

31
build
View File

@@ -1,31 +0,0 @@
#!/usr/bin/env bash
set -e
ORG_PATH="github.com/intel"
REPO_PATH="${ORG_PATH}/multus-cni"
# Add version/commit/date into binary
# In case of TravisCI, need to check error code of 'git describe'.
set +e
git describe --tags --abbrev=0 > /dev/null 2>&1
if [ "$?" != "0" ]; then
VERSION="master"
else
VERSION=$(git describe --tags --abbrev=0)
fi
set -e
DATE=$(date --iso-8601=seconds)
COMMIT=$(git rev-parse --verify HEAD)
LDFLAGS="-X main.version=${VERSION:-master} -X main.commit=${COMMIT} -X main.date=${DATE}"
if [ ! -h gopath/src/${REPO_PATH} ]; then
mkdir -p gopath/src/${ORG_PATH}
ln -s ../../../.. gopath/src/${REPO_PATH} || exit 255
fi
export GO15VENDOREXPERIMENT=1
export GOBIN=${PWD}/bin
export GOPATH=${PWD}/gopath
echo "Building plugins"
go install -ldflags "${LDFLAGS}" "$@" ${REPO_PATH}/multus

View File

@@ -1,113 +0,0 @@
// Copyright (c) 2018 Intel Corporation
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
//
package checkpoint
import (
"encoding/json"
"io/ioutil"
"github.com/intel/multus-cni/logging"
"github.com/intel/multus-cni/types"
)
const (
checkPointfile = "/var/lib/kubelet/device-plugins/kubelet_internal_checkpoint"
)
type PodDevicesEntry struct {
PodUID string
ContainerName string
ResourceName string
DeviceIDs []string
AllocResp []byte
}
type checkpointData struct {
PodDeviceEntries []PodDevicesEntry
RegisteredDevices map[string][]string
}
type Data struct {
Data checkpointData
Checksum uint64
}
type Checkpoint interface {
// GetComputeDeviceMap returns an instance of a map of ResourceInfo for a PodID
GetComputeDeviceMap(string) (map[string]*types.ResourceInfo, error)
}
type checkpoint struct {
fileName string
podEntires []PodDevicesEntry
}
// GetCheckpoint returns an instance of Checkpoint
func GetCheckpoint() (Checkpoint, error) {
logging.Debugf("GetCheckpoint(): invoked")
return getCheckpoint(checkPointfile)
}
func getCheckpoint(filePath string) (Checkpoint, error) {
cp := &checkpoint{fileName: filePath}
err := cp.getPodEntries()
if err != nil {
return nil, err
}
logging.Debugf("getCheckpoint(): created checkpoint instance with file: %s", filePath)
return cp, nil
}
// getPodEntries gets all Pod device allocation entries from checkpoint file
func (cp *checkpoint) getPodEntries() error {
cpd := &Data{}
rawBytes, err := ioutil.ReadFile(cp.fileName)
if err != nil {
return logging.Errorf("getPodEntries(): error reading file %s\n%v\n", checkPointfile, err)
}
if err = json.Unmarshal(rawBytes, cpd); err != nil {
return logging.Errorf("getPodEntries(): error unmarshalling raw bytes %v", err)
}
cp.podEntires = cpd.Data.PodDeviceEntries
logging.Debugf("getPodEntries(): podEntires %+v", cp.podEntires)
return nil
}
// GetComputeDeviceMap returns an instance of a map of ResourceInfo
func (cp *checkpoint) GetComputeDeviceMap(podID string) (map[string]*types.ResourceInfo, error) {
resourceMap := make(map[string]*types.ResourceInfo)
if podID == "" {
return nil, logging.Errorf("GetComputeDeviceMap(): invalid Pod cannot be empty")
}
for _, pod := range cp.podEntires {
if pod.PodUID == podID {
entry, ok := resourceMap[pod.ResourceName]
if ok {
// already exists; append to it
entry.DeviceIDs = append(entry.DeviceIDs, pod.DeviceIDs...)
} else {
// new entry
resourceMap[pod.ResourceName] = &types.ResourceInfo{DeviceIDs: pod.DeviceIDs}
}
}
}
return resourceMap, nil
}

View File

@@ -1,120 +0,0 @@
package checkpoint
import (
"os"
. "github.com/onsi/ginkgo"
. "github.com/onsi/gomega"
"io/ioutil"
"testing"
"github.com/intel/multus-cni/types"
)
const (
fakeTempFile = "/tmp/kubelet_internal_checkpoint"
)
type fakeCheckpoint struct {
fileName string
}
func (fc *fakeCheckpoint) WriteToFile(inBytes []byte) error {
return ioutil.WriteFile(fc.fileName, inBytes, 0600)
}
func (fc *fakeCheckpoint) DeleteFile() error {
return os.Remove(fc.fileName)
}
func TestCheckpoint(t *testing.T) {
RegisterFailHandler(Fail)
RunSpecs(t, "Checkpoint")
}
var _ = BeforeSuite(func() {
sampleData := `{
"Data": {
"PodDeviceEntries": [
{
"PodUID": "970a395d-bb3b-11e8-89df-408d5c537d23",
"ContainerName": "appcntr1",
"ResourceName": "intel.com/sriov_net_A",
"DeviceIDs": [
"0000:03:02.3",
"0000:03:02.0"
],
"AllocResp": "CikKC3NyaW92X25ldF9BEhogMDAwMDowMzowMi4zIDAwMDA6MDM6MDIuMA=="
}
],
"RegisteredDevices": {
"intel.com/sriov_net_A": [
"0000:03:02.1",
"0000:03:02.2",
"0000:03:02.3",
"0000:03:02.0"
],
"intel.com/sriov_net_B": [
"0000:03:06.3",
"0000:03:06.0",
"0000:03:06.1",
"0000:03:06.2"
]
}
},
"Checksum": 229855270
}`
fakeCheckpoint := &fakeCheckpoint{fileName: fakeTempFile}
err := fakeCheckpoint.WriteToFile([]byte(sampleData))
Expect(err).NotTo(HaveOccurred())
})
var _ = Describe("Kubelet checkpoint data read operations", func() {
Context("Using /tmp/kubelet_internal_checkpoint file", func() {
var (
cp Checkpoint
err error
resourceMap map[string]*types.ResourceInfo
resourceInfo *types.ResourceInfo
resourceAnnot = "intel.com/sriov_net_A"
)
It("should get a Checkpoint instance from file", func() {
cp, err = getCheckpoint(fakeTempFile)
Expect(err).NotTo(HaveOccurred())
})
It("should return a ResourceMap instance", func() {
rmap, err := cp.GetComputeDeviceMap("970a395d-bb3b-11e8-89df-408d5c537d23")
Expect(err).NotTo(HaveOccurred())
Expect(rmap).NotTo(BeEmpty())
resourceMap = rmap
})
It("resourceMap should have value for \"intel.com/sriov_net_A\"", func() {
rInfo, ok := resourceMap[resourceAnnot]
Expect(ok).To(BeTrue())
resourceInfo = rInfo
})
It("should have 2 deviceIDs", func() {
Expect(len(resourceInfo.DeviceIDs)).To(BeEquivalentTo(2))
})
It("should have \"0000:03:02.3\" in deviceIDs[0]", func() {
Expect(resourceInfo.DeviceIDs[0]).To(BeEquivalentTo("0000:03:02.3"))
})
It("should have \"0000:03:02.0\" in deviceIDs[1]", func() {
Expect(resourceInfo.DeviceIDs[1]).To(BeEquivalentTo("0000:03:02.0"))
})
})
})
var _ = AfterSuite(func() {
fakeCheckpoint := &fakeCheckpoint{fileName: fakeTempFile}
err := fakeCheckpoint.DeleteFile()
Expect(err).NotTo(HaveOccurred())
})

298
cmd/multus-daemon/main.go Normal file
View File

@@ -0,0 +1,298 @@
// Copyright (c) 2021 Multus Authors
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
//
// This binary works as a server that receives requests from multus-shim
// CNI plugin and creates network interface for kubernets pods.
package main
import (
"context"
"flag"
"fmt"
"io"
"net/http"
"os"
"os/user"
"path/filepath"
utilruntime "k8s.io/apimachinery/pkg/util/runtime"
utilwait "k8s.io/apimachinery/pkg/util/wait"
"gopkg.in/k8snetworkplumbingwg/multus-cni.v3/pkg/logging"
"gopkg.in/k8snetworkplumbingwg/multus-cni.v3/pkg/multus"
srv "gopkg.in/k8snetworkplumbingwg/multus-cni.v3/pkg/server"
"gopkg.in/k8snetworkplumbingwg/multus-cni.v3/pkg/server/api"
"gopkg.in/k8snetworkplumbingwg/multus-cni.v3/pkg/server/config"
"gopkg.in/k8snetworkplumbingwg/multus-cni.v3/pkg/types"
"github.com/prometheus/client_golang/prometheus/promhttp"
)
const (
multusPluginName = "multus-shim"
)
const (
defaultCniConfigDir = "/etc/cni/net.d"
defaultMultusGlobalNamespaces = ""
defaultMultusLogFile = ""
defaultMultusLogMaxSize = 100 // megabytes
defaultMultusLogMaxAge = 5 // days
defaultMultusLogMaxBackups = 5
defaultMultusLogCompress = true
defaultMultusLogLevel = ""
defaultMultusLogToStdErr = false
defaultMultusMasterCNIFile = ""
defaultMultusNamespaceIsolation = false
defaultMultusReadinessIndicatorFile = ""
)
func main() {
flag.CommandLine = flag.NewFlagSet(os.Args[0], flag.ExitOnError)
cniConfigDir := flag.String("cni-config-dir", defaultCniConfigDir, "CNI config dir")
multusConfigFile := flag.String("multus-conf-file", "auto", "The multus configuration file to use. By default, a new configuration is generated.")
multusMasterCni := flag.String("multus-master-cni-file", "", "The relative name of the configuration file of the cluster primary CNI.")
multusAutoconfigDir := flag.String("multus-autoconfig-dir", *cniConfigDir, "The directory path for the generated multus configuration.")
namespaceIsolation := flag.Bool("namespace-isolation", false, "If the network resources are only available within their defined namespaces.")
globalNamespaces := flag.String("global-namespaces", "", "Comma-separated list of namespaces which can be referred to globally when namespace isolation is enabled.")
logToStdErr := flag.Bool("multus-log-to-stderr", false, "If the multus logs are also to be echoed to stderr.")
logLevel := flag.String("multus-log-level", "", "One of: debug/verbose/error/panic. Used only with --multus-conf-file=auto.")
logFile := flag.String("multus-log-file", "", "Path where to multus will log. Used only with --multus-conf-file=auto.")
logMaxSize := flag.Int("multus-log-max-size", defaultMultusLogMaxSize, "the maximum size in megabytes of the log file before it gets rotated")
logMaxAge := flag.Int("multus-log-max-age", defaultMultusLogMaxAge, "the maximum number of days to retain old log files in their filename")
logMaxBackups := flag.Int("multus-log-max-backups", defaultMultusLogMaxBackups, "the maximum number of old log files to retain")
logCompress := flag.Bool("multus-log-compress", defaultMultusLogCompress, "compress determines if the rotated log files should be compressed using gzip")
cniVersion := flag.String("cni-version", "", "Allows you to specify CNI spec version. Used only with --multus-conf-file=auto.")
forceCNIVersion := flag.Bool("force-cni-version", false, "force to use given CNI version. only for kind-e2e testing") // this is only for kind-e2e
readinessIndicator := flag.String("readiness-indicator-file", "", "Which file should be used as the readiness indicator. Used only with --multus-conf-file=auto.")
overrideNetworkName := flag.Bool("override-network-name", false, "Used when we need overrides the name of the multus configuration with the name of the delegated primary CNI")
version := flag.Bool("version", false, "Show version")
configFilePath := flag.String("config", types.DefaultMultusDaemonConfigFile, "Specify the path to the multus-daemon configuration")
flag.Parse()
if *version {
fmt.Printf("multus-daemon: %s\n", multus.PrintVersionString())
os.Exit(4)
}
configWatcherStopChannel := make(chan struct{})
configWatcherDoneChannel := make(chan struct{})
serverStopChannel := make(chan struct{})
serverDoneChannel := make(chan struct{})
if err := startMultusDaemon(*configFilePath, serverStopChannel, serverDoneChannel); err != nil {
logging.Panicf("failed start the multus thick-plugin listener: %v", err)
os.Exit(3)
}
// Generate multus CNI config from current CNI config
if *multusConfigFile == "auto" {
if *cniVersion == "" {
_ = logging.Errorf("the CNI version is a mandatory parameter when the '-multus-config-file=auto' option is used")
}
var configurationOptions []config.Option
if *namespaceIsolation {
configurationOptions = append(
configurationOptions, config.WithNamespaceIsolation())
}
if *globalNamespaces != defaultMultusGlobalNamespaces {
configurationOptions = append(
configurationOptions, config.WithGlobalNamespaces(*globalNamespaces))
}
if *logToStdErr != defaultMultusLogToStdErr {
configurationOptions = append(
configurationOptions, config.WithLogToStdErr())
}
if *logLevel != defaultMultusLogLevel {
configurationOptions = append(
configurationOptions, config.WithLogLevel(*logLevel))
}
if *logFile != defaultMultusLogFile {
configurationOptions = append(
configurationOptions, config.WithLogFile(*logFile))
}
if *readinessIndicator != defaultMultusReadinessIndicatorFile {
configurationOptions = append(
configurationOptions, config.WithReadinessFileIndicator(*readinessIndicator))
}
// logOptions
var logOptionFuncs []config.LogOptionFunc
if *logMaxAge != defaultMultusLogMaxAge {
logOptionFuncs = append(logOptionFuncs, config.WithLogMaxAge(logMaxAge))
}
if *logMaxSize != defaultMultusLogMaxSize {
logOptionFuncs = append(logOptionFuncs, config.WithLogMaxSize(logMaxSize))
}
if *logMaxBackups != defaultMultusLogMaxBackups {
logOptionFuncs = append(logOptionFuncs, config.WithLogMaxBackups(logMaxBackups))
}
if *logCompress != defaultMultusLogCompress {
logOptionFuncs = append(logOptionFuncs, config.WithLogCompress(logCompress))
}
if len(logOptionFuncs) > 0 {
logOptions := &config.LogOptions{}
config.MutateLogOptions(logOptions, logOptionFuncs...)
configurationOptions = append(configurationOptions, config.WithLogOptions(logOptions))
}
multusConfig, err := config.NewMultusConfig(multusPluginName, *cniVersion, configurationOptions...)
if err != nil {
_ = logging.Errorf("Failed to create multus config: %v", err)
os.Exit(3)
}
var configManager *config.Manager
if *multusMasterCni == "" {
configManager, err = config.NewManager(*multusConfig, *multusAutoconfigDir, *forceCNIVersion)
} else {
configManager, err = config.NewManagerWithExplicitPrimaryCNIPlugin(
*multusConfig, *multusAutoconfigDir, *multusMasterCni, *forceCNIVersion)
}
if err != nil {
_ = logging.Errorf("failed to create the configuration manager for the primary CNI plugin: %v", err)
os.Exit(2)
}
if *overrideNetworkName {
if err := configManager.OverrideNetworkName(); err != nil {
_ = logging.Errorf("could not override the network name: %v", err)
}
}
generatedMultusConfig, err := configManager.GenerateConfig()
if err != nil {
_ = logging.Errorf("failed to generated the multus configuration: %v", err)
}
logging.Verbosef("Generated MultusCNI config: %s", generatedMultusConfig)
if err := configManager.PersistMultusConfig(generatedMultusConfig); err != nil {
_ = logging.Errorf("failed to persist the multus configuration: %v", err)
}
go func(stopChannel chan<- struct{}, doneChannel chan<- struct{}) {
if err := configManager.MonitorPluginConfiguration(configWatcherStopChannel, doneChannel); err != nil {
_ = logging.Errorf("error watching file: %v", err)
}
}(configWatcherStopChannel, configWatcherDoneChannel)
<-configWatcherDoneChannel
} else {
if err := copyUserProvidedConfig(*multusConfigFile, *cniConfigDir); err != nil {
logging.Errorf("failed to copy the user provided configuration %s: %v", *multusConfigFile, err)
}
}
serverDone := false
configWatcherDone := false
for {
select {
case <-configWatcherDoneChannel:
logging.Verbosef("ConfigWatcher done")
configWatcherDone = true
case <-serverDoneChannel:
logging.Verbosef("multus-server done.")
serverDone = true
}
if serverDone && configWatcherDone {
return
}
}
// never reached
}
func startMultusDaemon(configFilePath string, stopCh chan struct{}, done chan struct{}) error {
daemonConfig, config, err := types.LoadDaemonNetConf(configFilePath)
if err != nil {
logging.Panicf("failed to load the multus-daemon configuration: %v", err)
os.Exit(1)
}
if user, err := user.Current(); err != nil || user.Uid != "0" {
return fmt.Errorf("failed to run multus-daemon with root: %v, now running in uid: %s", err, user.Uid)
}
if err := srv.FilesystemPreRequirements(daemonConfig.MultusSocketDir); err != nil {
return fmt.Errorf("failed to prepare the cni-socket for communicating with the shim: %w", err)
}
server, err := srv.NewCNIServer(daemonConfig, config)
if err != nil {
return fmt.Errorf("failed to create the server: %v", err)
}
if daemonConfig.MetricsPort != nil {
go utilwait.Until(func() {
http.Handle("/metrics", promhttp.Handler())
logging.Debugf("metrics port: %d", *daemonConfig.MetricsPort)
logging.Debugf("metrics: %s", http.ListenAndServe(fmt.Sprintf(":%d", *daemonConfig.MetricsPort), nil))
}, 0, stopCh)
}
l, err := srv.GetListener(api.SocketPath(daemonConfig.MultusSocketDir))
if err != nil {
return fmt.Errorf("failed to start the CNI server using socket %s. Reason: %+v", api.SocketPath(daemonConfig.MultusSocketDir), err)
}
server.SetKeepAlivesEnabled(false)
go func() {
utilwait.Until(func() {
logging.Debugf("open for business")
if err := server.Serve(l); err != nil {
utilruntime.HandleError(fmt.Errorf("CNI server Serve() failed: %v", err))
}
}, 0, stopCh)
server.Shutdown(context.TODO())
close(done)
}()
return nil
}
func copyUserProvidedConfig(multusConfigPath string, cniConfigDir string) error {
srcFile, err := os.Open(multusConfigPath)
if err != nil {
return fmt.Errorf("failed to open (READ only) file %s: %w", multusConfigPath, err)
}
dstFileName := cniConfigDir + "/" + filepath.Base(multusConfigPath)
dstFile, err := os.Create(dstFileName)
if err != nil {
return fmt.Errorf("creating copying file %s: %w", dstFileName, err)
}
nBytes, err := io.Copy(dstFile, srcFile)
if err != nil {
return fmt.Errorf("error copying file: %w", err)
}
srcFileInfo, err := srcFile.Stat()
if err != nil {
return fmt.Errorf("failed to stat the file: %w", err)
} else if nBytes != srcFileInfo.Size() {
return fmt.Errorf("error copying file - copied only %d bytes out of %d", nBytes, srcFileInfo.Size())
}
return nil
}

58
cmd/multus-shim/main.go Normal file
View File

@@ -0,0 +1,58 @@
// Copyright (c) 2021 Multus Authors
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
// This is a "Multi-plugin".The delegate concept referred from CNI project
// It reads other plugin netconf, and then invoke them, e.g.
// flannel or sriov plugin.
package main
import (
"flag"
"fmt"
"os"
"github.com/containernetworking/cni/pkg/skel"
cniversion "github.com/containernetworking/cni/pkg/version"
"gopkg.in/k8snetworkplumbingwg/multus-cni.v3/pkg/multus"
"gopkg.in/k8snetworkplumbingwg/multus-cni.v3/pkg/server/api"
)
func main() {
// Init command line flags to clear vendored packages' one, especially in init()
flag.CommandLine = flag.NewFlagSet(os.Args[0], flag.ExitOnError)
// add version flag
versionOpt := false
flag.BoolVar(&versionOpt, "version", false, "Show application version")
flag.BoolVar(&versionOpt, "v", false, "Show application version")
flag.Parse()
if versionOpt == true {
fmt.Printf("multus-shim: %s\n", multus.PrintVersionString())
return
}
skel.PluginMain(
func(args *skel.CmdArgs) error {
return api.CmdAdd(args)
},
func(args *skel.CmdArgs) error {
return api.CmdCheck(args)
},
func(args *skel.CmdArgs) error {
return api.CmdDel(args)
},
cniversion.All, "meta-plugin that delegates to other CNI plugins")
}

58
cmd/multus/main.go Normal file
View File

@@ -0,0 +1,58 @@
// Copyright (c) 2017 Intel Corporation
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
// This is a "Multi-plugin".The delegate concept referred from CNI project
// It reads other plugin netconf, and then invoke them, e.g.
// flannel or sriov plugin.
package main
import (
"flag"
"fmt"
"os"
"github.com/containernetworking/cni/pkg/skel"
cniversion "github.com/containernetworking/cni/pkg/version"
"gopkg.in/k8snetworkplumbingwg/multus-cni.v3/pkg/multus"
)
func main() {
// Init command line flags to clear vendored packages' one, especially in init()
flag.CommandLine = flag.NewFlagSet(os.Args[0], flag.ExitOnError)
// add version flag
versionOpt := false
flag.BoolVar(&versionOpt, "version", false, "Show application version")
flag.BoolVar(&versionOpt, "v", false, "Show application version")
flag.Parse()
if versionOpt == true {
fmt.Printf("multus: %s\n", multus.PrintVersionString())
return
}
skel.PluginMain(
func(args *skel.CmdArgs) error {
result, err := multus.CmdAdd(args, nil, nil)
if err != nil {
return err
}
return result.Print()
},
func(args *skel.CmdArgs) error {
return multus.CmdCheck(args, nil, nil)
},
func(args *skel.CmdArgs) error { return multus.CmdDel(args, nil, nil) },
cniversion.All, "meta-plugin that delegates to other CNI plugins")
}

View File

@@ -0,0 +1,263 @@
---
apiVersion: apiextensions.k8s.io/v1beta1
kind: CustomResourceDefinition
metadata:
name: network-attachment-definitions.k8s.cni.cncf.io
spec:
group: k8s.cni.cncf.io
scope: Namespaced
names:
plural: network-attachment-definitions
singular: network-attachment-definition
kind: NetworkAttachmentDefinition
shortNames:
- net-attach-def
versions:
- name: v1
served: true
storage: true
schema:
openAPIV3Schema:
description: 'NetworkAttachmentDefinition is a CRD schema specified by the Network Plumbing
Working Group to express the intent for attaching pods to one or more logical or physical
networks. More information available at: https://github.com/k8snetworkplumbingwg/multi-net-spec'
type: object
properties:
spec:
description: 'NetworkAttachmentDefinition spec defines the desired state of a network attachment'
type: object
properties:
config:
description: 'NetworkAttachmentDefinition config is a JSON-formatted CNI configuration'
type: string
---
kind: ClusterRole
apiVersion: rbac.authorization.k8s.io/v1beta1
metadata:
name: multus
rules:
- apiGroups: ["k8s.cni.cncf.io"]
resources:
- '*'
verbs:
- '*'
- apiGroups:
- ""
resources:
- pods
- pods/status
verbs:
- get
- update
- apiGroups:
- ""
- events.k8s.io
resources:
- events
verbs:
- create
- patch
- update
---
kind: ClusterRoleBinding
apiVersion: rbac.authorization.k8s.io/v1beta1
metadata:
name: multus
roleRef:
apiGroup: rbac.authorization.k8s.io
kind: ClusterRole
name: multus
subjects:
- kind: ServiceAccount
name: multus
namespace: kube-system
---
apiVersion: v1
kind: ServiceAccount
metadata:
name: multus
namespace: kube-system
---
kind: ConfigMap
apiVersion: v1
metadata:
name: multus-cni-config
namespace: kube-system
labels:
tier: node
app: multus
data:
# NOTE: If you'd prefer to manually apply a configuration file, you may create one here.
# In the case you'd like to customize the Multus installation, you should change the arguments to the Multus pod
# change the "args" line below from
# - "--multus-conf-file=auto"
# to:
# "--multus-conf-file=/tmp/multus-conf/70-multus.conf"
# Additionally -- you should ensure that the name "70-multus.conf" is the alphabetically first name in the
# /etc/cni/net.d/ directory on each node, otherwise, it will not be used by the Kubelet.
cni-conf.json: |
{
"name": "multus-cni-network",
"type": "multus",
"capabilities": {
"portMappings": true
},
"delegates": [
{
"cniVersion": "0.3.1",
"name": "default-cni-network",
"plugins": [
{
"type": "flannel",
"name": "flannel.1",
"delegate": {
"isDefaultGateway": true,
"hairpinMode": true
}
},
{
"type": "portmap",
"capabilities": {
"portMappings": true
}
}
]
}
],
"kubeconfig": "/etc/cni/net.d/multus.d/multus.kubeconfig"
}
---
apiVersion: extensions/v1beta1
kind: DaemonSet
metadata:
name: kube-multus-ds-amd64
namespace: kube-system
labels:
tier: node
app: multus
spec:
updateStrategy:
type: RollingUpdate
template:
metadata:
labels:
tier: node
app: multus
spec:
hostNetwork: true
nodeSelector:
beta.kubernetes.io/arch: amd64
tolerations:
- operator: Exists
effect: NoSchedule
serviceAccountName: multus
containers:
- name: kube-multus
# crio support requires multus:latest for now. support 3.3 or later.
image: nfvpe/multus:v3.6
command: ["/entrypoint.sh"]
args:
- "--cni-bin-dir=/host/usr/libexec/cni"
- "--multus-conf-file=auto"
- "--override-network-name=true"
- "--restart-crio=true"
resources:
requests:
cpu: "100m"
memory: "50Mi"
limits:
cpu: "100m"
memory: "50Mi"
securityContext:
privileged: true
capabilities:
add: ["SYS_ADMIN"]
volumeMounts:
- name: run
mountPath: /run
- name: cni
mountPath: /host/etc/cni/net.d
- name: cnibin
mountPath: /host/usr/libexec/cni
- name: multus-cfg
mountPath: /tmp/multus-conf
volumes:
- name: run
hostPath:
path: /run
- name: cni
hostPath:
path: /etc/cni/net.d
- name: cnibin
hostPath:
path: /usr/libexec/cni
- name: multus-cfg
configMap:
name: multus-cni-config
items:
- key: cni-conf.json
path: 70-multus.conf
---
apiVersion: extensions/v1beta1
kind: DaemonSet
metadata:
name: kube-multus-ds-ppc64le
namespace: kube-system
labels:
tier: node
app: multus
spec:
updateStrategy:
type: RollingUpdate
template:
metadata:
labels:
tier: node
app: multus
spec:
hostNetwork: true
nodeSelector:
beta.kubernetes.io/arch: ppc64le
tolerations:
- operator: Exists
effect: NoSchedule
serviceAccountName: multus
containers:
- name: kube-multus
# crio support requires multus:latest for now. support 3.3 or later.
image: nfvpe/multus:latest-ppc64le
command: ["/entrypoint.sh"]
args:
- "--cni-bin-dir=/host/usr/libexec/cni"
- "--multus-conf-file=auto"
- "--override-network-name=true"
- "--restart-crio=true"
resources:
requests:
cpu: "100m"
memory: "90Mi"
limits:
cpu: "100m"
memory: "90Mi"
securityContext:
privileged: true
volumeMounts:
- name: cni
mountPath: /host/etc/cni/net.d
- name: cnibin
mountPath: /host/usr/libexec/cni
- name: multus-cfg
mountPath: /tmp/multus-conf
volumes:
- name: cni
hostPath:
path: /etc/cni/net.d
- name: cnibin
hostPath:
path: /usr/libexec/cni
- name: multus-cfg
configMap:
name: multus-cni-config
items:
- key: cni-conf.json
path: 70-multus.conf

View File

@@ -0,0 +1,232 @@
---
apiVersion: apiextensions.k8s.io/v1beta1
kind: CustomResourceDefinition
metadata:
name: network-attachment-definitions.k8s.cni.cncf.io
spec:
group: k8s.cni.cncf.io
version: v1
scope: Namespaced
names:
plural: network-attachment-definitions
singular: network-attachment-definition
kind: NetworkAttachmentDefinition
shortNames:
- net-attach-def
validation:
openAPIV3Schema:
properties:
spec:
properties:
config:
type: string
---
kind: ClusterRole
apiVersion: rbac.authorization.k8s.io/v1beta1
metadata:
name: multus
rules:
- apiGroups: ["k8s.cni.cncf.io"]
resources:
- '*'
verbs:
- '*'
- apiGroups:
- ""
resources:
- pods
- pods/status
verbs:
- get
- update
---
kind: ClusterRoleBinding
apiVersion: rbac.authorization.k8s.io/v1beta1
metadata:
name: multus
roleRef:
apiGroup: rbac.authorization.k8s.io
kind: ClusterRole
name: multus
subjects:
- kind: ServiceAccount
name: multus
namespace: kube-system
---
apiVersion: v1
kind: ServiceAccount
metadata:
name: multus
namespace: kube-system
---
kind: ConfigMap
apiVersion: v1
metadata:
name: multus-cni-config
namespace: kube-system
labels:
tier: node
app: multus
data:
# NOTE: If you'd prefer to manually apply a configuration file, you may create one here.
# In the case you'd like to customize the Multus installation, you should change the arguments to the Multus pod
# change the "args" line below from
# - "--multus-conf-file=auto"
# to:
# "--multus-conf-file=/tmp/multus-conf/70-multus.conf"
# Additionally -- you should ensure that the name "70-multus.conf" is the alphabetically first name in the
# /etc/cni/net.d/ directory on each node, otherwise, it will not be used by the Kubelet.
cni-conf.json: |
{
"name": "multus-cni-network",
"type": "multus",
"capabilities": {
"portMappings": true
},
"delegates": [
{
"cniVersion": "0.3.1",
"name": "default-cni-network",
"plugins": [
{
"type": "flannel",
"name": "flannel.1",
"delegate": {
"isDefaultGateway": true,
"hairpinMode": true
}
},
{
"type": "portmap",
"capabilities": {
"portMappings": true
}
}
]
}
],
"kubeconfig": "/etc/cni/net.d/multus.d/multus.kubeconfig"
}
---
apiVersion: extensions/v1beta1
kind: DaemonSet
metadata:
name: kube-multus-ds-amd64
namespace: kube-system
labels:
tier: node
app: multus
spec:
updateStrategy:
type: RollingUpdate
template:
metadata:
labels:
tier: node
app: multus
spec:
hostNetwork: true
nodeSelector:
beta.kubernetes.io/arch: amd64
tolerations:
- operator: Exists
effect: NoSchedule
serviceAccountName: multus
containers:
- name: kube-multus
image: nfvpe/multus:v3.6
command: ["/entrypoint.sh"]
args:
- "--multus-conf-file=auto"
- "--cni-bin-dir=/host/home/kubernetes/bin"
resources:
requests:
cpu: "100m"
memory: "50Mi"
limits:
cpu: "100m"
memory: "50Mi"
securityContext:
privileged: true
volumeMounts:
- name: cni
mountPath: /host/etc/cni/net.d
- name: cnibin
mountPath: /host/home/kubernetes/bin
- name: multus-cfg
mountPath: /tmp/multus-conf
volumes:
- name: cni
hostPath:
path: /etc/cni/net.d
- name: cnibin
hostPath:
path: /home/kubernetes/bin
- name: multus-cfg
configMap:
name: multus-cni-config
items:
- key: cni-conf.json
path: 70-multus.conf
---
apiVersion: extensions/v1beta1
kind: DaemonSet
metadata:
name: kube-multus-ds-ppc64le
namespace: kube-system
labels:
tier: node
app: multus
spec:
updateStrategy:
type: RollingUpdate
template:
metadata:
labels:
tier: node
app: multus
spec:
hostNetwork: true
nodeSelector:
beta.kubernetes.io/arch: ppc64le
tolerations:
- operator: Exists
effect: NoSchedule
serviceAccountName: multus
containers:
- name: kube-multus
# ppc64le support requires multus:latest for now. support 3.3 or later.
image: nfvpe/multus:latest-ppc64le
command: ["/entrypoint.sh"]
args:
- "--multus-conf-file=auto"
- "--cni-bin-dir=/host/home/kubernetes/bin"
resources:
requests:
cpu: "100m"
memory: "90Mi"
limits:
cpu: "100m"
memory: "90Mi"
securityContext:
privileged: true
volumeMounts:
- name: cni
mountPath: /host/etc/cni/net.d
- name: cnibin
mountPath: /host/home/kubernetes/bin
- name: multus-cfg
mountPath: /tmp/multus-conf
volumes:
- name: cni
hostPath:
path: /etc/cni/net.d
- name: cnibin
hostPath:
path: /home/kubernetes/bin
- name: multus-cfg
configMap:
name: multus-cni-config
items:
- key: cni-conf.json
path: 70-multus.conf

View File

@@ -0,0 +1,249 @@
---
apiVersion: apiextensions.k8s.io/v1beta1
kind: CustomResourceDefinition
metadata:
name: network-attachment-definitions.k8s.cni.cncf.io
spec:
group: k8s.cni.cncf.io
scope: Namespaced
names:
plural: network-attachment-definitions
singular: network-attachment-definition
kind: NetworkAttachmentDefinition
shortNames:
- net-attach-def
versions:
- name: v1
served: true
storage: true
schema:
openAPIV3Schema:
description: 'NetworkAttachmentDefinition is a CRD schema specified by the Network Plumbing
Working Group to express the intent for attaching pods to one or more logical or physical
networks. More information available at: https://github.com/k8snetworkplumbingwg/multi-net-spec'
type: object
properties:
spec:
description: 'NetworkAttachmentDefinition spec defines the desired state of a network attachment'
type: object
properties:
config:
description: 'NetworkAttachmentDefinition config is a JSON-formatted CNI configuration'
type: string
---
kind: ClusterRole
apiVersion: rbac.authorization.k8s.io/v1beta1
metadata:
name: multus
rules:
- apiGroups: ["k8s.cni.cncf.io"]
resources:
- '*'
verbs:
- '*'
- apiGroups:
- ""
resources:
- pods
- pods/status
verbs:
- get
- update
- apiGroups:
- ""
- events.k8s.io
resources:
- events
verbs:
- create
- patch
- update
---
kind: ClusterRoleBinding
apiVersion: rbac.authorization.k8s.io/v1beta1
metadata:
name: multus
roleRef:
apiGroup: rbac.authorization.k8s.io
kind: ClusterRole
name: multus
subjects:
- kind: ServiceAccount
name: multus
namespace: kube-system
---
apiVersion: v1
kind: ServiceAccount
metadata:
name: multus
namespace: kube-system
---
kind: ConfigMap
apiVersion: v1
metadata:
name: multus-cni-config
namespace: kube-system
labels:
tier: node
app: multus
data:
# NOTE: If you'd prefer to manually apply a configuration file, you may create one here.
# In the case you'd like to customize the Multus installation, you should change the arguments to the Multus pod
# change the "args" line below from
# - "--multus-conf-file=auto"
# to:
# "--multus-conf-file=/tmp/multus-conf/70-multus.conf"
# Additionally -- you should ensure that the name "70-multus.conf" is the alphabetically first name in the
# /etc/cni/net.d/ directory on each node, otherwise, it will not be used by the Kubelet.
cni-conf.json: |
{
"name": "multus-cni-network",
"type": "multus",
"capabilities": {
"portMappings": true
},
"delegates": [
{
"cniVersion": "0.3.1",
"name": "default-cni-network",
"plugins": [
{
"type": "flannel",
"name": "flannel.1",
"delegate": {
"isDefaultGateway": true,
"hairpinMode": true
}
},
{
"type": "portmap",
"capabilities": {
"portMappings": true
}
}
]
}
],
"kubeconfig": "/etc/cni/net.d/multus.d/multus.kubeconfig"
}
---
apiVersion: extensions/v1beta1
kind: DaemonSet
metadata:
name: kube-multus-ds-amd64
namespace: kube-system
labels:
tier: node
app: multus
spec:
updateStrategy:
type: RollingUpdate
template:
metadata:
labels:
tier: node
app: multus
spec:
hostNetwork: true
nodeSelector:
beta.kubernetes.io/arch: amd64
tolerations:
- operator: Exists
effect: NoSchedule
serviceAccountName: multus
containers:
- name: kube-multus
image: nfvpe/multus:v3.6
command: ["/entrypoint.sh"]
args:
- "--multus-conf-file=auto"
resources:
requests:
cpu: "100m"
memory: "50Mi"
limits:
cpu: "100m"
memory: "50Mi"
securityContext:
privileged: true
volumeMounts:
- name: cni
mountPath: /host/etc/cni/net.d
- name: cnibin
mountPath: /host/opt/cni/bin
- name: multus-cfg
mountPath: /tmp/multus-conf
volumes:
- name: cni
hostPath:
path: /etc/cni/net.d
- name: cnibin
hostPath:
path: /opt/cni/bin
- name: multus-cfg
configMap:
name: multus-cni-config
items:
- key: cni-conf.json
path: 70-multus.conf
---
apiVersion: extensions/v1beta1
kind: DaemonSet
metadata:
name: kube-multus-ds-ppc64le
namespace: kube-system
labels:
tier: node
app: multus
spec:
updateStrategy:
type: RollingUpdate
template:
metadata:
labels:
tier: node
app: multus
spec:
hostNetwork: true
nodeSelector:
beta.kubernetes.io/arch: ppc64le
tolerations:
- operator: Exists
effect: NoSchedule
serviceAccountName: multus
containers:
- name: kube-multus
# ppc64le support requires multus:latest for now. support 3.3 or later.
image: nfvpe/multus:latest-ppc64le
command: ["/entrypoint.sh"]
args:
- "--multus-conf-file=auto"
resources:
requests:
cpu: "100m"
memory: "90Mi"
limits:
cpu: "100m"
memory: "90Mi"
securityContext:
privileged: true
volumeMounts:
- name: cni
mountPath: /host/etc/cni/net.d
- name: cnibin
mountPath: /host/opt/cni/bin
- name: multus-cfg
mountPath: /tmp/multus-conf
volumes:
- name: cni
hostPath:
path: /etc/cni/net.d
- name: cnibin
hostPath:
path: /opt/cni/bin
- name: multus-cfg
configMap:
name: multus-cni-config
items:
- key: cni-conf.json
path: 70-multus.conf

View File

@@ -0,0 +1,227 @@
# Note:
# This deployment file is designed for 'quickstart' of multus, easy installation to test it,
# hence this deployment yaml does not care about following things intentionally.
# - various configuration options
# - minor deployment scenario
# - upgrade/update/uninstall scenario
# Multus team understand users deployment scenarios are diverse, hence we do not cover
# comprehensive deployment scenario. We expect that it is covered by each platform deployment.
---
apiVersion: apiextensions.k8s.io/v1
kind: CustomResourceDefinition
metadata:
name: network-attachment-definitions.k8s.cni.cncf.io
spec:
group: k8s.cni.cncf.io
scope: Namespaced
names:
plural: network-attachment-definitions
singular: network-attachment-definition
kind: NetworkAttachmentDefinition
shortNames:
- net-attach-def
versions:
- name: v1
served: true
storage: true
schema:
openAPIV3Schema:
description: 'NetworkAttachmentDefinition is a CRD schema specified by the Network Plumbing
Working Group to express the intent for attaching pods to one or more logical or physical
networks. More information available at: https://github.com/k8snetworkplumbingwg/multi-net-spec'
type: object
properties:
apiVersion:
description: 'APIVersion defines the versioned schema of this represen
tation of an object. Servers should convert recognized schemas to the
latest internal value, and may reject unrecognized values. More info:
https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources'
type: string
kind:
description: 'Kind is a string value representing the REST resource this
object represents. Servers may infer this from the endpoint the client
submits requests to. Cannot be updated. In CamelCase. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#types-kinds'
type: string
metadata:
type: object
spec:
description: 'NetworkAttachmentDefinition spec defines the desired state of a network attachment'
type: object
properties:
config:
description: 'NetworkAttachmentDefinition config is a JSON-formatted CNI configuration'
type: string
---
kind: ClusterRole
apiVersion: rbac.authorization.k8s.io/v1
metadata:
name: multus
rules:
- apiGroups: ["k8s.cni.cncf.io"]
resources:
- '*'
verbs:
- '*'
- apiGroups:
- ""
resources:
- pods
- pods/status
verbs:
- get
- update
- apiGroups:
- ""
- events.k8s.io
resources:
- events
verbs:
- create
- patch
- update
---
kind: ClusterRoleBinding
apiVersion: rbac.authorization.k8s.io/v1
metadata:
name: multus
roleRef:
apiGroup: rbac.authorization.k8s.io
kind: ClusterRole
name: multus
subjects:
- kind: ServiceAccount
name: multus
namespace: kube-system
---
apiVersion: v1
kind: ServiceAccount
metadata:
name: multus
namespace: kube-system
---
kind: ConfigMap
apiVersion: v1
metadata:
name: multus-cni-config
namespace: kube-system
labels:
tier: node
app: multus
data:
# NOTE: If you'd prefer to manually apply a configuration file, you may create one here.
# In the case you'd like to customize the Multus installation, you should change the arguments to the Multus pod
# change the "args" line below from
# - "--multus-conf-file=auto"
# to:
# "--multus-conf-file=/tmp/multus-conf/70-multus.conf"
# Additionally -- you should ensure that the name "70-multus.conf" is the alphabetically first name in the
# /etc/cni/net.d/ directory on each node, otherwise, it will not be used by the Kubelet.
cni-conf.json: |
{
"name": "multus-cni-network",
"type": "multus",
"capabilities": {
"portMappings": true
},
"delegates": [
{
"cniVersion": "0.3.1",
"name": "default-cni-network",
"plugins": [
{
"type": "flannel",
"name": "flannel.1",
"delegate": {
"isDefaultGateway": true,
"hairpinMode": true
}
},
{
"type": "portmap",
"capabilities": {
"portMappings": true
}
}
]
}
],
"kubeconfig": "/etc/cni/net.d/multus.d/multus.kubeconfig"
}
---
apiVersion: apps/v1
kind: DaemonSet
metadata:
name: kube-multus-ds
namespace: kube-system
labels:
tier: node
app: multus
name: multus
spec:
selector:
matchLabels:
name: multus
updateStrategy:
type: RollingUpdate
template:
metadata:
labels:
tier: node
app: multus
name: multus
spec:
hostNetwork: true
tolerations:
- operator: Exists
effect: NoSchedule
- operator: Exists
effect: NoExecute
serviceAccountName: multus
containers:
- name: kube-multus
# crio support requires multus:latest for now. support 3.3 or later.
image: ghcr.io/k8snetworkplumbingwg/multus-cni:stable
command: ["/entrypoint.sh"]
args:
- "--cni-version=0.3.1"
- "--cni-bin-dir=/host/usr/libexec/cni"
- "--multus-conf-file=auto"
- "--restart-crio=true"
resources:
requests:
cpu: "100m"
memory: "50Mi"
limits:
cpu: "100m"
memory: "50Mi"
securityContext:
privileged: true
capabilities:
add: ["SYS_ADMIN"]
volumeMounts:
- name: run
mountPath: /run
mountPropagation: HostToContainer
- name: cni
mountPath: /host/etc/cni/net.d
- name: cnibin
mountPath: /host/usr/libexec/cni
- name: multus-cfg
mountPath: /tmp/multus-conf
terminationGracePeriodSeconds: 10
volumes:
- name: run
hostPath:
path: /run
- name: cni
hostPath:
path: /etc/cni/net.d
- name: cnibin
hostPath:
path: /usr/libexec/cni
- name: multus-cfg
configMap:
name: multus-cni-config
items:
- key: cni-conf.json
path: 70-multus.conf

View File

@@ -0,0 +1,189 @@
# Note:
# This deployment file is designed for 'quickstart' of multus, easy installation to test it,
# hence this deployment yaml does not care about following things intentionally.
# - various configuration options
# - minor deployment scenario
# - upgrade/update/uninstall scenario
# Multus team understand users deployment scenarios are diverse, hence we do not cover
# comprehensive deployment scenario. We expect that it is covered by each platform deployment.
---
apiVersion: apiextensions.k8s.io/v1
kind: CustomResourceDefinition
metadata:
name: network-attachment-definitions.k8s.cni.cncf.io
spec:
group: k8s.cni.cncf.io
scope: Namespaced
names:
plural: network-attachment-definitions
singular: network-attachment-definition
kind: NetworkAttachmentDefinition
shortNames:
- net-attach-def
versions:
- name: v1
served: true
storage: true
schema:
openAPIV3Schema:
type: object
properties:
spec:
type: object
properties:
config:
type: string
---
kind: ClusterRole
apiVersion: rbac.authorization.k8s.io/v1
metadata:
name: multus
rules:
- apiGroups: ["k8s.cni.cncf.io"]
resources:
- '*'
verbs:
- '*'
- apiGroups:
- ""
resources:
- pods
- pods/status
verbs:
- get
- update
---
kind: ClusterRoleBinding
apiVersion: rbac.authorization.k8s.io/v1
metadata:
name: multus
roleRef:
apiGroup: rbac.authorization.k8s.io
kind: ClusterRole
name: multus
subjects:
- kind: ServiceAccount
name: multus
namespace: kube-system
---
apiVersion: v1
kind: ServiceAccount
metadata:
name: multus
namespace: kube-system
---
kind: ConfigMap
apiVersion: v1
metadata:
name: multus-cni-config
namespace: kube-system
labels:
tier: node
app: multus
data:
# NOTE: If you'd prefer to manually apply a configuration file, you may create one here.
# In the case you'd like to customize the Multus installation, you should change the arguments to the Multus pod
# change the "args" line below from
# - "--multus-conf-file=auto"
# to:
# "--multus-conf-file=/tmp/multus-conf/70-multus.conf"
# Additionally -- you should ensure that the name "70-multus.conf" is the alphabetically first name in the
# /etc/cni/net.d/ directory on each node, otherwise, it will not be used by the Kubelet.
cni-conf.json: |
{
"name": "multus-cni-network",
"type": "multus",
"capabilities": {
"portMappings": true
},
"delegates": [
{
"cniVersion": "0.3.1",
"name": "default-cni-network",
"plugins": [
{
"type": "flannel",
"name": "flannel.1",
"delegate": {
"isDefaultGateway": true,
"hairpinMode": true
}
},
{
"type": "portmap",
"capabilities": {
"portMappings": true
}
}
]
}
],
"kubeconfig": "/etc/cni/net.d/multus.d/multus.kubeconfig"
}
---
apiVersion: apps/v1
kind: DaemonSet
metadata:
name: kube-multus-ds
namespace: kube-system
labels:
tier: node
app: multus
name: multus
spec:
selector:
matchLabels:
name: multus
updateStrategy:
type: RollingUpdate
template:
metadata:
labels:
tier: node
app: multus
name: multus
spec:
hostNetwork: true
tolerations:
- operator: Exists
effect: NoSchedule
- operator: Exists
effect: NoExecute
serviceAccountName: multus
containers:
- name: kube-multus
image: ghcr.io/k8snetworkplumbingwg/multus-cni:stable
command: ["/entrypoint.sh"]
args:
- "--multus-conf-file=auto"
- "--cni-version=0.3.1"
- "--cni-bin-dir=/host/home/kubernetes/bin"
resources:
requests:
cpu: "100m"
memory: "50Mi"
limits:
cpu: "100m"
memory: "50Mi"
securityContext:
privileged: true
volumeMounts:
- name: cni
mountPath: /host/etc/cni/net.d
- name: cnibin
mountPath: /host/home/kubernetes/bin
- name: multus-cfg
mountPath: /tmp/multus-conf
volumes:
- name: cni
hostPath:
path: /etc/cni/net.d
- name: cnibin
hostPath:
path: /home/kubernetes/bin
- name: multus-cfg
configMap:
name: multus-cni-config
items:
- key: cni-conf.json
path: 70-multus.conf

View File

@@ -0,0 +1,240 @@
# Note:
# This deployment file is designed for 'quickstart' of multus, easy installation to test it,
# hence this deployment yaml does not care about following things intentionally.
# - various configuration options
# - minor deployment scenario
# - upgrade/update/uninstall scenario
# Multus team understand users deployment scenarios are diverse, hence we do not cover
# comprehensive deployment scenario. We expect that it is covered by each platform deployment.
---
apiVersion: apiextensions.k8s.io/v1
kind: CustomResourceDefinition
metadata:
name: network-attachment-definitions.k8s.cni.cncf.io
spec:
group: k8s.cni.cncf.io
scope: Namespaced
names:
plural: network-attachment-definitions
singular: network-attachment-definition
kind: NetworkAttachmentDefinition
shortNames:
- net-attach-def
versions:
- name: v1
served: true
storage: true
schema:
openAPIV3Schema:
description: 'NetworkAttachmentDefinition is a CRD schema specified by the Network Plumbing
Working Group to express the intent for attaching pods to one or more logical or physical
networks. More information available at: https://github.com/k8snetworkplumbingwg/multi-net-spec'
type: object
properties:
apiVersion:
description: 'APIVersion defines the versioned schema of this represen
tation of an object. Servers should convert recognized schemas to the
latest internal value, and may reject unrecognized values. More info:
https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources'
type: string
kind:
description: 'Kind is a string value representing the REST resource this
object represents. Servers may infer this from the endpoint the client
submits requests to. Cannot be updated. In CamelCase. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#types-kinds'
type: string
metadata:
type: object
spec:
description: 'NetworkAttachmentDefinition spec defines the desired state of a network attachment'
type: object
properties:
config:
description: 'NetworkAttachmentDefinition config is a JSON-formatted CNI configuration'
type: string
---
kind: ClusterRole
apiVersion: rbac.authorization.k8s.io/v1
metadata:
name: multus
rules:
- apiGroups: ["k8s.cni.cncf.io"]
resources:
- '*'
verbs:
- '*'
- apiGroups:
- ""
resources:
- pods
- pods/status
verbs:
- get
- update
- apiGroups:
- ""
- events.k8s.io
resources:
- events
verbs:
- create
- patch
- update
---
kind: ClusterRoleBinding
apiVersion: rbac.authorization.k8s.io/v1
metadata:
name: multus
roleRef:
apiGroup: rbac.authorization.k8s.io
kind: ClusterRole
name: multus
subjects:
- kind: ServiceAccount
name: multus
namespace: kube-system
---
apiVersion: v1
kind: ServiceAccount
metadata:
name: multus
namespace: kube-system
---
kind: ConfigMap
apiVersion: v1
metadata:
name: multus-daemon-config
namespace: kube-system
labels:
tier: node
app: multus
data:
daemon-config.json: |
{
"chrootDir": "/hostroot",
"confDir": "/host/etc/cni/net.d",
"logToStderr": true,
"logLevel": "debug",
"logFile": "/tmp/multus.log",
"binDir": "/opt/cni/bin",
"cniDir": "/var/lib/cni/multus",
"socketDir": "/host/run/multus/"
}
---
apiVersion: apps/v1
kind: DaemonSet
metadata:
name: kube-multus-ds
namespace: kube-system
labels:
tier: node
app: multus
name: multus
spec:
selector:
matchLabels:
name: multus
updateStrategy:
type: RollingUpdate
template:
metadata:
labels:
tier: node
app: multus
name: multus
spec:
hostNetwork: true
hostPID: true
tolerations:
- operator: Exists
effect: NoSchedule
- operator: Exists
effect: NoExecute
serviceAccountName: multus
containers:
- name: kube-multus
image: ghcr.io/k8snetworkplumbingwg/multus-cni:snapshot-thick
command: [ "/usr/src/multus-cni/bin/multus-daemon" ]
args:
- "-cni-version=0.3.1"
- "-cni-config-dir=/host/etc/cni/net.d"
- "-multus-autoconfig-dir=/host/etc/cni/net.d"
- "-multus-log-to-stderr=true"
- "-multus-log-level=verbose"
resources:
requests:
cpu: "100m"
memory: "50Mi"
limits:
cpu: "100m"
memory: "50Mi"
securityContext:
privileged: true
volumeMounts:
- name: cni
mountPath: /host/etc/cni/net.d
- name: host-run
mountPath: /host/run
- name: host-var-lib-cni-multus
mountPath: /var/lib/cni/multus
- name: host-var-lib-kubelet
mountPath: /var/lib/kubelet
- name: host-run-k8s-cni-cncf-io
mountPath: /run/k8s.cni.cncf.io
- name: host-run-netns
mountPath: /run/netns
mountPropagation: HostToContainer
- name: multus-daemon-config
mountPath: /etc/cni/net.d/multus.d
readOnly: true
- name: hostroot
mountPath: /hostroot
mountPropagation: HostToContainer
initContainers:
- name: install-multus-binary
image: ghcr.io/k8snetworkplumbingwg/multus-cni:snapshot-thick
command:
- "cp"
- "/usr/src/multus-cni/bin/multus-shim"
- "/host/opt/cni/bin/multus-shim"
resources:
requests:
cpu: "10m"
memory: "15Mi"
securityContext:
privileged: true
volumeMounts:
- name: cnibin
mountPath: /host/opt/cni/bin
mountPropagation: Bidirectional
terminationGracePeriodSeconds: 10
volumes:
- name: cni
hostPath:
path: /etc/cni/net.d
- name: cnibin
hostPath:
path: /opt/cni/bin
- name: hostroot
hostPath:
path: /
- name: multus-daemon-config
configMap:
name: multus-daemon-config
items:
- key: daemon-config.json
path: daemon-config.json
- name: host-run
hostPath:
path: /run
- name: host-var-lib-cni-multus
hostPath:
path: /var/lib/cni/multus
- name: host-var-lib-kubelet
hostPath:
path: /var/lib/kubelet
- name: host-run-k8s-cni-cncf-io
hostPath:
path: /run/k8s.cni.cncf.io
- name: host-run-netns
hostPath:
path: /run/netns/

View File

@@ -0,0 +1,233 @@
# Note:
# This deployment file is designed for 'quickstart' of multus, easy installation to test it,
# hence this deployment yaml does not care about following things intentionally.
# - various configuration options
# - minor deployment scenario
# - upgrade/update/uninstall scenario
# Multus team understand users deployment scenarios are diverse, hence we do not cover
# comprehensive deployment scenario. We expect that it is covered by each platform deployment.
---
apiVersion: apiextensions.k8s.io/v1
kind: CustomResourceDefinition
metadata:
name: network-attachment-definitions.k8s.cni.cncf.io
spec:
group: k8s.cni.cncf.io
scope: Namespaced
names:
plural: network-attachment-definitions
singular: network-attachment-definition
kind: NetworkAttachmentDefinition
shortNames:
- net-attach-def
versions:
- name: v1
served: true
storage: true
schema:
openAPIV3Schema:
description: 'NetworkAttachmentDefinition is a CRD schema specified by the Network Plumbing
Working Group to express the intent for attaching pods to one or more logical or physical
networks. More information available at: https://github.com/k8snetworkplumbingwg/multi-net-spec'
type: object
properties:
apiVersion:
description: 'APIVersion defines the versioned schema of this represen
tation of an object. Servers should convert recognized schemas to the
latest internal value, and may reject unrecognized values. More info:
https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources'
type: string
kind:
description: 'Kind is a string value representing the REST resource this
object represents. Servers may infer this from the endpoint the client
submits requests to. Cannot be updated. In CamelCase. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#types-kinds'
type: string
metadata:
type: object
spec:
description: 'NetworkAttachmentDefinition spec defines the desired state of a network attachment'
type: object
properties:
config:
description: 'NetworkAttachmentDefinition config is a JSON-formatted CNI configuration'
type: string
---
kind: ClusterRole
apiVersion: rbac.authorization.k8s.io/v1
metadata:
name: multus
rules:
- apiGroups: ["k8s.cni.cncf.io"]
resources:
- '*'
verbs:
- '*'
- apiGroups:
- ""
resources:
- pods
- pods/status
verbs:
- get
- update
- apiGroups:
- ""
- events.k8s.io
resources:
- events
verbs:
- create
- patch
- update
---
kind: ClusterRoleBinding
apiVersion: rbac.authorization.k8s.io/v1
metadata:
name: multus
roleRef:
apiGroup: rbac.authorization.k8s.io
kind: ClusterRole
name: multus
subjects:
- kind: ServiceAccount
name: multus
namespace: kube-system
---
apiVersion: v1
kind: ServiceAccount
metadata:
name: multus
namespace: kube-system
---
kind: ConfigMap
apiVersion: v1
metadata:
name: multus-cni-config
namespace: kube-system
labels:
tier: node
app: multus
data:
# NOTE: If you'd prefer to manually apply a configuration file, you may create one here.
# In the case you'd like to customize the Multus installation, you should change the arguments to the Multus pod
# change the "args" line below from
# - "--multus-conf-file=auto"
# to:
# "--multus-conf-file=/tmp/multus-conf/70-multus.conf"
# Additionally -- you should ensure that the name "70-multus.conf" is the alphabetically first name in the
# /etc/cni/net.d/ directory on each node, otherwise, it will not be used by the Kubelet.
cni-conf.json: |
{
"name": "multus-cni-network",
"type": "multus",
"capabilities": {
"portMappings": true
},
"delegates": [
{
"cniVersion": "0.3.1",
"name": "default-cni-network",
"plugins": [
{
"type": "flannel",
"name": "flannel.1",
"delegate": {
"isDefaultGateway": true,
"hairpinMode": true
}
},
{
"type": "portmap",
"capabilities": {
"portMappings": true
}
}
]
}
],
"kubeconfig": "/etc/cni/net.d/multus.d/multus.kubeconfig"
}
---
apiVersion: apps/v1
kind: DaemonSet
metadata:
name: kube-multus-ds
namespace: kube-system
labels:
tier: node
app: multus
name: multus
spec:
selector:
matchLabels:
name: multus
updateStrategy:
type: RollingUpdate
template:
metadata:
labels:
tier: node
app: multus
name: multus
spec:
hostNetwork: true
tolerations:
- operator: Exists
effect: NoSchedule
- operator: Exists
effect: NoExecute
serviceAccountName: multus
containers:
- name: kube-multus
image: ghcr.io/k8snetworkplumbingwg/multus-cni:stable
command: ["/entrypoint.sh"]
args:
- "--multus-conf-file=auto"
- "--cni-version=0.3.1"
resources:
requests:
cpu: "100m"
memory: "50Mi"
limits:
cpu: "100m"
memory: "50Mi"
securityContext:
privileged: true
volumeMounts:
- name: cni
mountPath: /host/etc/cni/net.d
- name: cnibin
mountPath: /host/opt/cni/bin
- name: multus-cfg
mountPath: /tmp/multus-conf
initContainers:
- name: install-multus-binary
image: ghcr.io/k8snetworkplumbingwg/multus-cni:stable
command:
- "cp"
- "/usr/src/multus-cni/bin/multus"
- "/host/opt/cni/bin/multus"
resources:
requests:
cpu: "10m"
memory: "15Mi"
securityContext:
privileged: true
volumeMounts:
- name: cnibin
mountPath: /host/opt/cni/bin
mountPropagation: Bidirectional
terminationGracePeriodSeconds: 10
volumes:
- name: cni
hostPath:
path: /etc/cni/net.d
- name: cnibin
hostPath:
path: /opt/cni/bin
- name: multus-cfg
configMap:
name: multus-cni-config
items:
- key: cni-conf.json
path: 70-multus.conf

View File

@@ -1,30 +0,0 @@
## Development Information
## How to build the multus-cni?
```
git clone https://github.com/intel/multus-cni.git
cd multus-cni
./build
```
## How to run CI tests?
Multus has go unit tests (based on ginkgo framework). Following commands drive CI tests manually in your environment:
```
sudo ./test.sh
```
## Logging Best Practices
Followings are multus logging best practices:
* Add `logging.Debugf()` at the begining of function
* In case of error handling, use `logging.Errorf()` with given error info
* `logging.Panicf()` only be used at very critical error (it should NOT used usually)
## CI Introduction
TBD

View File

@@ -1,470 +0,0 @@
## How to use multus-cni?
### Prerequisites
* Kubelet configured to use CNI
* Kubernetes version with CRD support (generally )
Your Kubelet(s) must be configured to run with the CNI network plugin. Please see [Kubernetes document for CNI](https://kubernetes.io/docs/concepts/extend-kubernetes/compute-storage-net/network-plugins/#cni) for more details.
### Install multus
Generally we recommend two options: Manually place a Multus binary in your `/opt/cni/bin`, or use our [quick-start method](quickstart.md) -- which creates a daemonset that has an opinionated way of how to install & configure Multus CNI (recommended).
*Copy Multus Binary into place*
You may acquire the Multus binary via compilation (see the [developer guide](development.md)) or download the a binary from the [GitHub releases](https://github.com/intel/multus-cni/releases) page. Copy multus binary into CNI binary directory, usually `/opt/cni/bin`. Perform this on all nodes in your cluster (master and nodes).
$ cp multus /opt/cni/bin
*Via Daemonset method*
As a [quickstart](quickstart.md), you may apply these YAML files (included in the clone of this repository). Run this command (typically you would run this on the master, or wherever you have access to the `kubectl` command to manage your cluster).
$ cat ./images/{multus-daemonset.yml,flannel-daemonset.yml} | kubectl apply -f -
If you need more comprehensive detail, continue along with this guide, otherwise, you may wish to either [follow the quickstart guide]() or skip to the ['Create network attachment definition'](#create-network-attachment-definition) section.
### Set up conf file in /etc/cni/net.d/ (Installed automatically by Daemonset)
**If you use daemonset to install multus, skip this section and go to "Create network attachment"**
You put CNI config file in `/etc/cni/net.d`. Kubernetes CNI runtime uses the alphabetically first file in the directory. (`"NOTE1"`, `"NOTE2"` are just comments, you can remove them at your configuration)
Execute following commands at all Kubernetes nodes (i.e. master and minions)
```
$ mkdir -p /etc/cni/net.d
$ cat >/etc/cni/net.d/30-multus.conf <<EOF
{
"name": "multus-cni-network",
"type": "multus",
"readinessindicatorfile": "/var/run/flannel/subnet.env",
"delegates": [
{
"NOTE1": "This is example, wrote your CNI config in delegates",
"NOTE2": "If you use flannel, you also need to run flannel daemonset before!",
"type": "flannel",
"name": "flannel.1",
"delegate": {
"isDefaultGateway": true
}
}
],
"kubeconfig": "/etc/cni/net.d/multus.d/multus.kubeconfig"
}
EOF
```
For the detail, please take a look into [Configuration Reference](configuration.md)
**NOTE: You can use "clusterNetwork"/"defaultNetworks" instead of "delegates", see []() for the detail**
As above config, you need to set `"kubeconfig"` in the config file for NetworkAttachmentDefinition(CRD).
##### Which network will be used for "Pod IP"?
In case of "delegates", the first delegates network will be used for "Pod IP". Otherwise, "clusterNetwork" will be used for "Pod IP".
#### Create ServiceAccount, ClusterRole and its binding
Create resources for multus to access CRD objects as following command:
```
# Execute following commands at Kubernetes master
$ cat <<EOF | kubectl create -f -
apiVersion: v1
kind: ServiceAccount
metadata:
name: multus
namespace: kube-system
---
kind: ClusterRole
apiVersion: rbac.authorization.k8s.io/v1beta1
metadata:
name: multus
rules:
- apiGroups: ["k8s.cni.cncf.io"]
resources:
- '*'
verbs:
- '*'
- apiGroups:
- ""
resources:
- pods
- pods/status
verbs:
- get
- update
---
kind: ClusterRoleBinding
apiVersion: rbac.authorization.k8s.io/v1beta1
metadata:
name: multus
roleRef:
apiGroup: rbac.authorization.k8s.io
kind: ClusterRole
name: multus
subjects:
- kind: ServiceAccount
name: multus
namespace: kube-system
EOF
```
#### Set up kubeconfig file
Create kubeconfig at master node as following commands:
```
# Execute following command at Kubernetes master
$ mkdir -p /etc/cni/net.d/multus.d
$ SERVICEACCOUNT_CA=$(kubectl get secrets -n=kube-system -o json | jq -r '.items[]|select(.metadata.annotations."kubernetes.io/service-account.name"=="multus")| .data."ca.crt"')
$ SERVICEACCOUNT_TOKEN=$(kubectl get secrets -n=kube-system -o json | jq -r '.items[]|select(.metadata.annotations."kubernetes.io/service-account.name"=="multus")| .data.token' | base64 -d )
$ KUBERNETES_SERVICE_PROTO=$(kubectl get all -o json | jq -r .items[0].spec.ports[0].name)
$ KUBERNETES_SERVICE_HOST=$(kubectl get all -o json | jq -r .items[0].spec.clusterIP)
$ KUBERNETES_SERVICE_PORT=$(kubectl get all -o json | jq -r .items[0].spec.ports[0].port)
$ cat > /etc/cni/net.d/multus.d/multus.kubeconfig <<EOF
# Kubeconfig file for Multus CNI plugin.
apiVersion: v1
kind: Config
clusters:
- name: local
cluster:
server: ${KUBERNETES_SERVICE_PROTOCOL:-https}://${KUBERNETES_SERVICE_HOST}:${KUBERNETES_SERVICE_PORT}
certificate-authority-data: ${SERVICEACCOUNT_CA}
users:
- name: multus
user:
token: "${SERVICEACCOUNT_TOKEN}"
contexts:
- name: multus-context
context:
cluster: local
user: multus
current-context: multus-context
EOF
```
Copy `/etc/cni/net.d/multus.d/multus.kubeconfig` into other Kubernetes nodes
**NOTE: Recommend to exec 'chmod 600 /etc/cni/net.d/multus.d/multus.kubeconfig' to keep secure**
```
$ scp /etc/cni/net.d/multus.d/multus.kubeconfig ...
```
### Setup CRDs (daemonset automatically does)
**If you use daemonset to install multus, skip this section and go to "Create network attachment"**
Create CRD definition in Kubernetes as following command at master node:
```
# Execute following command at Kubernetes master
$ cat <<EOF | kubectl create -f -
apiVersion: apiextensions.k8s.io/v1beta1
kind: CustomResourceDefinition
metadata:
name: network-attachment-definitions.k8s.cni.cncf.io
spec:
group: k8s.cni.cncf.io
version: v1
scope: Namespaced
names:
plural: network-attachment-definitions
singular: network-attachment-definition
kind: NetworkAttachmentDefinition
shortNames:
- net-attach-def
validation:
openAPIV3Schema:
properties:
spec:
properties:
config:
type: string
EOF
```
### Create network attachment definition
The 'NetworkAttachmentDefinition' is used to setup the network attachment, i.e. secondary interface for the pod, There are two ways to configure the 'NetworkAttachmentDefinition' as following:
- NetworkAttachmentDefinition with json CNI config
- NetworkAttachmentDefinition with CNI config file
#### NetworkAttachmentDefinition with json CNI config:
Following command creates NetworkAttachmentDefinition. CNI config is in `config:` field.
```
# Execute following command at Kubernetes master
$ cat <<EOF | kubectl create -f -
apiVersion: "k8s.cni.cncf.io/v1"
kind: NetworkAttachmentDefinition
metadata:
name: macvlan-conf-1
spec:
config: '{
"cniVersion": "0.3.0",
"type": "macvlan",
"master": "eth1",
"mode": "bridge",
"ipam": {
"type": "host-local",
"ranges": [
[ {
"subnet": "10.10.0.0/16",
"rangeStart": "10.10.1.20",
"rangeEnd": "10.10.3.50",
"gateway": "10.10.0.254"
} ]
]
}
}'
EOF
```
#### NetworkAttachmentDefinition with CNI config file:
If NetworkAttachmentDefinition has no spec, multus find a file in defaultConfDir ('/etc/cni/multus/net.d', with same name in the 'name' field of CNI config.
```
# Execute following command at Kubernetes master
$ cat <<EOF | kubectl create -f -
apiVersion: "k8s.cni.cncf.io/v1"
kind: NetworkAttachmentDefinition
metadata:
name: macvlan-conf-2
EOF
```
```
# Execute following commands at all Kubernetes nodes (i.e. master and minions)
$ cat <<EOF > /etc/cni/multus/net.d/macvlan2.conf
{
"cniVersion": "0.3.0",
"type": "macvlan",
"name": "macvlan-conf-2",
"master": "eth1",
"mode": "bridge",
"ipam": {
"type": "host-local",
"ranges": [
[ {
"subnet": "11.10.0.0/16",
"rangeStart": "11.10.1.20",
"rangeEnd": "11.10.3.50"
} ]
]
}
}
```
### Run pod with network annotation
#### Lauch pod with text annotation
```
# Execute following command at Kubernetes master
$ cat <<EOF | kubectl create -f -
apiVersion: v1
kind: Pod
metadata:
name: pod-case-01
annotations:
k8s.v1.cni.cncf.io/networks: macvlan-conf-1, macvlan-conf-2
spec:
containers:
- name: pod-case-01
image: docker.io/centos/tools:latest
command:
- /sbin/init
EOF
```
#### Lauch pod with text annotation for NetworkAttachmentDefinition in different namespace
You can also specify NetworkAttachmentDefinition with its namespace as adding `<namespace>/`
```
# Execute following command at Kubernetes master
$ cat <<EOF | kubectl create -f -
apiVersion: "k8s.cni.cncf.io/v1"
kind: NetworkAttachmentDefinition
metadata:
name: macvlan-conf-3
namespace: testns1
spec:
config: '{
"cniVersion": "0.3.0",
"type": "macvlan",
"master": "eth1",
"mode": "bridge",
"ipam": {
"type": "host-local",
"ranges": [
[ {
"subnet": "12.10.0.0/16",
"rangeStart": "12.10.1.20",
"rangeEnd": "12.10.3.50"
} ]
]
}
}'
EOF
$ cat <<EOF | kubectl create -f -
apiVersion: v1
kind: Pod
metadata:
name: pod-case-02
annotations:
k8s.v1.cni.cncf.io/networks: testns1/macvlan-conf-3
spec:
containers:
- name: pod-case-02
image: docker.io/centos/tools:latest
command:
- /sbin/init
EOF
```
#### Lauch pod with text annotation with interface name
You can also specify interface name as adding `@<ifname>`.
```
# Execute following command at Kubernetes master
$ cat <<EOF | kubectl create -f -
apiVersion: v1
kind: Pod
metadata:
name: pod-case-03
annotations:
k8s.v1.cni.cncf.io/networks: macvlan-conf-1@macvlan1
spec:
containers:
- name: pod-case-03
image: docker.io/centos/tools:latest
command:
- /sbin/init
EOF
```
#### Lauch pod with json annotation
```
# Execute following command at Kubernetes master
$ cat <<EOF | kubectl create -f -
apiVersion: v1
kind: Pod
metadata:
name: pod-case-04
annotations:
k8s.v1.cni.cncf.io/networks: '[
{ "name" : "macvlan-conf-1" },
{ "name" : "macvlan-conf-2" }
]'
spec:
containers:
- name: pod-case-04
image: docker.io/centos/tools:latest
command:
- /sbin/init
EOF
```
#### Lauch pod with json annotation for NetworkAttachmentDefinition in different namespace
You can also specify NetworkAttachmentDefinition with its namespace as adding `"namespace": "<namespace>"`.
```
# Execute following command at Kubernetes master
$ cat <<EOF | kubectl create -f -
apiVersion: v1
kind: Pod
metadata:
name: pod-case-05
annotations:
k8s.v1.cni.cncf.io/networks: '[
{ "name" : "macvlan-conf-1",
"namespace": "testns1" }
]'
spec:
containers:
- name: pod-case-05
image: docker.io/centos/tools:latest
command:
- /sbin/init
EOF
```
#### Lauch pod with json annotation with interface
You can also specify interface name as adding `"interfaceRequest": "<ifname>"`.
```
# Execute following command at Kubernetes master
$ cat <<EOF | kubectl create -f -
apiVersion: v1
kind: Pod
metadata:
name: pod-case-06
annotations:
k8s.v1.cni.cncf.io/networks: '[
{ "name" : "macvlan-conf-1",
"interfaceRequest": "macvlan1" },
{ "name" : "macvlan-conf-2" }
]'
spec:
containers:
- name: pod-case-06
image: docker.io/centos/tools:latest
command:
- /sbin/init
EOF
```
### Verifying pod network
Following the example of `ip -d address` output of above pod, "pod-case-06":
```
# Execute following command at Kubernetes master
$ kubectl exec -it pod-case-06 -- ip -d address
1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue state UNKNOWN group default qlen 1
link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00 promiscuity 0 numtxqueues 1 numrxqueues 1 gso_max_size 65536 gso_max_segs 65535
inet 127.0.0.1/8 scope host lo
valid_lft forever preferred_lft forever
inet6 ::1/128 scope host
valid_lft forever preferred_lft forever
3: eth0@if11: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1450 qdisc noqueue state UP group default
link/ether 0a:58:0a:f4:02:06 brd ff:ff:ff:ff:ff:ff link-netnsid 0 promiscuity 0
veth numtxqueues 1 numrxqueues 1 gso_max_size 65536 gso_max_segs 65535
inet 10.244.2.6/24 scope global eth0
valid_lft forever preferred_lft forever
inet6 fe80::ac66:45ff:fe7c:3a19/64 scope link
valid_lft forever preferred_lft forever
4: macvlan1@if3: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc noqueue state UNKNOWN group default
link/ether 4e:6d:7a:4e:14:87 brd ff:ff:ff:ff:ff:ff link-netnsid 0 promiscuity 0
macvlan mode bridge numtxqueues 1 numrxqueues 1 gso_max_size 65536 gso_max_segs 65535
inet 10.10.1.22/16 scope global macvlan1
valid_lft forever preferred_lft forever
inet6 fe80::4c6d:7aff:fe4e:1487/64 scope link
valid_lft forever preferred_lft forever
5: net2@if3: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc noqueue state UNKNOWN group default
link/ether 6e:e3:71:7f:86:f7 brd ff:ff:ff:ff:ff:ff link-netnsid 0 promiscuity 0
macvlan mode bridge numtxqueues 1 numrxqueues 1 gso_max_size 65536 gso_max_segs 65535
inet 11.10.1.22/16 scope global net2
valid_lft forever preferred_lft forever
inet6 fe80::6ce3:71ff:fe7f:86f7/64 scope link
valid_lft forever preferred_lft forever
```
| Interface name | Description |
| --- | --- |
| lo | loopback |
| eth0 | Default network interface (flannel) |
| macvlan1 | macvlan interface (macvlan-conf-1) |
| net2 | macvlan interface (macvlan-conf-2) |

View File

@@ -1,184 +0,0 @@
# Quickstart Guide
This guide is intended as a way to get you off the ground, and using Multus CNI to create Kubernetes pods with multiple interfaces. If you're already using Multus and need more detail, see the [comprehensive usage guide](how-to-use.md). This document a quickstart and a getting started guide in one, intended for your first run-through of Multus CNI.
We'll first install Multus CNI, and then we'll setup some configurations so that you can see how multiple interfaces are created for pods.
## Key Concepts
Two things we'll refer to a number of times through this document are:
* "Default network" -- This is your pod-to-pod network. This is how pods communicate among one another in your cluster, how they have connectivity. Generally speaking, this is presented as the interface named `eth0`. This interface is always attached to your pods, so that they can have connectivity among themselves. We'll add interfaces in addition to this.
* "CRDs" -- Custom Resource Definitions. Custom Resources are a way that the Kubernetes API is extended. We use these here to store some information that Multus can read. Primarily, we use these to store the configurations for each of the additional interfaces that are attached to your pods.
## Installation
Our recommended quickstart method to deploy Multus is to deploy using a Daemonset. This method is provided in this guide along with [Flannel](https://github.com/coreos/flannel). Flannel is deployed as a pod-to-pod network that is used as our "default network" -- this provides connectivity between pods in your cluster. Each additional network attachment (i.e. for multiple interfaces in pods) is made in addition to this default network. This guide generally assumes a new Kubernetes cluster that hasn't yet had any networking configured. If it's your first time using Multus, you might consider using a fresh cluster to learn with, and then later configure it to work with an existing cluster.
Firstly, clone this GitHub repository.
```
git clone https://github.com/intel/multus-cni.git && cd multus-cni
```
We'll apply files to `kubectl` from this repo. The files we're applying here specify a "Daemonset" (pods that run on each node in the cluster), this Daemonset handles installing the Multus CNI binary, dropping a default configuration on each node in the cluster -- and then also installs Flannel to use as a default network.
```
$ cat ./images/{multus-daemonset.yml,flannel-daemonset.yml} | kubectl apply -f -
```
Note: For crio runtime use multus-crio-daemonset.yml (crio uses /usr/libexec/cni as default path for plugin directory). Before deploying daemonsets,delete all default network plugin configuration files under /etc/cni/net.d
If the runtime is cri-o, then apply these files.
```
$ cat ./images/{multus-crio-daemonset.yml,flannel-daemonset.yml} | kubectl apply -f -
```
### Validating your installation
Generally, the first step in validating your installation is to look at the `STATUS` field of your nodes, you can check it out by looking at:
```
$ kubectl get nodes
```
This will show each of the nodes in your cluster, take a look at the `STATUS` field, and look for `Ready` to appear for each of your nodes. This readiness is determined by the presence of a CNI configuration file on each of the nodes, and when that file appears.
You may also wish to start any pod in your cluster (without any further configuration), and validate that it works as you'd otherwise expect -- especially that it can communicate over the default network.
## Creating additional interfaces
The first thing we'll do is create configurations for each of the additional interfaces that we attach to pods. We'll do this by creating Custom Resources. Part of the quickstart installation creates a "CRD" -- a custom resource definition that is the home where we keep these custom resources -- we'll store our configurations for each interface in these.
### CNI Configurations
Each configuration we'll add is a CNI configuration. If you're not familiar with them, let's break them down quickly. Here's an example CNI configuration:
```
{
"cniVersion": "0.3.0",
"type": "loopback",
"additional": "information"
}
```
CNI configurations are JSON, and we have a structure here that has a few things we're interested in:
1. `cniVersion`: Tells each CNI plugin which version is being used and can give the plugin information if it's using a too late (or too early) version.
2. `type`: This tells CNI which binary to call on disk. Each CNI plugin is a binary that's called. Typically, these binaries are stored in `/opt/cni/bin` on each node, and CNI executes this binary. In this case we've specified the `loopback` binary (which create a loopback-type network interface). If this is your first time installing Multus, you might want to verify that the plugins that are in the "type" field are actually on disk in the `/opt/cni/bin` directory.
3. `additional`: This field is put here as an example, each CNI plugin can specify whatever configuration parameters they'd like in JSON. These are specific to the binary you're calling in the `type` field.
For an even further example -- take a look at the [bridge CNI plugin README](https://github.com/containernetworking/plugins/tree/master/plugins/main/bridge) which shows additional
If you'd like more information about CNI configuration, you can read [the entire CNI specification](https://github.com/containernetworking/cni/blob/master/SPEC.md). It might also be useful to look at the [CNI reference plugins](https://github.com/containernetworking/plugins) and see how they're configured.
You do not need to reload or refresh the Kubelets when CNI configurations change. These are read on each creation & deletion of pods. So if you change a configuration, it'll apply the next time a pod is created. Existing pods may need to be restarted if they need the new configuration.
### Storing a configuration as a Custom Resource
So, we want to create an additional interface. Let's create a macvlan interface for pods to use. We'll create a custom resource that defines the CNI configuration for interfaces.
Note in the following command that there's a `kind: NetworkAttachmentDefinition`. This is our fancy name for our configuration -- it's a custom extension of Kubernetes that defines how we attach networks to our pods.
Secondarily, note the `config` field. You'll see that this is a CNI configuration just like we explained earlier.
Lastly but *very* importantly, note under `metadata` the `name` field -- here's where we give this configuration a name, and it's how we tell pods to use this configuration. The name here is `macvlan-conf` -- as we're creating a configuration for macvlan.
Here's the command to create this example configuration:
```
cat <<EOF | kubectl create -f -
apiVersion: "k8s.cni.cncf.io/v1"
kind: NetworkAttachmentDefinition
metadata:
name: macvlan-conf
spec:
config: '{
"cniVersion": "0.3.0",
"type": "macvlan",
"master": "eth0",
"mode": "bridge",
"ipam": {
"type": "host-local",
"subnet": "192.168.1.0/24",
"rangeStart": "192.168.1.200",
"rangeEnd": "192.168.1.216",
"routes": [
{ "dst": "0.0.0.0/0" }
],
"gateway": "192.168.1.1"
}
}'
EOF
```
*NOTE*: This example uses `eth0` as the `master` parameter, this master parameter should match the interface name on the hosts in your cluster.
You can see which configurations you've created using `kubectl` here's how you can do that:
```
kubectl get network-attachment-definitions
```
You can get more detail by describing them:
```
kubectl describe network-attachment-definitions macvlan-conf
```
### Creating a pod that attaches an additional interface
We're going to create a pod. This will look familiar as any pod you might have created before, but, we'll have a special `annotations` field -- in this case we'll have an annotation called `k8s.v1.cni.cncf.io/networks`. This field takes a comma delimited list of the names of your `NetworkAttachmentDefinition`s as we created above. Note in the comand below that we have the annotation of `k8s.v1.cni.cncf.io/networks: macvlan-conf` where `macvlan-conf` is the name we used above when we created our configuration.
Let's go ahead and create a pod (that just sleeps for a really long time) with this command:
```
cat <<EOF | kubectl create -f -
apiVersion: v1
kind: Pod
metadata:
name: samplepod
annotations:
k8s.v1.cni.cncf.io/networks: macvlan-conf
spec:
containers:
- name: samplepod
command: ["/bin/bash", "-c", "sleep 2000000000000"]
image: dougbtv/centos-network
EOF
```
You may now inspect the pod and see what interfaces interfaces are attached, like so:
```
$ kubectl exec -it samplepod -- ip a
```
You should note that there's 3 interfaces:
* `lo` a loopback interface
* `eth0` our default network
* `net1` the new interface we created with the macvlan configuration.
### What if I want more interfaces?
You can add more interfaces to a pod by creating more custom resources and then referring to them in pod's annotation. You can also reuse configurations, so for example, to attach two macvlan interfaces to a pod, you could create a pod like so:
```
cat <<EOF | kubectl create -f -
apiVersion: v1
kind: Pod
metadata:
name: samplepod
annotations:
k8s.v1.cni.cncf.io/networks: macvlan-conf,macvlan-conf
spec:
containers:
- name: samplepod
command: ["/bin/bash", "-c", "sleep 2000000000000"]
image: dougbtv/centos-network
EOF
```
Note that the annotation now reads `k8s.v1.cni.cncf.io/networks: macvlan-conf,macvlan-conf`. Where we have the same configuration used twice, separated by a comma.
If you were to create another custom resource with the name `foo` you could use that such as: `k8s.v1.cni.cncf.io/networks: foo,macvlan-conf`, and use any number of attachments.

View File

@@ -5,6 +5,7 @@ Following is the example of multus config file, in `/etc/cni/net.d/`.
```
{
"cniVersion": "0.3.1",
"name": "node-cni-network",
"type": "multus",
"kubeconfig": "/etc/kubernetes/node-kubeconfig.yaml",
@@ -13,6 +14,12 @@ Following is the example of multus config file, in `/etc/cni/net.d/`.
"binDir": "/opt/cni/bin",
"logFile": "/var/log/multus.log",
"logLevel": "debug",
"logOptions": {
"maxAge": 5,
"maxSize": 100,
"maxBackups": 5,
"compress": true
},
"capabilities": {
"portMappings": true
},
@@ -38,18 +45,20 @@ Following is the example of multus config file, in `/etc/cni/net.d/`.
* `type` (string, required): &quot;multus&quot;
* `confDir` (string, optional): directory for CNI config file that multus reads. default `/etc/cni/multus/net.d`
* `cniDir` (string, optional): Multus CNI data directory, default `/var/lib/cni/multus`
* `binDir` (string, optional): directory for CNI plugins which multus calls. default `/opt/cni/bin`
* `kubeconfig` (string, optional): kubeconfig file for the out of cluster communication with kube-apiserver. See the example [kubeconfig](https://github.com/intel/multus-cni/blob/master/doc/node-kubeconfig.yaml). If you would like to use CRD (i.e. network attachment definition), this is required
* `binDir` (string, optional): additional directory for CNI plugins which multus calls, in addition to the default (the default is typically set to `/opt/cni/bin`)
* `kubeconfig` (string, optional): kubeconfig file for the out of cluster communication with kube-apiserver. See the example [kubeconfig](https://github.com/k8snetworkplumbingwg/multus-cni/blob/master/docs/node-kubeconfig.yaml). If you would like to use CRD (i.e. network attachment definition), this is required
* `logToStderr` (bool, optional): Enable or disable logging to `STDERR`. Defaults to true.
* `logFile` (string, optional): file path for log file. multus puts log in given file
* `logLevel` (string, optional): logging level ("debug", "error" or "panic")
* `logLevel` (string, optional): logging level ("debug", "error", "verbose", or "panic")
* `logOptions` (object, optional): logging option, More detailed log configuration
* `namespaceIsolation` (boolean, optional): Enables a security feature where pods are only allowed to access `NetworkAttachmentDefinitions` in the namespace where the pod resides. Defaults to false.
* `capabilities` ({}list, optional): [capabilities](https://github.com/containernetworking/cni/blob/master/CONVENTIONS.md#dynamic-plugin-specific-fields-capabilities--runtime-configuration) supported by at least one of the delegates. (NOTE: Multus only supports portMappings capability for now). See the [example](https://github.com/intel/multus-cni/blob/master/examples/multus-ptp-portmap.conf).
* `readinessindicatorfile`: The path to a file whose existance denotes that the default network is ready
* `capabilities` ({}list, optional): [capabilities](https://github.com/containernetworking/cni/blob/master/CONVENTIONS.md#dynamic-plugin-specific-fields-capabilities--runtime-configuration) supported by at least one of the delegates. (NOTE: Multus only supports portMappings/Bandwidth capability for cluster networks).
* `readinessindicatorfile`: The path to a file whose existence denotes that the default network is ready
User should chose following parameters combination (`clusterNetwork`+`defaultNetworks` or `delegates`):
* `clusterNetwork` (string, required): default CNI network for pods, used in kubernetes cluster (Pod IP and so on): name of network-attachment-definition, CNI json file name (without extention, .conf/.conflist) or directory for CNI config file
* `defaultNetworks` ([]string, required): default CNI network attachment: name of network-attachment-definition, CNI json file name (without extention, .conf/.conflist) or directory for CNI config file
* `clusterNetwork` (string, required): default CNI network for pods, used in kubernetes cluster (Pod IP and so on): name of network-attachment-definition, CNI json file name (without extension, .conf/.conflist), directory for CNI config file or absolute file path for CNI config file
* `defaultNetworks` ([]string, required): default CNI network attachment: name of network-attachment-definition, CNI json file name (without extension, .conf/.conflist), directory for CNI config file or absolute file path for CNI config file
* `systemNamespaces` ([]string, optional): list of namespaces for Kubernetes system (namespaces listed here will not have `defaultNetworks` added)
* `multusNamespace` (string, optional): namespace for `clusterNetwork`/`defaultNetworks`
* `delegates` ([]map,required): number of delegate details in the Multus
@@ -59,8 +68,9 @@ User should chose following parameters combination (`clusterNetwork`+`defaultNet
Multus will find network for clusterNetwork/defaultNetworks as following sequences:
1. CRD object for given network name, in 'kube-system' namespace
1. CNI json config file in `confDir`. Given name should be without extention, like .conf/.conflist. (e.g. "test" for "test.conf")
1. CNI json config file in `confDir`. Given name should be without extension, like .conf/.conflist. (e.g. "test" for "test.conf"). The given name for `clusterNetwork` should match the value for `name` key in the config file (e.g. `"name": "test"` in "test.conf" when `"clusterNetwork": "test"`)
1. Directory for CNI json config file. Multus will find alphabetically first file for the network
1. File path for CNI json confile file.
1. Multus failed to find network. Multus raise error message
## Miscellaneous config
@@ -75,7 +85,7 @@ In this manner, you may prevent pods from crash looping, and instead wait for th
Only one option is necessary to configure this functionality:
* `readinessindicatorfile`: The path to a file whose existance denotes that the default network is ready.
* `readinessindicatorfile`: The path to a file whose existence denotes that the default network is ready.
*NOTE*: If `readinessindicatorfile` is unset, or is an empty string, this functionality will be disabled, and is disabled by default.
@@ -84,7 +94,15 @@ Only one option is necessary to configure this functionality:
You may wish to enable some enhanced logging for Multus, especially during the process where you're configuring Multus and need to understand what is or isn't working with your particular configuration.
Multus will always log via `STDERR`, which is the standard method by which CNI plugins communicate errors, and these errors are logged by the Kubelet. This method is always enabled.
#### Logging via STDERR
By default, Multus will log via `STDERR`, which is the standard method by which CNI plugins communicate errors, and these errors are logged by the Kubelet.
Optionally, you may disable this method by setting the `logToStderr` option in your CNI configuration:
```
"logToStderr": false,
```
#### Writing to a Log File
@@ -93,7 +111,7 @@ Optionally, you may have Multus log to a file on the filesystem. This file will
For example in your CNI configuration, you may set:
```
"LogFile": "/var/log/multus.log",
"logFile": "/var/log/multus.log",
```
#### Logging Level
@@ -103,19 +121,44 @@ The default logging level is set as `panic` -- this will log only the most criti
The available logging level values, in decreasing order of verbosity are:
* `debug`
* `verbose`
* `error`
* `panic`
You may configure the logging level by using the `LogLevel` option in your CNI configuration. For example:
```
"LogLevel": "debug",
"logLevel": "debug",
```
#### Logging Options
If you want a more detailed configuration of the logging, This includes the following parameters:
* `maxAge` the maximum number of days to retain old log files in their filename
* `maxSize` the maximum size in megabytes of the log file before it gets rotated
* `maxBackups` the maximum number of days to retain old log files in their filename
* `compress` compress determines if the rotated log files should be compressed using gzip
For example in your CNI configuration, you may set:
```
"logOptions": {
"maxAge": 5,
"maxSize": 100,
"maxBackups": 5,
"compress": true
}
```
### Namespace Isolation
The functionality provided by the `namespaceIsolation` configuration option enables a mode where Multus only allows pods to access custom resources (the `NetworkAttachmentDefinitions`) within the namespace where that pod resides. In other words, the `NetworkAttachmentDefinitions` are isolated to usage within the namespace in which they're created.
**NOTE**: The default namespace is special in this scenario. Even with namespace isolation enabled, any pod, in any namespace is allowed to refer to `NetworkAttachmentDefinitions` in the default namespace. This allows you to create commonly used unprivileged `NetworkAttachmentDefinitions` without having to put them in all namespaces. For example, if you had a `NetworkAttachmentDefinition` named `foo` the default namespace, you may reference it in an annotation with: `default/foo`.
**NOTE**: You can also add additional namespaces which can be referred to globally using the `global-namespaces` option (see next section).
For example, if a pod is created in the namespace called `development`, Multus will not allow networks to be attached when defined by custom resources created in a different namespace, say in the `default` network.
Consider the situation where you have a system that has users of different privilege levels -- as an example, a platform which has two administrators: a Senior Administrator and a Junior Administrator. The Senior Administrator may have access to all namespaces, and some network configurations as used by Multus are considered to be privileged in that they allow access to some protected resources available on the network. However, the Junior Administrator has access to only a subset of namespaces, and therefore it should be assumed that the Junior Administrator cannot create pods in their limited subset of namespaces. The `namespaceIsolation` feature provides for this isolation, allowing pods created in given namespaces to only access custom resources in the same namespace as the pod.
@@ -212,7 +255,7 @@ pod/samplepod created
You'll note that pod fails to spawn successfully. If you check the Multus logs, you'll see an entry such as:
```
2018-12-18T21:41:32Z [error] GetPodNetwork: namespace isolation violation: podnamespace: development / target namespace: privileged
2018-12-18T21:41:32Z [error] GetNetworkDelegates: namespace isolation enabled, annotation violates permission, pod is in namespace development but refers to target namespace privileged
```
This error expresses that the pod resides in the namespace named `development` but refers to a `NetworkAttachmentDefinition` outside of that namespace, in this case, the namespace named `privileged`.
@@ -250,6 +293,16 @@ NAME READY STATUS RESTARTS AGE
samplepod 1/1 Running 0 31s
```
### Allow specific namespaces to be used across namespaces when using namespace isolation
The `globalNamespaces` configuration option is only used when `namespaceIsolation` is set to true. `globalNamespaces` specifies a comma-delimited list of namespaces which can be referred to from outside of any given namespace in which a pod resides.
```
"globalNamespaces": "default,namespace-a,namespace-b",
```
Note that when using `globalNamespaces` the `default` namespace must be specified in the list if you wish to use that namespace, when `globalNamespaces` is not set, the `default` namespace is implied to be used across namespaces.
### Specify default cluster network in Pod annotations
Users may also specify the default network for any given pod (via annotation), for cases where there are multiple cluster networks available within a Kubernetes cluster.

56
docs/development.md Normal file
View File

@@ -0,0 +1,56 @@
## Development/Support Information
## Which Kubernetes version is supported in multus?
Currently multus team supports Kubernetes that Kubernetes community maintains.
See [Version Skew Policy](https://kubernetes.io/releases/version-skew-policy/) for the details.
## How to utilize multus-cni code as library?
Multus now uses [gopkg.in](http://gopkg.in/) to expose its code as library.
You can use following command to import our code into your go code.
```
go get gopkg.in/k8snetworkplumbingwg/multus-cni.v3
```
## How do I submit an issue?
Use GitHub as normally, you'll be presented with an option to submit a issue or enhancement request.
Issues are considered stale after 90 days. After which, the maintainers reserve the right to close an issue.
Typically, we'll tag the submitter and ask for more information if necessary before closing.
If an issue is closed that you don't feel is sufficiently resolved, please feel free to re-open the issue and provide any necessary information.
## How do I build multus-cni?
You can use the built in `./hack/build-go.sh` script!
```
git clone https://github.com/k8snetworkplumbingwg/multus-cni.git
cd multus-cni
./hack/build-go.sh
```
## How do I run CI tests?
Multus has go unit tests (based on ginkgo framework).The following commands drive CI tests manually in your environment:
```
sudo ./hack/test-go.sh
```
## What are the best practices for logging?
The following are the best practices for multus logging:
* Add `logging.Debugf()` at the beginning of functions
* In case of error handling, use `logging.Errorf()` with given error info
* `logging.Panicf()` only be used for critical errors (it should NOT normally be used)
## Multus release schedule
On the first maintainer's meeting, twice yearly, after January 1st and July 1st, if a new version has not been tagged, a new version will tagged.

640
docs/how-to-use.md Normal file
View File

@@ -0,0 +1,640 @@
## Multus CNI usage guide
### Prerequisites
* Kubelet configured to use CNI
* Kubernetes version with CRD support (generally )
Your Kubelet(s) must be configured to run with the CNI network plugin. Please see [Kubernetes document for CNI](https://kubernetes.io/docs/concepts/extend-kubernetes/compute-storage-net/network-plugins/#cni) for more details.
### Install Multus
Generally we recommend two options: Manually place a Multus binary in your `/opt/cni/bin`, or use our [quick-start method](quickstart.md) -- which creates a daemonset that has an opinionated way of how to install & configure Multus CNI (recommended).
*Copy Multus Binary into place*
You may acquire the Multus binary via compilation (see the [developer guide](development.md)) or download the a binary from the [GitHub releases](https://github.com/k8snetworkplumbingwg/multus-cni/releases) page. Copy multus binary into CNI binary directory, usually `/opt/cni/bin`. Perform this on all nodes in your cluster (master and nodes).
cp multus /opt/cni/bin
*Via Daemonset method*
As a [quickstart](quickstart.md), you may apply these YAML files (included in the clone of this repository). Run this command (typically you would run this on the master, or wherever you have access to the `kubectl` command to manage your cluster).
cat ./deployments/multus-daemonset.yml | kubectl apply -f - # thin deployment
or
cat ./deployments/multus-daemonset-thick.yml | kubectl apply -f - # thick (client/server) deployment
If you need more comprehensive detail, continue along with this guide, otherwise, you may wish to either [follow the quickstart guide]() or skip to the ['Create network attachment definition'](#create-network-attachment-definition) section.
### Set up conf file in /etc/cni/net.d/ (Installed automatically by Daemonset)
**If you use daemonset to install multus, skip this section and go to "Create network attachment"**
You put CNI config file in `/etc/cni/net.d`. Kubernetes CNI runtime uses the alphabetically first file in the directory. (`"NOTE1"`, `"NOTE2"` are just comments, you can remove them at your configuration)
Execute following commands at all Kubernetes nodes (i.e. master and minions)
```
mkdir -p /etc/cni/net.d
cat >/etc/cni/net.d/00-multus.conf <<EOF
{
"name": "multus-cni-network",
"type": "multus",
"readinessindicatorfile": "/run/flannel/subnet.env",
"delegates": [
{
"NOTE1": "This is example, wrote your CNI config in delegates",
"NOTE2": "If you use flannel, you also need to run flannel daemonset before!",
"type": "flannel",
"name": "flannel.1",
"delegate": {
"isDefaultGateway": true
}
}
],
"kubeconfig": "/etc/cni/net.d/multus.d/multus.kubeconfig"
}
EOF
```
For the detail, please take a look into [Configuration Reference](configuration.md)
**NOTE: You can use "clusterNetwork"/"defaultNetworks" instead of "delegates", see []() for the detail**
As above config, you need to set `"kubeconfig"` in the config file for NetworkAttachmentDefinition(CRD).
##### Which network will be used for "Pod IP"?
In case of "delegates", the first delegates network will be used for "Pod IP". Otherwise, "clusterNetwork" will be used for "Pod IP".
#### Create ServiceAccount, ClusterRole and its binding
Create resources for multus to access CRD objects as following command:
```
# Execute following commands at Kubernetes master
cat <<EOF | kubectl create -f -
apiVersion: v1
kind: ServiceAccount
metadata:
name: multus
namespace: kube-system
---
kind: ClusterRole
apiVersion: rbac.authorization.k8s.io/v1beta1
metadata:
name: multus
rules:
- apiGroups: ["k8s.cni.cncf.io"]
resources:
- '*'
verbs:
- '*'
- apiGroups:
- ""
resources:
- pods
- pods/status
verbs:
- get
- update
---
kind: ClusterRoleBinding
apiVersion: rbac.authorization.k8s.io/v1beta1
metadata:
name: multus
roleRef:
apiGroup: rbac.authorization.k8s.io
kind: ClusterRole
name: multus
subjects:
- kind: ServiceAccount
name: multus
namespace: kube-system
EOF
```
#### Set up kubeconfig file
Create kubeconfig at master node as following commands:
```
# Execute following command at Kubernetes master
mkdir -p /etc/cni/net.d/multus.d
SERVICEACCOUNT_CA=$(kubectl get secrets -n=kube-system -o json | jq -r '.items[]|select(.metadata.annotations."kubernetes.io/service-account.name"=="multus")| .data."ca.crt"')
SERVICEACCOUNT_TOKEN=$(kubectl get secrets -n=kube-system -o json | jq -r '.items[]|select(.metadata.annotations."kubernetes.io/service-account.name"=="multus")| .data.token' | base64 -d )
KUBERNETES_SERVICE_PROTO=$(kubectl get all -o json | jq -r .items[0].spec.ports[0].name)
KUBERNETES_SERVICE_HOST=$(kubectl get all -o json | jq -r .items[0].spec.clusterIP)
KUBERNETES_SERVICE_PORT=$(kubectl get all -o json | jq -r .items[0].spec.ports[0].port)
cat > /etc/cni/net.d/multus.d/multus.kubeconfig <<EOF
# Kubeconfig file for Multus CNI plugin.
apiVersion: v1
kind: Config
clusters:
- name: local
cluster:
server: ${KUBERNETES_SERVICE_PROTOCOL:-https}://${KUBERNETES_SERVICE_HOST}:${KUBERNETES_SERVICE_PORT}
certificate-authority-data: ${SERVICEACCOUNT_CA}
users:
- name: multus
user:
token: "${SERVICEACCOUNT_TOKEN}"
contexts:
- name: multus-context
context:
cluster: local
user: multus
current-context: multus-context
EOF
```
Copy `/etc/cni/net.d/multus.d/multus.kubeconfig` into other Kubernetes nodes
**NOTE: Recommend to exec 'chmod 600 /etc/cni/net.d/multus.d/multus.kubeconfig' to keep secure**
```
scp /etc/cni/net.d/multus.d/multus.kubeconfig ...
```
### Setup CRDs (daemonset automatically does)
**If you use daemonset to install multus, skip this section and go to "Create network attachment"**
Create CRD definition in Kubernetes as following command at master node:
```
# Execute following command at Kubernetes master
cat <<EOF | kubectl create -f -
apiVersion: apiextensions.k8s.io/v1beta1
kind: CustomResourceDefinition
metadata:
name: network-attachment-definitions.k8s.cni.cncf.io
spec:
group: k8s.cni.cncf.io
version: v1
scope: Namespaced
names:
plural: network-attachment-definitions
singular: network-attachment-definition
kind: NetworkAttachmentDefinition
shortNames:
- net-attach-def
validation:
openAPIV3Schema:
properties:
spec:
properties:
config:
type: string
EOF
```
### Create network attachment definition
The 'NetworkAttachmentDefinition' is used to setup the network attachment, i.e. secondary interface for the pod, There are two ways to configure the 'NetworkAttachmentDefinition' as following:
- NetworkAttachmentDefinition with json CNI config
- NetworkAttachmentDefinition with CNI config file
#### NetworkAttachmentDefinition with json CNI config:
Following command creates NetworkAttachmentDefinition. CNI config is in `config:` field.
```
# Execute following command at Kubernetes master
cat <<EOF | kubectl create -f -
apiVersion: "k8s.cni.cncf.io/v1"
kind: NetworkAttachmentDefinition
metadata:
name: macvlan-conf-1
spec:
config: '{
"cniVersion": "0.3.0",
"type": "macvlan",
"master": "eth1",
"mode": "bridge",
"ipam": {
"type": "host-local",
"ranges": [
[ {
"subnet": "10.10.0.0/16",
"rangeStart": "10.10.1.20",
"rangeEnd": "10.10.3.50",
"gateway": "10.10.0.254"
} ]
]
}
}'
EOF
```
#### NetworkAttachmentDefinition with CNI config file:
If NetworkAttachmentDefinition has no spec, multus find a file in defaultConfDir ('/etc/cni/multus/net.d', with same name in the 'name' field of CNI config.
```
# Execute following command at Kubernetes master
cat <<EOF | kubectl create -f -
apiVersion: "k8s.cni.cncf.io/v1"
kind: NetworkAttachmentDefinition
metadata:
name: macvlan-conf-2
EOF
```
```
# Execute following commands at all Kubernetes nodes (i.e. master and minions)
cat <<EOF > /etc/cni/multus/net.d/macvlan2.conf
{
"cniVersion": "0.3.0",
"type": "macvlan",
"name": "macvlan-conf-2",
"master": "eth1",
"mode": "bridge",
"ipam": {
"type": "host-local",
"ranges": [
[ {
"subnet": "11.10.0.0/16",
"rangeStart": "11.10.1.20",
"rangeEnd": "11.10.3.50"
} ]
]
}
}
EOF
```
### Run pod with network annotation
#### Launch pod with text annotation
```
# Execute following command at Kubernetes master
cat <<EOF | kubectl create -f -
apiVersion: v1
kind: Pod
metadata:
name: pod-case-01
annotations:
k8s.v1.cni.cncf.io/networks: macvlan-conf-1, macvlan-conf-2
spec:
containers:
- name: pod-case-01
image: docker.io/centos/tools:latest
command:
- /sbin/init
EOF
```
#### Launch pod with text annotation for NetworkAttachmentDefinition in different namespace
You can also specify NetworkAttachmentDefinition with its namespace as adding `<namespace>/`
```
# Execute following command at Kubernetes master
cat <<EOF | kubectl create -f -
apiVersion: "k8s.cni.cncf.io/v1"
kind: NetworkAttachmentDefinition
metadata:
name: macvlan-conf-3
namespace: testns1
spec:
config: '{
"cniVersion": "0.3.0",
"type": "macvlan",
"master": "eth1",
"mode": "bridge",
"ipam": {
"type": "host-local",
"ranges": [
[ {
"subnet": "12.10.0.0/16",
"rangeStart": "12.10.1.20",
"rangeEnd": "12.10.3.50"
} ]
]
}
}'
EOF
cat <<EOF | kubectl create -f -
apiVersion: v1
kind: Pod
metadata:
name: pod-case-02
annotations:
k8s.v1.cni.cncf.io/networks: testns1/macvlan-conf-3
spec:
containers:
- name: pod-case-02
image: docker.io/centos/tools:latest
command:
- /sbin/init
EOF
```
#### Launch pod with text annotation with interface name
You can also specify interface name as adding `@<ifname>`.
```
# Execute following command at Kubernetes master
cat <<EOF | kubectl create -f -
apiVersion: v1
kind: Pod
metadata:
name: pod-case-03
annotations:
k8s.v1.cni.cncf.io/networks: macvlan-conf-1@macvlan1
spec:
containers:
- name: pod-case-03
image: docker.io/centos/tools:latest
command:
- /sbin/init
EOF
```
#### Launch pod with json annotation
```
# Execute following command at Kubernetes master
cat <<EOF | kubectl create -f -
apiVersion: v1
kind: Pod
metadata:
name: pod-case-04
annotations:
k8s.v1.cni.cncf.io/networks: '[
{ "name" : "macvlan-conf-1" },
{ "name" : "macvlan-conf-2" }
]'
spec:
containers:
- name: pod-case-04
image: docker.io/centos/tools:latest
command:
- /sbin/init
EOF
```
#### Launch pod with json annotation for NetworkAttachmentDefinition in different namespace
You can also specify NetworkAttachmentDefinition with its namespace as adding `"namespace": "<namespace>"`.
```
# Execute following command at Kubernetes master
cat <<EOF | kubectl create -f -
apiVersion: v1
kind: Pod
metadata:
name: pod-case-05
annotations:
k8s.v1.cni.cncf.io/networks: '[
{ "name" : "macvlan-conf-1",
"namespace": "testns1" }
]'
spec:
containers:
- name: pod-case-05
image: docker.io/centos/tools:latest
command:
- /sbin/init
EOF
```
#### Launch pod with json annotation with interface
You can also specify interface name as adding `"interface": "<ifname>"`.
```
# Execute following command at Kubernetes master
cat <<EOF | kubectl create -f -
apiVersion: v1
kind: Pod
metadata:
name: pod-case-06
annotations:
k8s.v1.cni.cncf.io/networks: '[
{ "name" : "macvlan-conf-1",
"interface": "macvlan1" },
{ "name" : "macvlan-conf-2" }
]'
spec:
containers:
- name: pod-case-06
image: docker.io/centos/tools:latest
command:
- /sbin/init
EOF
```
### Verifying pod network
Following the example of `ip -d address` output of above pod, "pod-case-06":
```
# Execute following command at Kubernetes master
kubectl exec -it pod-case-06 -- ip -d address
1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue state UNKNOWN group default qlen 1
link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00 promiscuity 0 numtxqueues 1 numrxqueues 1 gso_max_size 65536 gso_max_segs 65535
inet 127.0.0.1/8 scope host lo
valid_lft forever preferred_lft forever
inet6 ::1/128 scope host
valid_lft forever preferred_lft forever
3: eth0@if11: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1450 qdisc noqueue state UP group default
link/ether 0a:58:0a:f4:02:06 brd ff:ff:ff:ff:ff:ff link-netnsid 0 promiscuity 0
veth numtxqueues 1 numrxqueues 1 gso_max_size 65536 gso_max_segs 65535
inet 10.244.2.6/24 scope global eth0
valid_lft forever preferred_lft forever
inet6 fe80::ac66:45ff:fe7c:3a19/64 scope link
valid_lft forever preferred_lft forever
4: macvlan1@if3: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc noqueue state UNKNOWN group default
link/ether 4e:6d:7a:4e:14:87 brd ff:ff:ff:ff:ff:ff link-netnsid 0 promiscuity 0
macvlan mode bridge numtxqueues 1 numrxqueues 1 gso_max_size 65536 gso_max_segs 65535
inet 10.10.1.22/16 scope global macvlan1
valid_lft forever preferred_lft forever
inet6 fe80::4c6d:7aff:fe4e:1487/64 scope link
valid_lft forever preferred_lft forever
5: net2@if3: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc noqueue state UNKNOWN group default
link/ether 6e:e3:71:7f:86:f7 brd ff:ff:ff:ff:ff:ff link-netnsid 0 promiscuity 0
macvlan mode bridge numtxqueues 1 numrxqueues 1 gso_max_size 65536 gso_max_segs 65535
inet 11.10.1.22/16 scope global net2
valid_lft forever preferred_lft forever
inet6 fe80::6ce3:71ff:fe7f:86f7/64 scope link
valid_lft forever preferred_lft forever
```
| Interface name | Description |
| --- | --- |
| lo | loopback |
| eth0 | Default network interface (flannel) |
| macvlan1 | macvlan interface (macvlan-conf-1) |
| net2 | macvlan interface (macvlan-conf-2) |
## Specifying a default route for a specific attachment
Typically, the default route for a pod will route traffic over the `eth0` and therefore over the cluster-wide default network. You may wish to specify that a different network attachment will have the default route.
You can achieve this by using the JSON formatted annotation and specifying a `default-route` key.
*NOTE*: It's important that you consider that this may impact some functionality of getting traffic to route over the cluster-wide default network.
For example, we have a this configuration for macvlan:
```
cat <<EOF | kubectl create -f -
apiVersion: "k8s.cni.cncf.io/v1"
kind: NetworkAttachmentDefinition
metadata:
name: macvlan-conf
spec:
config: '{
"cniVersion": "0.3.0",
"type": "macvlan",
"master": "eth0",
"mode": "bridge",
"ipam": {
"type": "host-local",
"subnet": "192.168.2.0/24",
"rangeStart": "192.168.2.200",
"rangeEnd": "192.168.2.216",
"routes": [
{ "dst": "0.0.0.0/0" }
],
"gateway": "192.168.2.1"
}
}'
EOF
```
We can then create a pod which uses the `default-route` key in the JSON formatted `k8s.v1.cni.cncf.io/networks` annotation.
```
cat <<EOF | kubectl create -f -
apiVersion: v1
kind: Pod
metadata:
name: samplepod
annotations:
k8s.v1.cni.cncf.io/networks: '[{
"name": "macvlan-conf",
"default-route": ["192.168.2.1"]
}]'
spec:
containers:
- name: samplepod
command: ["/bin/bash", "-c", "trap : TERM INT; sleep infinity & wait"]
image: dougbtv/centos-network
EOF
```
This will set `192.168.2.1` as the default route over the `net1` interface, such as:
```
kubectl exec -it samplepod -- ip route
default via 192.168.2.1 dev net1
10.244.0.0/24 dev eth0 proto kernel scope link src 10.244.0.169
10.244.0.0/16 via 10.244.0.1 dev eth0
```
## Entrypoint Parameters
Multus CNI, when installed using the daemonset-style installation uses an entrypoint script which copies the Multus binary into place, places CNI configurations. This entrypoint takes a variety of parameters for customization.
Typically, you'd modified the daemonset YAML itself to specify these parameters.
For example, the `command` and `args` parameters in the `containers` section of the DaemonSet may look something like:
```
command: ["/entrypoint.sh"]
args:
- "--multus-conf-file=auto"
- "--namespace-isolation=true"
- "--multus-log-level=verbose"
```
Note that some of the defaults have directories inside the root directory named `/host/`, this is because it is deployed as a container and we have host file system locations mapped into this directory inside the container. If you use other directories, you may have to change the mounted volumes.
### Entrypoint script parameters
Each parameter is shown with the default as the value.
--cni-conf-dir=/host/etc/cni/net.d
This is the configuration directory where Multus will write its configuration file.
--cni-bin-dir=/host/opt/cni/bin
This the directory in which the Multus binary will be installed.
--namespace-isolation=false
Setting this option to true enables the Namespace isolation feature, which insists that custom resources must be created in the same namespace as the pods, otherwise it will refuse to attach those definitions as additional interfaces. See (the configuration guide for more information)[configuration.md].
--global-namespaces=default,foo,bar
The `--global-namespaces` works only when `--namespace-isolation=true`. This takes a comma-separated list of namespaces which can be referred to globally when namespace isolation is enabled. See (the configuration guide for more information)[configuration.md].
--multus-bin-file=/usr/src/multus-cni/bin/multus
This option lets you set which binary executable to copy from the container onto the host (into the directory specified by `--cni-bin-dir`), allowing one to copy an alternate version or build of Multus CNI.
--multus-conf-file=/usr/src/multus-cni/images/70-multus.conf
The `--multus-conf-file` is one of two options; it can be set to a source file to be copied into the location specified by `--cni-conf-dir`. Or, to a value of `auto`, that is: `--multus-conf-file=auto`.
The automatic configuration option is used to automatically generate Multus configurations given existing on-disk CNI configurations for your default network.
In the case that `--multus-conf-file=auto` -- The entrypoint script will look at the `--multus-autoconfig-dir` (by default, the same as the `--cni-conf-dir`). Multus will wait (600 seconds) until there's a CNI configuration file there, and it will take the alphabetically first configuration there, and it will wrap that configuration into a Multus configuration.
--multus-autoconfig-dir=/host/etc/cni/net.d
Used only with `--multus-conf-file=auto`. This option allows one to set which directory will be used to generate configuration files.
This can be used if you have your CNI configuration stored in an alternate location, or, you have constraints on race conditions where you'd like to generate your default network configuration first, and then only have Multus write its configuration when it finds that configuration -- allowing only Multus to write the CNI configuration in the `--cni-conf-dir`, therefore notifying the Kubelet that the node is in a ready state.
--multus-kubeconfig-file-host=/etc/cni/net.d/multus.d/multus.kubeconfig
Used only with `--multus-conf-file=auto`. Allows you to specify an alternate path to the Kubeconfig.
--multus-master-cni-file-name=
The `--multus-master-cni-file-name` can be used to select the cni file as the master cni, rather than the first file in cni-conf-dir. For example, `--multus-master-cni-file-name=10-calico.conflist`.
--multus-log-level=
--multus-log-file=
Used only with `--multus-conf-file=auto`. See the [documentation for logging](https://github.com/k8snetworkplumbingwg/multus-cni/blob/master/docs/configuration.md#logging) for which values are permitted.
Used only with `--multus-conf-file=auto`. Allows you to specify CNI spec version. Please set if you need to specify CNI spec version.
--cni-version=
In some cases, the original CNI configuration that the Multus configuration was generated from (using `--multus-conf-file=auto`) may be used as a sort of semaphor for network readiness -- as this model is used by the Kubelet itself. If you need to disable Multus' availability, you may wish to clean out the generated configuration file when the source file for autogeneration of the config file is no longer present. You can use this functionality by setting:
--cleanup-config-on-exit=true
When using CRIO, you may need to restart CRIO to get the Multus configuration file to take -- this is rarely necessary.
--restart-crio=false
Additionally when using CRIO, you may wish to have the CNI config file that's used as the source for `--multus-conf-file=auto` renamed. This boolean option when set to true automatically renames the file with a `.old` suffix to the original filename.
--rename-conf-file=true
When using `--multus-conf-file=auto` you may also care to specify a `binDir` in the configuration, this can be accomplished using the `--additional-bin-dir` option.
--additional-bin-dir=/opt/multus/bin
Sometimes, you may wish to not have the entrypoint copy the binary file onto the host. Potentially, you have another way to copy in a specific version of Multus, for example. By default, it's always copied, but you may disable the copy with:
--skip-multus-binary-copy=true
If you wish to have auto configuration use the `readinessindicatorfile` in the configuration, you can use the `--readiness-indicator-file` to express which file should be used as the readiness indicator.
--readiness-indicator-file=/path/to/file

View File

Before

Width:  |  Height:  |  Size: 38 KiB

After

Width:  |  Height:  |  Size: 38 KiB

View File

Before

Width:  |  Height:  |  Size: 190 KiB

After

Width:  |  Height:  |  Size: 190 KiB

View File

Before

Width:  |  Height:  |  Size: 49 KiB

After

Width:  |  Height:  |  Size: 49 KiB

View File

Before

Width:  |  Height:  |  Size: 197 KiB

After

Width:  |  Height:  |  Size: 197 KiB

View File

Before

Width:  |  Height:  |  Size: 34 KiB

After

Width:  |  Height:  |  Size: 34 KiB

246
docs/quickstart.md Normal file
View File

@@ -0,0 +1,246 @@
# Quickstart Guide
This guide is intended as a way to get you off the ground, using Multus CNI to create Kubernetes pods with multiple interfaces. If you're already using Multus and need more detail, see the [comprehensive usage guide](how-to-use.md). This document is a quickstart and a getting started guide in one, intended for your first run-through of Multus CNI.
We'll first install Multus CNI, and then we'll setup some configurations so that you can see how multiple interfaces are created for pods.
## Key Concepts
Two things we'll refer to a number of times through this document are:
* "Default network" -- This is your pod-to-pod network. This is how pods communicate among one another in your cluster, how they have connectivity. Generally speaking, this is presented as the interface named `eth0`. This interface is always attached to your pods, so that they can have connectivity among themselves. We'll add interfaces in addition to this.
* "CRDs" -- Custom Resource Definitions. Custom Resources are a way that the Kubernetes API is extended. We use these here to store some information that Multus can read. Primarily, we use these to store the configurations for each of the additional interfaces that are attached to your pods.
## Prerequisites
Our installation method requires that you first have installed Kubernetes and have configured a default network -- that is, a CNI plugin that's used for your pod-to-pod connectivity.
We support Kubernetes versions that Kubernetes community supports. Please see [Supported versions](https://kubernetes.io/releases/version-skew-policy/#supported-versions) in Kubernetes document.
To install Kubernetes, you may decide to use [kubeadm](https://kubernetes.io/docs/setup/independent/create-cluster-kubeadm/), or potentially [kubespray](https://github.com/kubernetes-sigs/kubespray).
After installing Kubernetes, you must install a default network CNI plugin. If you're using kubeadm, refer to the "[Installing a pod network add-on](https://kubernetes.io/docs/setup/independent/create-cluster-kubeadm/#pod-network)" section in the kubeadm documentation. If it's your first time, we generally recommend using Flannel for the sake of simplicity.
Alternatively, for advanced use cases, for installing Multus and a default network plugin at the same time, you may refer to the [Kubernetes Network Plumbing Group's Reference Deployments](https://github.com/k8snetworkplumbingwg/reference-deployment).
To verify that you default network is ready, you may list your Kubernetes nodes with:
```
kubectl get nodes
```
In the case that your default network is ready you will see the `STATUS` column also switch to `Ready` for each node.
```
NAME STATUS ROLES AGE VERSION
master-0 Ready master 1h v1.17.1
master-1 Ready master 1h v1.17.1
master-2 Ready master 1h v1.17.1
```
## Installation
Our recommended quickstart method to deploy Multus is to deploy using a Daemonset (a method of running pods on each nodes in your cluster), this spins up pods which install a Multus binary and configure Multus for usage.
Firstly, clone this GitHub repository.
```
git clone https://github.com/k8snetworkplumbingwg/multus-cni.git && cd multus-cni
```
We'll apply a YAML file with `kubectl` from this repo, which installs the Multus components.
Recommended installation:
```
cat ./deployments/multus-daemonset-thick.yml | kubectl apply -f -
```
See the [thick plugin docs](./thick-plugin.md) for more information about this architecture.
Alternatively, you may install the thin-plugin with:
```
cat ./deployments/multus-daemonset.yml | kubectl apply -f -
```
### What the Multus daemonset does
* Starts a Multus daemonset, this runs a pod on each node which places a Multus binary on each node in `/opt/cni/bin`
* Reads the lexicographically (alphabetically) first configuration file in `/etc/cni/net.d`, and creates a new configuration file for Multus on each node as `/etc/cni/net.d/00-multus.conf`, this configuration is auto-generated and is based on the default network configuration (which is assumed to be the alphabetically first configuration)
* Creates a `/etc/cni/net.d/multus.d` directory on each node with authentication information for Multus to access the Kubernetes API.
### Validating your installation
Generally, the first step in validating your installation is to ensure that the Multus pods have run without error, you may see an overview of those by looking at:
```
kubectl get pods --all-namespaces | grep -i multus
```
You may further validate that it has ran by looking at the `/etc/cni/net.d/` directory and ensure that the auto-generated `/etc/cni/net.d/00-multus.conf` exists corresponding to the alphabetically first configuration file.
## Creating additional interfaces
The first thing we'll do is create configurations for each of the additional interfaces that we attach to pods. We'll do this by creating Custom Resources. Part of the quickstart installation creates a "CRD" -- a custom resource definition that is the home where we keep these custom resources -- we'll store our configurations for each interface in these.
### CNI Configurations
Each configuration we'll add is a CNI configuration. If you're not familiar with them, let's break them down quickly. Here's an example CNI configuration:
```
{
"cniVersion": "0.3.0",
"type": "loopback",
"additional": "information"
}
```
CNI configurations are JSON, and we have a structure here that has a few things we're interested in:
1. `cniVersion`: Tells each CNI plugin which version is being used and can give the plugin information if it's using a too late (or too early) version.
2. `type`: This tells CNI which binary to call on disk. Each CNI plugin is a binary that's called. Typically, these binaries are stored in `/opt/cni/bin` on each node, and CNI executes this binary. In this case we've specified the `loopback` binary (which create a loopback-type network interface). If this is your first time installing Multus, you might want to verify that the plugins that are in the "type" field are actually on disk in the `/opt/cni/bin` directory.
3. `additional`: This field is put here as an example, each CNI plugin can specify whatever configuration parameters they'd like in JSON. These are specific to the binary you're calling in the `type` field.
For an even further example -- take a look at the [bridge CNI plugin README](https://github.com/containernetworking/plugins/tree/master/plugins/main/bridge) which shows additional details.
If you'd like more information about CNI configuration, you can read [the entire CNI specification](https://github.com/containernetworking/cni/blob/master/SPEC.md). It might also be useful to look at the [CNI reference plugins](https://github.com/containernetworking/plugins) and see how they're configured.
You do not need to reload or refresh the Kubelets when CNI configurations change. These are read on each creation & deletion of pods. So if you change a configuration, it'll apply the next time a pod is created. Existing pods may need to be restarted if they need the new configuration.
### Storing a configuration as a Custom Resource
So, we want to create an additional interface. Let's create a macvlan interface for pods to use. We'll create a custom resource that defines the CNI configuration for interfaces.
Note in the following command that there's a `kind: NetworkAttachmentDefinition`. This is our fancy name for our configuration -- it's a custom extension of Kubernetes that defines how we attach networks to our pods.
Secondarily, note the `config` field. You'll see that this is a CNI configuration just like we explained earlier.
Lastly but *very* importantly, note under `metadata` the `name` field -- here's where we give this configuration a name, and it's how we tell pods to use this configuration. The name here is `macvlan-conf` -- as we're creating a configuration for macvlan.
Here's the command to create this example configuration:
```
cat <<EOF | kubectl create -f -
apiVersion: "k8s.cni.cncf.io/v1"
kind: NetworkAttachmentDefinition
metadata:
name: macvlan-conf
spec:
config: '{
"cniVersion": "0.3.0",
"type": "macvlan",
"master": "eth0",
"mode": "bridge",
"ipam": {
"type": "host-local",
"subnet": "192.168.1.0/24",
"rangeStart": "192.168.1.200",
"rangeEnd": "192.168.1.216",
"routes": [
{ "dst": "0.0.0.0/0" }
],
"gateway": "192.168.1.1"
}
}'
EOF
```
*NOTE*: This example uses `eth0` as the `master` parameter, this master parameter should match the interface name on the hosts in your cluster.
You can see which configurations you've created using `kubectl` here's how you can do that:
```
kubectl get network-attachment-definitions
```
You can get more detail by describing them:
```
kubectl describe network-attachment-definitions macvlan-conf
```
### Creating a pod that attaches an additional interface
We're going to create a pod. This will look familiar as any pod you might have created before, but, we'll have a special `annotations` field -- in this case we'll have an annotation called `k8s.v1.cni.cncf.io/networks`. This field takes a comma delimited list of the names of your `NetworkAttachmentDefinition`s as we created above. Note in the command below that we have the annotation of `k8s.v1.cni.cncf.io/networks: macvlan-conf` where `macvlan-conf` is the name we used above when we created our configuration.
Let's go ahead and create a pod (that just sleeps for a really long time) with this command:
```
cat <<EOF | kubectl create -f -
apiVersion: v1
kind: Pod
metadata:
name: samplepod
annotations:
k8s.v1.cni.cncf.io/networks: macvlan-conf
spec:
containers:
- name: samplepod
command: ["/bin/ash", "-c", "trap : TERM INT; sleep infinity & wait"]
image: alpine
EOF
```
You may now inspect the pod and see what interfaces are attached, like so:
```
kubectl exec -it samplepod -- ip a
```
You should note that there are 3 interfaces:
* `lo` a loopback interface
* `eth0` our default network
* `net1` the new interface we created with the macvlan configuration.
### Network Status Annotations
For additional confirmation, use `kubectl describe pod samplepod` and there will be an annotations section, similar to the following:
```
Annotations: k8s.v1.cni.cncf.io/networks: macvlan-conf
k8s.v1.cni.cncf.io/network-status:
[{
"name": "cbr0",
"ips": [
"10.244.1.73"
],
"default": true,
"dns": {}
},{
"name": "macvlan-conf",
"interface": "net1",
"ips": [
"192.168.1.205"
],
"mac": "86:1d:96:ff:55:0d",
"dns": {}
}]
```
This metadata tells us that we have two CNI plugins running successfully.
### What if I want more interfaces?
You can add more interfaces to a pod by creating more custom resources and then referring to them in pod's annotation. You can also reuse configurations, so for example, to attach two macvlan interfaces to a pod, you could create a pod like so:
```
cat <<EOF | kubectl create -f -
apiVersion: v1
kind: Pod
metadata:
name: samplepod
annotations:
k8s.v1.cni.cncf.io/networks: macvlan-conf,macvlan-conf
spec:
containers:
- name: samplepod
command: ["/bin/ash", "-c", "trap : TERM INT; sleep infinity & wait"]
image: alpine
EOF
```
Note that the annotation now reads `k8s.v1.cni.cncf.io/networks: macvlan-conf,macvlan-conf`. Where we have the same configuration used twice, separated by a comma.
If you were to create another custom resource with the name `foo` you could use that such as: `k8s.v1.cni.cncf.io/networks: foo,macvlan-conf`, and use any number of attachments.

93
docs/thick-plugin.md Normal file
View File

@@ -0,0 +1,93 @@
# Multus Thick plugin
Multus CNI can also be deployed using a thick plugin architecture, which is
characterized by a client/server architecture.
The client - which will be referred to as "shim" - is a binary executable
located on the Kubernetes node's file-system that
[speaks CNI](https://github.com/containernetworking/cni/blob/master/SPEC.md#section-2-execution-protocol):
the runtime - Kubernetes - passes parameters to the plugin via environment
variables and configuration - which is passed via stdin.
The plugin returns a result on stdout on success, or an error on stderr if the
operation fails. Configuration and results are a JSON encoded string.
Once the shim is invoked by the runtime (Kubernetes) it will contact the
multus-daemon (server) via a unix domain socket which is bind mounted to the
host's file-system; the multus-daemon is the one that will do all the
heavy-pulling: fetch the delegate CNI configuration from the corresponding
`net-attach-def`, compute the `RuntimeConfig`, and finally, invoke the delegate.
It will then return the result of the operation back to the client.
Please refer to the diagram below for a visual representation of the flow
described above:
```
┌─────────┐ ┌───────┐ ┌────────┐ ┌──────────┐
│ │ cni ADD/DEL │ │ REST POST │ │ cni ADD/DEL │ │
│ runtime ├────────────►│ shim │===========│ daemon ├────────────►│ delegate │
│ │<------------│ │ │ │<------------│ │
└─────────┘ └───────┘ └────────┘ └──────────┘
```
## How to use it
### Configure Deployment
If your delegate CNI plugin requires some files which is in container host, please update
update `deployments/multus-daemonset-thick.yml` to add directory into multus-daemon pod.
For example, flannel requires `/run/flannel/subnet.env`, so you need to mount this directory
into the multus-daemon pod.
Required directory/files are different for each CNI plugin, so please refer your CNI plugin.
### Deployment
There is a dedicated multus daemonset specification for users wanting to use
this thick plugin variant. This reference deployment spec of multus can be
deployed by following these commands:
```bash
kubectl apply -f deployments/multus-daemonset-thick.yml
```
### Command line parameters
Multus thick plugin variant accepts the same
[entrypoint arguments](https://github.com/k8snetworkplumbingwg/multus-cni/blob/master/docs/how-to-use.md#entrypoint-script-parameters)
its thin counterpart allows - with the following exceptions:
- `additional-bin-dir`
- `binDir`
- `cleanup-config-on-exit`
- `cniDir`
- `multus-kubeconfig-file-host`
- `rename-conf-file`
- `restart-crio`
- `skip-multus-binary-copy`
It is important to refer that these are command line parameters to the golang
binary; as such, they should be passed using a single dash ("-") e.g.
`-additional-bin-dir=/opt/multus/bin`, `-multus-log-level=debug`, etc.
Furthermore, it also accepts a new command line parameter, where the user
specifies the path to the server configuration:
- `config`: Defaults to `"/etc/cni/net.d/multus.d/daemon-config.json"`
- `metricsPort`: Metrics port (of multus' metric exporter), default is disable
### Server configuration
The server configuration is encoded in JSON, and allows the following keys:
- `"chrootDir"`: Specify the directory which points to host root from the pod. See 'Chroot configuration' section for the details.
- `"socketDir"`: Specify the location where the unix domain socket used for
client/server communication will be located. Defaults to `"/run/multus"`.
In addition, you can add any configuration which is in [configuration reference](https://github.com/k8snetworkplumbingwg/multus-cni/blob/master/docs/configuration.md#multus-cni-configuration-reference). Server configuration override multus CNI configuration (e.g. `/etc/cni/net.d/00-multus.conf`)
#### Chroot configuration
In thick plugin case, delegate CNI plugin is executed by multus-daemon from Pod, hence if the delegate CNI requires resources in container host, for example unix socket or even file, then CNI plugin is failed to execute because multus-daemon runs in Pod. Multus-daemon supports "chrootDir" option which executes delegate CNI under chroot (to container host).
This configuration is enabled in deployments/multus-daemonset-thick.yml as default.

26
e2e/README.md Normal file
View File

@@ -0,0 +1,26 @@
## Multus e2e test with kind
### Prerequisite
To run the e2e test, you need the following components:
- curl
- j2cli
- docker
### How to test e2e
```
$ git clone https://github.com/k8snetworkplumbingwg/multus-cni.git
$ cd multus-cni/e2e
$ ./get_tools.sh
$ ./generate_yamls.sh
$ ./setup_cluster.sh
$ ./test-simple-macvlan1.sh
```
### How to teardown cluster
```
$ ./teardown.sh
```

17
e2e/generate_yamls.sh Executable file
View File

@@ -0,0 +1,17 @@
#!/bin/sh
if [ ! -d yamls ]; then
mkdir yamls
fi
# specify CNI version (default: 0.4.0)
export CNI_VERSION=${CNI_VERSION:-0.4.0}
templates_dir="$(dirname $(readlink -f $0))/templates"
# generate yaml files based on templates/*.j2 to yamls directory
for i in `ls templates/`; do
echo $i
j2 -e CNI_VERSION ${templates_dir}/$i -o yamls/${i%.j2}
done
unset CNI_VERSION

15
e2e/get_tools.sh Executable file
View File

@@ -0,0 +1,15 @@
#!/bin/sh
set -o errexit
if [ ! -d bin ]; then
mkdir bin
fi
curl -Lo ./bin/kind "https://github.com/kubernetes-sigs/kind/releases/download/v0.12.0/kind-$(uname)-amd64"
chmod +x ./bin/kind
curl -Lo ./bin/kubectl https://storage.googleapis.com/kubernetes-release/release/`curl -s https://storage.googleapis.com/kubernetes-release/release/stable.txt`/bin/linux/amd64/kubectl
chmod +x ./bin/kubectl
curl -Lo ./bin/koko https://github.com/redhat-nfvpe/koko/releases/download/v0.83/koko_0.83_linux_amd64
chmod +x ./bin/koko
curl -Lo ./bin/jq https://github.com/stedolan/jq/releases/download/jq-1.6/jq-linux64
chmod +x ./bin/jq

86
e2e/setup_cluster.sh Executable file
View File

@@ -0,0 +1,86 @@
#!/bin/sh
set -o errexit
export PATH=${PATH}:./bin
# define the OCI binary to be used. Acceptable values are `docker`, `podman`.
# Defaults to `docker`.
OCI_BIN="${OCI_BIN:-docker}"
# define the deployment spec to use when deploying multus.
# Acceptable values are `multus-daemonset.yml`. `multus-daemonset-thick.yml`.
# Defaults to `multus-daemonset-thick.yml`.
MULTUS_MANIFEST="${MULTUS_MANIFEST:-multus-daemonset-thick.yml}"
kind_network='kind'
reg_name='kind-registry'
reg_port='5000'
running="$($OCI_BIN inspect -f '{{.State.Running}}' "${reg_name}" 2>/dev/null || true)"
if [ "${running}" != 'true' ]; then
# run registry and push the multus image
$OCI_BIN run -d --restart=always -p "${reg_port}:5000" --name "${reg_name}" registry:2
$OCI_BIN build -t localhost:5000/multus:e2e -f ../images/Dockerfile ..
$OCI_BIN push localhost:5000/multus:e2e
fi
reg_host="${reg_name}"
if [ "${kind_network}" = "bridge" ]; then
reg_host="$($OCI_BIN inspect -f '{{.NetworkSettings.IPAddress}}' "${reg_name}")"
fi
echo "Registry Host: ${reg_host}"
# deploy cluster with kind
cat <<EOF | kind create cluster --config=-
kind: Cluster
apiVersion: kind.x-k8s.io/v1alpha4
containerdConfigPatches:
- |-
[plugins."io.containerd.grpc.v1.cri".registry.mirrors."localhost:${reg_port}"]
endpoint = ["http://${reg_host}:${reg_port}"]
nodes:
- role: control-plane
- role: worker
kubeadmConfigPatches:
- |
kind: InitConfiguration
nodeRegistration:
kubeletExtraArgs:
pod-manifest-path: "/etc/kubernetes/manifests/"
- role: worker
EOF
cat <<EOF | kubectl apply -f -
apiVersion: v1
kind: ConfigMap
metadata:
name: local-registry-hosting
namespace: kube-public
data:
localRegistryHosting.v1: |
host: "localhost:${reg_port}"
help: "https://kind.sigs.k8s.io/docs/user/local-registry/"
EOF
containers=$($OCI_BIN network inspect ${kind_network} -f "{{range .Containers}}{{.Name}} {{end}}")
needs_connect="true"
for c in $containers; do
if [ "$c" = "${reg_name}" ]; then
needs_connect="false"
fi
done
if [ "${needs_connect}" = "true" ]; then
$OCI_BIN network connect "${kind_network}" "${reg_name}" || true
fi
worker1_pid=$($OCI_BIN inspect --format "{{ .State.Pid }}" kind-worker)
worker2_pid=$($OCI_BIN inspect --format "{{ .State.Pid }}" kind-worker2)
kind export kubeconfig
sudo env PATH=${PATH} koko -p "$worker1_pid,eth1" -p "$worker2_pid,eth1"
sleep 1
kubectl -n kube-system wait --for=condition=available deploy/coredns --timeout=300s
kubectl create -f yamls/$MULTUS_MANIFEST
sleep 1
kubectl -n kube-system wait --for=condition=ready -l name=multus pod --timeout=300s
kubectl create -f yamls/cni-install.yml
sleep 1
kubectl -n kube-system wait --for=condition=ready -l name=cni-plugins pod --timeout=300s

11
e2e/simple-static-pod.yml Normal file
View File

@@ -0,0 +1,11 @@
apiVersion: v1
kind: Pod
metadata:
name: static-web
annotations:
k8s.v1.cni.cncf.io/networks: "bridge-nad"
spec:
containers:
- name: web
image: centos:8
command: ["/bin/bash", "-c", "trap : TERM INT; sleep infinity & wait"]

15
e2e/static-pod-nad.yml Normal file
View File

@@ -0,0 +1,15 @@
apiVersion: "k8s.cni.cncf.io/v1"
kind: NetworkAttachmentDefinition
metadata:
name: bridge-nad
spec:
config: '{
"cniVersion": "0.3.1",
"name": "testnet",
"type": "bridge",
"bridge": "testnet0",
"ipam": {
"type": "host-local",
"subnet": "10.10.0.0/16"
}
}'

10
e2e/teardown.sh Executable file
View File

@@ -0,0 +1,10 @@
#!/bin/sh
#set -o errexit
reg_name='kind-registry'
export PATH=${PATH}:./bin
# delete cluster kind
kind delete cluster
docker kill ${reg_name}
docker rm ${reg_name}

View File

@@ -0,0 +1,64 @@
---
kind: ConfigMap
apiVersion: v1
metadata:
name: cni-install-sh
namespace: kube-system
data:
install_cni.sh: |
cd /tmp
wget https://github.com/containernetworking/plugins/releases/download/v1.1.1/cni-plugins-linux-amd64-v1.1.1.tgz
cd /host/opt/cni/bin
tar xvfzp /tmp/cni-plugins-linux-amd64-v1.1.1.tgz
sleep infinite
---
apiVersion: apps/v1
kind: DaemonSet
metadata:
name: install-cni-plugins
namespace: kube-system
labels:
name: cni-plugins
spec:
selector:
matchLabels:
name: cni-plugins
template:
metadata:
labels:
name: cni-plugins
spec:
hostNetwork: true
nodeSelector:
kubernetes.io/arch: amd64
tolerations:
- operator: Exists
effect: NoSchedule
containers:
- name: install-cni-plugins
image: alpine
command: ["/bin/sh", "/scripts/install_cni.sh"]
resources:
requests:
cpu: "100m"
memory: "50Mi"
limits:
cpu: "100m"
memory: "50Mi"
securityContext:
privileged: true
volumeMounts:
- name: cni-bin
mountPath: /host/opt/cni/bin
- name: scripts
mountPath: /scripts
volumes:
- name: cni-bin
hostPath:
path: /opt/cni/bin
- name: scripts
configMap:
name: cni-install-sh
items:
- key: install_cni.sh
path: install_cni.sh

View File

@@ -0,0 +1,57 @@
---
apiVersion: "k8s.cni.cncf.io/v1"
kind: NetworkAttachmentDefinition
metadata:
name: default-route-config
spec:
config: '{
"cniVersion": "{{ CNI_VERSION }}",
"plugins": [
{
"type": "macvlan",
"master": "eth1",
"mode": "bridge",
"ipam": {
"type": "static"
}
} ]
}'
---
apiVersion: v1
kind: Pod
metadata:
name: default-route-worker1
annotations:
k8s.v1.cni.cncf.io/networks: '[
{ "name": "default-route-config",
"ips": [ "10.1.1.21/24" ] ,
"default-route": [ "10.1.1.254" ] }
]'
labels:
app: default-route1
spec:
containers:
- name: default-route-worker1
image: centos:8
command: ["/bin/sleep", "10000"]
securityContext:
privileged: true
---
apiVersion: v1
kind: Pod
metadata:
name: default-route-worker2
annotations:
k8s.v1.cni.cncf.io/networks: '[
{ "name": "default-route-config",
"ips": [ "10.1.1.22/24" ] }
]'
labels:
app: default-route1
spec:
containers:
- name: default-route-worker2
image: centos:8
command: ["/bin/sleep", "10000"]
securityContext:
privileged: true

View File

@@ -0,0 +1,199 @@
---
apiVersion: apiextensions.k8s.io/v1
kind: CustomResourceDefinition
metadata:
name: network-attachment-definitions.k8s.cni.cncf.io
spec:
group: k8s.cni.cncf.io
scope: Namespaced
names:
plural: network-attachment-definitions
singular: network-attachment-definition
kind: NetworkAttachmentDefinition
shortNames:
- net-attach-def
versions:
- name: v1
served: true
storage: true
schema:
openAPIV3Schema:
type: object
properties:
spec:
type: object
properties:
config:
type: string
---
kind: ClusterRole
apiVersion: rbac.authorization.k8s.io/v1
metadata:
name: multus
rules:
- apiGroups: ["k8s.cni.cncf.io"]
resources:
- '*'
verbs:
- '*'
- apiGroups:
- ""
resources:
- pods
- pods/status
verbs:
- get
- update
- apiGroups:
- ""
- events.k8s.io
resources:
- events
verbs:
- create
- patch
- update
---
kind: ClusterRoleBinding
apiVersion: rbac.authorization.k8s.io/v1
metadata:
name: multus
roleRef:
apiGroup: rbac.authorization.k8s.io
kind: ClusterRole
name: multus
subjects:
- kind: ServiceAccount
name: multus
namespace: kube-system
---
apiVersion: v1
kind: ServiceAccount
metadata:
name: multus
namespace: kube-system
---
kind: ConfigMap
apiVersion: v1
metadata:
name: multus-daemon-config
namespace: kube-system
labels:
tier: node
app: multus
data:
daemon-config.json: |
{
"confDir": "/host/etc/cni/net.d",
"logToStderr": true,
"logLevel": "debug",
"logFile": "/tmp/multus.log",
"binDir": "/host/opt/cni/bin",
"cniDir": "/var/lib/cni/multus",
"socketDir": "/host/run/multus"
}
---
apiVersion: apps/v1
kind: DaemonSet
metadata:
name: kube-multus-ds-amd64
namespace: kube-system
labels:
tier: node
app: multus
name: multus
spec:
selector:
matchLabels:
name: multus
updateStrategy:
type: RollingUpdate
template:
metadata:
labels:
tier: node
app: multus
name: multus
spec:
hostNetwork: true
hostPID: true
nodeSelector:
kubernetes.io/arch: amd64
tolerations:
- operator: Exists
effect: NoSchedule
serviceAccountName: multus
containers:
- name: kube-multus
image: localhost:5000/multus:e2e
imagePullPolicy: Always
command: [ "/usr/src/multus-cni/bin/multus-daemon" ]
args:
- "-cni-version={{ CNI_VERSION }}"
- "-cni-config-dir=/host/etc/cni/net.d"
- "-force-cni-version=true"
- "-multus-conf-file=auto"
- "-multus-autoconfig-dir=/host/etc/cni/net.d"
resources:
requests:
cpu: "100m"
memory: "50Mi"
limits:
cpu: "100m"
memory: "50Mi"
securityContext:
privileged: true
volumeMounts:
- name: cni
mountPath: /host/etc/cni/net.d
- name: cnibin
mountPath: /host/opt/cni/bin
- name: host-run
mountPath: /host/run
- name: host-var-lib-cni-multus
mountPath: /var/lib/cni/multus
- name: host-run-netns
mountPath: /run/netns
mountPropagation: HostToContainer
- name: multus-daemon-config
mountPath: /etc/cni/net.d/multus.d
readOnly: true
initContainers:
- name: install-multus-shim
image: localhost:5000/multus:e2e
command:
- "cp"
- "/usr/src/multus-cni/bin/multus-shim"
- "/host/opt/cni/bin/multus-shim"
resources:
requests:
cpu: "10m"
memory: "15Mi"
securityContext:
privileged: true
volumeMounts:
- name: cnibin
mountPath: /host/opt/cni/bin
mountPropagation: Bidirectional
volumes:
- name: cni
hostPath:
path: /etc/cni/net.d
- name: cnibin
hostPath:
path: /opt/cni/bin
- name: multus-daemon-config
configMap:
name: multus-daemon-config
items:
- key: daemon-config.json
path: daemon-config.json
- name: host-run
hostPath:
path: /run
- name: host-var-lib-cni-multus
hostPath:
path: /var/lib/cni/multus
- name: host-run-netns
hostPath:
path: /run/netns/

View File

@@ -0,0 +1,198 @@
---
apiVersion: apiextensions.k8s.io/v1
kind: CustomResourceDefinition
metadata:
name: network-attachment-definitions.k8s.cni.cncf.io
spec:
group: k8s.cni.cncf.io
scope: Namespaced
names:
plural: network-attachment-definitions
singular: network-attachment-definition
kind: NetworkAttachmentDefinition
shortNames:
- net-attach-def
versions:
- name: v1
served: true
storage: true
schema:
openAPIV3Schema:
type: object
properties:
spec:
type: object
properties:
config:
type: string
---
kind: ClusterRole
apiVersion: rbac.authorization.k8s.io/v1
metadata:
name: multus
rules:
- apiGroups: ["k8s.cni.cncf.io"]
resources:
- '*'
verbs:
- '*'
- apiGroups:
- ""
resources:
- pods
- pods/status
verbs:
- get
- update
---
kind: ClusterRoleBinding
apiVersion: rbac.authorization.k8s.io/v1
metadata:
name: multus
roleRef:
apiGroup: rbac.authorization.k8s.io
kind: ClusterRole
name: multus
subjects:
- kind: ServiceAccount
name: multus
namespace: kube-system
---
apiVersion: v1
kind: ServiceAccount
metadata:
name: multus
namespace: kube-system
---
kind: ConfigMap
apiVersion: v1
metadata:
name: multus-cni-config
namespace: kube-system
labels:
tier: node
app: multus
data:
# NOTE: If you'd prefer to manually apply a configuration file, you may create one here.
# In the case you'd like to customize the Multus installation, you should change the arguments to the Multus pod
# change the "args" line below from
# - "--multus-conf-file=auto"
# to:
# "--multus-conf-file=/tmp/multus-conf/70-multus.conf"
# Additionally -- you should ensure that the name "70-multus.conf" is the alphabetically first name in the
# /etc/cni/net.d/ directory on each node, otherwise, it will not be used by the Kubelet.
cni-conf.json: |
{
"name": "multus-cni-network",
"type": "multus",
"capabilities": {
"portMappings": true
},
"delegates": [
{
"cniVersion": "0.3.1",
"name": "default-cni-network",
"plugins": [
{
"type": "flannel",
"name": "flannel.1",
"delegate": {
"isDefaultGateway": true,
"hairpinMode": true
}
},
{
"type": "portmap",
"capabilities": {
"portMappings": true
}
}
]
}
],
"kubeconfig": "/etc/cni/net.d/multus.d/multus.kubeconfig"
}
---
apiVersion: apps/v1
kind: DaemonSet
metadata:
name: kube-multus-ds-amd64
namespace: kube-system
labels:
tier: node
app: multus
name: multus
spec:
selector:
matchLabels:
name: multus
updateStrategy:
type: RollingUpdate
template:
metadata:
labels:
tier: node
app: multus
name: multus
spec:
hostNetwork: true
nodeSelector:
kubernetes.io/arch: amd64
tolerations:
- operator: Exists
effect: NoSchedule
serviceAccountName: multus
containers:
- name: kube-multus
image: localhost:5000/multus:e2e
command: ["/entrypoint.sh"]
args:
- "--multus-conf-file=auto"
- "--force-cni-version=true"
- "--cni-version={{ CNI_VERSION }}"
resources:
requests:
cpu: "100m"
memory: "50Mi"
limits:
cpu: "100m"
memory: "50Mi"
securityContext:
privileged: true
volumeMounts:
- name: cni
mountPath: /host/etc/cni/net.d
- name: cnibin
mountPath: /host/opt/cni/bin
- name: multus-cfg
mountPath: /tmp/multus-conf
initContainers:
- name: install-multus-binary
image: localhost:5000/multus:e2e
command:
- "cp"
- "/usr/src/multus-cni/bin/multus"
- "/host/opt/cni/bin/multus"
resources:
requests:
cpu: "10m"
memory: "15Mi"
securityContext:
privileged: true
volumeMounts:
- name: cnibin
mountPath: /host/opt/cni/bin
mountPropagation: Bidirectional
volumes:
- name: cni
hostPath:
path: /etc/cni/net.d
- name: cnibin
hostPath:
path: /opt/cni/bin
- name: multus-cfg
configMap:
name: multus-cni-config
items:
- key: cni-conf.json
path: 70-multus.conf

View File

@@ -0,0 +1,63 @@
---
apiVersion: "k8s.cni.cncf.io/v1"
kind: NetworkAttachmentDefinition
metadata:
name: macvlan1-config
spec:
config: '{
"cniVersion": "{{ CNI_VERSION }}",
"plugins": [
{
"type": "macvlan",
"capabilities": { "ips": true },
"master": "eth1",
"mode": "bridge",
"ipam": {
"type": "static"
}
}, {
"type": "tuning"
} ]
}'
---
apiVersion: v1
kind: Pod
metadata:
name: macvlan1-worker1
annotations:
k8s.v1.cni.cncf.io/networks: '[
{ "name": "macvlan1-config",
"ips": [ "10.1.1.11/24" ] }
]'
labels:
app: macvlan
spec:
containers:
- name: macvlan-worker1
image: centos:8
command: ["/bin/sleep", "10000"]
securityContext:
privileged: true
nodeSelector:
kubernetes.io/hostname: kind-worker
---
apiVersion: v1
kind: Pod
metadata:
name: macvlan1-worker2
annotations:
k8s.v1.cni.cncf.io/networks: '[
{ "name": "macvlan1-config",
"ips": [ "10.1.1.12/24" ] }
]'
labels:
app: macvlan
spec:
containers:
- name: macvlan-worker2
image: centos:8
command: ["/bin/sleep", "10000"]
securityContext:
privileged: true
nodeSelector:
kubernetes.io/hostname: kind-worker2

View File

@@ -0,0 +1,15 @@
---
apiVersion: v1
kind: Pod
metadata:
name: simple-centos1
annotations:
labels:
app: simple
spec:
containers:
- name: simple-centos1
image: centos:8
command: ["/bin/sleep", "10000"]
securityContext:
privileged: true

44
e2e/test-default-route1.sh Executable file
View File

@@ -0,0 +1,44 @@
#!/bin/sh
set -o errexit
export PATH=${PATH}:./bin
kubectl create -f yamls/default-route1.yml
kubectl wait --for=condition=ready -l app=default-route1 --timeout=300s pod
echo "check default-route-worker1 interface: net1"
kubectl exec default-route-worker1 -- ip a show dev net1
echo "check default-route-worker1 interface address: net1"
ipaddr=$(kubectl exec default-route-worker1 -- ip -j a show | jq -r \
'.[]|select(.ifname =="net1")|.addr_info[]|select(.family=="inet").local')
if [ $ipaddr != "10.1.1.21" ]; then
echo "default-route-worker1 IP address is different: ${ipaddr}"
fi
echo "check default-route-worker1 default route"
ipaddr=$(kubectl exec default-route-worker1 -- ip -j route | jq -r \
'.[]|select(.dst=="default")|.gateway')
if [ $ipaddr != "10.1.1.254" ]; then
echo "default-route-worker1 default route is different: ${ipaddr}"
fi
echo "check default-route-worker2 interface: net1"
kubectl exec default-route-worker2 -- ip a show dev net1
echo "check default-route-worker2 interface address: net1"
ipaddr=$(kubectl exec default-route-worker2 -- ip -j a show | jq -r \
'.[]|select(.ifname =="net1")|.addr_info[]|select(.family=="inet").local')
if [ $ipaddr != "10.1.1.22" ]; then
echo "default-route-worker2 IP address is different: ${ipaddr}"
fi
echo "check default-route-worker2 default route"
ipaddr=$(kubectl exec default-route-worker2 -- ip -j route | jq -r \
'.[]|select(.dst=="default")|.gateway')
if [ $ipaddr != "10.244.1.1" ]; then
echo "default-route-worker2 default route is different: ${ipaddr}"
fi
echo "cleanup resources"
kubectl delete -f yamls/default-route1.yml

30
e2e/test-simple-macvlan1.sh Executable file
View File

@@ -0,0 +1,30 @@
#!/bin/sh
set -o errexit
export PATH=${PATH}:./bin
kubectl create -f yamls/simple-macvlan1.yml
kubectl wait --for=condition=ready -l app=macvlan --timeout=300s pod
echo "check macvlan1-worker1 interface: net1"
kubectl exec macvlan1-worker1 -- ip a show dev net1
echo "check macvlan1-worker1 interface address: net1"
ipaddr=$(kubectl exec macvlan1-worker1 -- ip -j a show | jq -r \
'.[]|select(.ifname =="net1")|.addr_info[]|select(.family=="inet").local')
if [ $ipaddr != "10.1.1.11" ]; then
echo "macvlan1-worker1 IP address is different: ${ipaddr}"
fi
echo "check macvlan1-worker2 interface: net1"
kubectl exec macvlan1-worker2 -- ip a show dev net1
echo "check macvlan1-worker2 interface address: net1"
ipaddr=$(kubectl exec macvlan1-worker2 -- ip -j a show | jq -r \
'.[]|select(.ifname =="net1")|.addr_info[]|select(.family=="inet").local')
if [ $ipaddr != "10.1.1.12" ]; then
echo "macvlan1-worker2 IP address is different: ${ipaddr}"
fi
echo "cleanup resources"
kubectl delete -f yamls/simple-macvlan1.yml

10
e2e/test-simple-pod.sh Executable file
View File

@@ -0,0 +1,10 @@
#!/bin/sh
set -o errexit
export PATH=${PATH}:./bin
kubectl create -f yamls/simple-pod.yml
kubectl wait --for=condition=ready -l app=simple --timeout=300s pod
echo "cleanup resources"
kubectl delete -f yamls/simple-pod.yml

22
e2e/test-static-pod.sh Executable file
View File

@@ -0,0 +1,22 @@
#!/usr/bin/env bash
set -o errexit
echo "Creating network attachment definition"
kubectl create -f static-pod-nad.yml
echo "Creating static pod config file"
docker cp simple-static-pod.yml kind-worker:/etc/kubernetes/manifests/static-web.yaml
echo "Waiting for static pod to start"
kubectl wait --for=condition=Ready --namespace=default pod/static-web-kind-worker
echo "Checking the pod annotation for net1 interface"
kubectl exec static-web-kind-worker --namespace=default -- ip a show dev net1
echo "Deleting static pod"
docker exec kind-worker /bin/bash -c "rm /etc/kubernetes/manifests/static-web.yaml"
echo "Deleting network attachment definition"
kubectl delete -f static-pod-nad.yml
echo "Test complete"

View File

@@ -62,9 +62,9 @@ A sample `cni-configuration.conf` is provided, typically this file is placed in
Primarily in this setup one thing that one should consider are the aspects of the `macvlan-conf.yml`, which is likely specific to the configuration of the node on which this resides.
## Passing down device information
Some CNI plugins require specific device information which maybe pre-allocated by K8s device plugin. This could be indicated by providing `k8s.v1.cni.cncf.io/resourceName` annotaton in its network attachment definition CRD. The file [`examples/sriov-net.yaml`](./sriov-net.yaml) shows an example on how to define a Network attachment definition with specific device allocation information. Multus will get allocated device information and make them available for CNI plugin to work on.
Some CNI plugins require specific device information which maybe pre-allocated by K8s device plugin. This could be indicated by providing `k8s.v1.cni.cncf.io/resourceName` annotation in its network attachment definition CRD. The file [`examples/sriov-net.yaml`](./sriov-net.yaml) shows an example on how to define a Network attachment definition with specific device allocation information. Multus will get allocated device information and make them available for CNI plugin to work on.
In this exmaple (shown below), it is expected that an [SRIOV Device Plugin](https://github.com/intel/sriov-network-device-plugin/) making a pool of SRIOV VFs available to the K8s with `intel.com/sriov` as their resourceName. Any device allocated from this resource pool will be passed down by Multus to the [sriov-cni](https://github.com/intel/sriov-cni/tree/dev/k8s-deviceid-model) plugin in `deviceID` field. This is up to the sriov-cni plugin to capture this information and work with this specific device information.
In this example (shown below), it is expected that an [SRIOV Device Plugin](https://github.com/intel/sriov-network-device-plugin/) making a pool of SRIOV VFs available to the K8s with `intel.com/sriov` as their resourceName. Any device allocated from this resource pool will be passed down by Multus to the [sriov-cni](https://github.com/intel/sriov-cni/tree/dev/k8s-deviceid-model) plugin in `deviceID` field. This is up to the sriov-cni plugin to capture this information and work with this specific device information.
```yaml
apiVersion: "k8s.cni.cncf.io/v1"
@@ -89,6 +89,6 @@ spec:
}
}'
```
The [net-resource-sample-pod.yaml](./net-resource-sample-pod.yaml) is an exmaple Pod manifest file that requesting a SRIOV device from a host which is then configured using the above network attachement definition.
The [sriov-pod.yml](./sriov-pod.yml) is an example Pod manifest file that requesting a SRIOV device from a host which is then configured using the above network attachment definition.
>For further information on how to configure SRIOV Device Plugin and SRIOV-CNI please refer to the links given above.
>For further information on how to configure SRIOV Device Plugin and SRIOV-CNI please refer to the links given above.

View File

@@ -1,19 +0,0 @@
---
kind: ClusterRole
apiVersion: rbac.authorization.k8s.io/v1beta1
metadata:
name: multus-crd-overpowered
rules:
- apiGroups: ["k8s.cni.cncf.io"]
resources:
- '*'
verbs:
- '*'
- apiGroups:
- ""
resources:
- pods
- pods/status
verbs:
- get
- update

View File

@@ -1,13 +0,0 @@
{
"name": "multus-cni-network",
"type": "multus",
"delegates": [
{
"type": "flannel",
"delegate": {
"isDefaultGateway": true
}
}
],
"kubeconfig": "/etc/kubernetes/kubelet.conf"
}

View File

@@ -1,21 +0,0 @@
apiVersion: apiextensions.k8s.io/v1beta1
kind: CustomResourceDefinition
metadata:
name: network-attachment-definitions.k8s.cni.cncf.io
spec:
group: k8s.cni.cncf.io
version: v1
scope: Namespaced
names:
plural: network-attachment-definitions
singular: network-attachment-definition
kind: NetworkAttachmentDefinition
shortNames:
- net-attach-def
validation:
openAPIV3Schema:
properties:
spec:
properties:
config:
type: string

View File

@@ -1,12 +0,0 @@
apiVersion: "k8s.cni.cncf.io/v1"
kind: NetworkAttachmentDefinition
metadata:
name: flannel-conf
spec:
config: '{
"cniVersion": "0.3.0",
"type": "flannel",
"delegate": {
"isDefaultGateway": true
}
}'

View File

@@ -1,21 +0,0 @@
apiVersion: "k8s.cni.cncf.io/v1"
kind: NetworkAttachmentDefinition
metadata:
name: macvlan-conf
spec:
config: '{
"cniVersion": "0.3.0",
"type": "macvlan",
"master": "eth0",
"mode": "bridge",
"ipam": {
"type": "host-local",
"subnet": "192.168.1.0/24",
"rangeStart": "192.168.1.200",
"rangeEnd": "192.168.1.216",
"routes": [
{ "dst": "0.0.0.0/0" }
],
"gateway": "192.168.1.1"
}
}'

56
examples/macvlan-pod.yml Normal file
View File

@@ -0,0 +1,56 @@
---
# This net-attach-def defines macvlan-conf with
# + ips capabilities to specify ip in pod annotation and
# + mac capabilities to specify mac address in pod annotation
# default gateway is defined as well
apiVersion: "k8s.cni.cncf.io/v1"
kind: NetworkAttachmentDefinition
metadata:
name: macvlan-conf
spec:
config: '{
"cniVersion": "0.3.1",
"plugins": [
{
"type": "macvlan",
"capabilities": { "ips": true },
"master": "eth0",
"mode": "bridge",
"ipam": {
"type": "static",
"routes": [
{
"dst": "0.0.0.0/0",
"gw": "10.1.1.1"
}
]
}
}, {
"capabilities": { "mac": true },
"type": "tuning"
}
]
}'
---
# Define a pod with macvlan-conf, defined above, with ip address and mac, and
# "gateway" overrides default gateway to use macvlan-conf's one.
# without "gateway" in k8s.v1.cni.cncf.io/networks, default route will be cluster
# network interface, eth0, even tough macvlan-conf has default gateway config.
apiVersion: v1
kind: Pod
metadata:
name: samplepod
annotations:
k8s.v1.cni.cncf.io/networks: '[
{ "name": "macvlan-conf",
"ips": [ "10.1.1.101/24" ],
"mac": "c2:b0:57:49:47:f1",
"gateway": [ "10.1.1.1" ]
}]'
spec:
containers:
- name: samplepod
command: ["/bin/bash", "-c", "trap : TERM INT; sleep infinity & wait"]
image: dougbtv/centos-network
ports:
- containerPort: 80

View File

@@ -1,36 +0,0 @@
{
"name": "multus-cni-network",
"type": "multus"
"capabilities": {
"portMappings": true
},
"delegates": [
{
"cniVersion": "0.3.1",
"name": "ptp-tuning-conflist",
"plugins": [
{
"dns": {
"nameservers": [
"172.16.1.1"
]
},
"ipMasq": true,
"ipam": {
"subnet": "172.16.0.0/24",
"type": "host-local"
},
"mtu": 512,
"type": "ptp"
},
{
"capabilities": {
"portMappings": true
},
"externalSetMarkChain": "KUBE-MARK-MASQ",
"type": "portmap"
}
]
}
],
}

View File

@@ -1,161 +0,0 @@
# -----------------------------------------------
# - Example Configuration Deployment
# -----------------------------------------------
# - Deploys a .conf file on each node
# - Configured for Multus + Flannel.
# - As well as assets for Flannel
# - Based on https://github.com/coreos/flannel/blob/master/Documentation/kube-flannel.yml
# -----------------------------------------------
---
kind: ClusterRole
apiVersion: rbac.authorization.k8s.io/v1beta1
metadata:
name: flannel
rules:
- apiGroups:
- ""
resources:
- pods
verbs:
- get
- apiGroups:
- ""
resources:
- nodes
verbs:
- list
- watch
- apiGroups:
- ""
resources:
- nodes/status
verbs:
- patch
---
kind: ClusterRoleBinding
apiVersion: rbac.authorization.k8s.io/v1beta1
metadata:
name: flannel
roleRef:
apiGroup: rbac.authorization.k8s.io
kind: ClusterRole
name: flannel
subjects:
- kind: ServiceAccount
name: flannel
namespace: kube-system
---
apiVersion: v1
kind: ServiceAccount
metadata:
name: flannel
namespace: kube-system
---
kind: ConfigMap
apiVersion: v1
metadata:
name: kube-multus-cfg
namespace: kube-system
labels:
tier: node
app: multus
data:
cni-conf.json: |
{
"name": "multus-cni-network",
"type": "multus",
"delegates": [
{
"type": "flannel",
"delegate": {
"isDefaultGateway": true
}
}
],
"kubeconfig": "/etc/kubernetes/kubelet.conf"
}
net-conf.json: |
{
"Network": "10.244.0.0/16",
"Backend": {
"Type": "vxlan"
}
}
---
apiVersion: extensions/v1beta1
kind: DaemonSet
metadata:
name: kube-multus-ds
namespace: kube-system
labels:
tier: node
app: multus
spec:
template:
metadata:
labels:
tier: node
app: multus
spec:
hostNetwork: true
nodeSelector:
beta.kubernetes.io/arch: amd64
tolerations:
- operator: Exists
effect: NoSchedule
serviceAccountName: flannel
initContainers:
- name: install-cni
image: quay.io/coreos/flannel:v0.10.0-amd64
command:
- cp
args:
- -f
- /etc/kube-flannel/cni-conf.json
- /etc/cni/net.d/10-multus-with-flannel.conf
volumeMounts:
- name: cni
mountPath: /etc/cni/net.d
- name: multus-cfg
mountPath: /etc/kube-flannel/
containers:
- name: kube-flannel
image: quay.io/coreos/flannel:v0.10.0-amd64
command:
- /opt/bin/flanneld
args:
- --ip-masq
- --kube-subnet-mgr
resources:
requests:
cpu: "100m"
memory: "50Mi"
limits:
cpu: "100m"
memory: "50Mi"
securityContext:
privileged: true
env:
- name: POD_NAME
valueFrom:
fieldRef:
fieldPath: metadata.name
- name: POD_NAMESPACE
valueFrom:
fieldRef:
fieldPath: metadata.namespace
volumeMounts:
- name: run
mountPath: /run
- name: multus-cfg
mountPath: /etc/kube-flannel/
volumes:
- name: run
hostPath:
path: /run
- name: cni
hostPath:
path: /etc/cni/net.d
- name: multus-cfg
configMap:
name: kube-multus-cfg

View File

@@ -1,21 +0,0 @@
apiVersion: v1
kind: Pod
metadata:
name: testpod1
labels:
env: test
annotations:
k8s.v1.cni.cncf.io/networks: sriov-net-a
spec:
containers:
- name: appcntr1
image: centos/tools
imagePullPolicy: IfNotPresent
command: [ "/bin/bash", "-c", "--" ]
args: [ "while true; do sleep 300000; done;" ]
resources:
requests:
intel.com/sriov: '1'
limits:
intel.com/sriov: '1'
restartPolicy: "Never"

View File

@@ -1,30 +0,0 @@
apiVersion: apiextensions.k8s.io/v1beta1
kind: CustomResourceDefinition
metadata:
# name must match the spec fields below, and be in the form: <plural>.<group>
name: network-attachment-definitions.k8s.cni.cncf.io
spec:
# group name to use for REST API: /apis/<group>/<version>
group: k8s.cni.cncf.io
# version name to use for REST API: /apis/<group>/<version>
version: v1
# either Namespaced or Cluster
scope: Namespaced
names:
# plural name to be used in the URL: /apis/<group>/<version>/<plural>
plural: network-attachment-definitions
# singular name to be used as an alias on the CLI and for display
singular: network-attachment-definition
# kind is normally the CamelCased singular type. Your resource manifests use this.
kind: NetworkAttachmentDefinition
# shortNames allow shorter string to match your resource on the CLI
shortNames:
- net-attach-def
validation:
openAPIV3Schema:
properties:
spec:
properties:
config:
type: string

View File

@@ -1,16 +0,0 @@
---
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRole
metadata:
name: multus
rules:
- apiGroups:
- '*'
resources:
- '*'
verbs:
- '*'
- nonResourceURLs:
- '*'
verbs:
- '*'

View File

@@ -1,5 +0,0 @@
---
apiVersion: v1
kind: Namespace
metadata:
name: testns1

View File

@@ -1,72 +0,0 @@
---
apiVersion: "k8s.cni.cncf.io/v1"
kind: NetworkAttachmentDefinition
metadata:
name: macvlan-conf-1
spec:
config: '{
"cniVersion": "0.3.0",
"type": "macvlan",
"master": "eth1",
"mode": "bridge",
"ipam": {
"type": "static",
"addresses": [
{ "address": "10.1.1.101/24" }
]
}
}'
---
apiVersion: "k8s.cni.cncf.io/v1"
kind: NetworkAttachmentDefinition
metadata:
name: macvlan-conf-2
spec:
config: '{
"cniVersion": "0.3.0",
"type": "macvlan",
"master": "eth1",
"mode": "bridge",
"ipam": {
"type": "static",
"addresses": [
{ "address": "10.1.1.102/24" }
]
}
}'
---
apiVersion: "k8s.cni.cncf.io/v1"
kind: NetworkAttachmentDefinition
metadata:
name: macvlan-conf-3
spec:
config: '{
"cniVersion": "0.3.0",
"type": "macvlan",
"master": "eth1",
"mode": "bridge",
"ipam": {
"type": "static",
"addresses": [
{ "address": "10.1.1.103/24" }
]
}
}'
---
apiVersion: "k8s.cni.cncf.io/v1"
kind: NetworkAttachmentDefinition
metadata:
name: macvlan-conf-4
spec:
config: '{
"cniVersion": "0.3.0",
"type": "macvlan",
"master": "eth1",
"mode": "bridge",
"ipam": {
"type": "static",
"addresses": [
{ "address": "10.1.1.104/24" }
]
}
}'

View File

@@ -1,19 +0,0 @@
---
apiVersion: "k8s.cni.cncf.io/v1"
kind: NetworkAttachmentDefinition
metadata:
name: vlan-conf-1-1
namespace: testns1
spec:
config: '{
"cniVersion": "0.3.0",
"type": "vlan",
"master": "eth1",
"vlanid": 1,
"ipam": {
"type": "static",
"addresses": [
{ "address": "172.16.1.101/24"
} ]
}
}'

View File

@@ -1,194 +0,0 @@
---
kind: ClusterRole
apiVersion: rbac.authorization.k8s.io/v1beta1
metadata:
name: flannel2
namespace: kube-system
rules:
- apiGroups:
- ""
resources:
- pods
verbs:
- get
- apiGroups:
- ""
resources:
- nodes
verbs:
- list
- watch
- apiGroups:
- ""
resources:
- nodes/status
verbs:
- patch
---
kind: ClusterRoleBinding
apiVersion: rbac.authorization.k8s.io/v1beta1
metadata:
name: flannel2
namespace: kube-system
roleRef:
apiGroup: rbac.authorization.k8s.io
kind: ClusterRole
name: flannel2
subjects:
- kind: ServiceAccount
name: flannel2
namespace: kube-system
---
kind: ServiceAccount
apiVersion: v1
metadata:
name: flannel2
namespace: kube-system
---
kind: ConfigMap
apiVersion: v1
metadata:
name: kube-flannel2-cfg
namespace: kube-system
labels:
tier: node
app: flannel2
data:
flannel2-conf.json: |
{
"type": "flannel",
"name": "flannel-2",
"subnetFile": "/run/flannel/flannel2.env",
"dataDir": "/var/lib/cni/flannel2",
"delegate": {
"bridge": "kbr1"
}
}
net-conf.json: |
{
"Network": "10.144.0.0/16",
"SubnetLen": 24,
"SubnetMin": "10.144.0.0",
"Backend": {
"Type": "vxlan"
}
}
---
apiVersion: v1
kind: Pod
metadata:
name: flannel-etcd
namespace: kube-system
spec:
containers:
- command:
- etcd
- --advertise-client-urls=http://10.1.1.1:12379
- --listen-client-urls=http://0.0.0.0:12379
- --listen-peer-urls=http://localhost:12380
image: quay.io/coreos/etcd:latest
name: etcd
hostNetwork: true
nodeName: kube-master
---
apiVersion: batch/v1
kind: Job
metadata:
name: flannel-etcdctl
namespace: kube-system
spec:
template:
spec:
containers:
- name: flannel-etcdctl
image: quay.io/coreos/etcd:latest
command: ["etcdctl"]
args: ["--endpoints=http://10.1.1.1:12379", "set", "/flannel2/network/config", '{ "Network": "10.5.0.0/16", "Backend": {"Type": "vxlan", "VNI": 2}}']
hostNetwork: true
nodeName: kube-master
restartPolicy: Never
---
apiVersion: extensions/v1beta1
kind: DaemonSet
metadata:
name: kube-flannel2-ds
namespace: kube-system
labels:
tier: node
app: flannel2
spec:
template:
metadata:
labels:
tier: node
app: flannel2
spec:
hostNetwork: true
nodeSelector:
beta.kubernetes.io/arch: amd64
tolerations:
- key: node-role.kubernetes.io/master
operator: Exists
effect: NoSchedule
serviceAccountName: flannel2
initContainers:
- name: install-cni
image: quay.io/coreos/flannel:v0.10.0-amd64
command:
- cp
args:
- -f
- /etc/kube-flannel/flannel2-conf.json
- /etc/cni/multus/net.d/10-flannel.conf
volumeMounts:
- name: cni
mountPath: /etc/cni/multus/net.d
- name: flannel2-cfg
mountPath: /etc/kube-flannel/
containers:
- name: kube-flannel2
image: quay.io/coreos/flannel:v0.10.0-amd64
command:
- /opt/bin/flanneld
args:
- --ip-masq
- --etcd-endpoints=http://10.1.1.1:12379
- -iface=eth1
- -subnet-file=/run/flannel/flannel2.env
- -etcd-prefix=/flannel2/network
resources:
requests:
cpu: "100m"
memory: "50Mi"
limits:
cpu: "100m"
memory: "50Mi"
securityContext:
privileged: true
env:
- name: POD_NAME
valueFrom:
fieldRef:
fieldPath: metadata.name
- name: POD_NAMESPACE
valueFrom:
fieldRef:
fieldPath: metadata.namespace
volumeMounts:
- name: run
mountPath: /run
volumes:
- name: run
hostPath:
path: /run
- name: cni
hostPath:
path: /etc/cni/multus/net.d
- name: flannel2-cfg
configMap:
name: kube-flannel2-cfg
---
apiVersion: "kubernetes.cni.cncf.io/v1"
kind: Network
metadata:
name: flannel-2

View File

@@ -1,30 +0,0 @@
---
apiVersion: "k8s.cni.cncf.io/v1"
kind: NetworkAttachmentDefinition
metadata:
name: ptp-tuning-conflist
spec:
config: '{
"cniVersion": "0.3.1",
"name": "ptp-tuning-conflist",
"plugins": [{
"type": "ptp",
"ipMasq": true,
"mtu": 512,
"ipam": {
"type": "host-local",
"subnet": "172.16.0.0/24"
},
"dns": {
"nameservers": ["172.16.1.1"]
}
},
{
"name": "mytuning",
"type": "tuning",
"sysctl": {
"net.core.somaxconn": "500"
}
}
]
}'

View File

@@ -1,13 +0,0 @@
---
apiVersion: v1
kind: Pod
metadata:
name: pod-case-01
annotations:
k8s.v1.cni.cncf.io/networks: macvlan-conf-1
spec:
containers:
- name: pod-case-01
image: docker.io/centos/tools:latest
command:
- /sbin/init

View File

@@ -1,18 +0,0 @@
---
apiVersion: v1
kind: Pod
metadata:
name: pod-case-02
annotations:
k8s.v1.cni.cncf.io/networks: '[
{ "name": "macvlan-conf-2" },
{ "name": "vlan-conf-1-1",
"namespace": "testns1",
"interface": "vlan1-1" }
]'
spec:
containers:
- name: pod-case-02
image: docker.io/centos/tools:latest
command:
- /sbin/init

View File

@@ -1,17 +0,0 @@
---
apiVersion: v1
kind: Pod
metadata:
name: pod-case-03
annotations:
k8s.v1.cni.cncf.io/networks: '[
{ "name": "macvlan-conf-3" },
{ "name": "macvlan-conf-4" },
{ "name": "flannel-2" }
]'
spec:
containers:
- name: pod-case-03
image: docker.io/centos/tools:latest
command:
- /sbin/init

View File

@@ -1,11 +0,0 @@
---
apiVersion: v1
kind: Pod
metadata:
name: pod-case-04
spec:
containers:
- name: pod-case-04
image: docker.io/centos/tools:latest
command:
- /sbin/init

View File

@@ -1,15 +0,0 @@
---
apiVersion: v1
kind: Pod
metadata:
name: pod-case-05
annotations:
k8s.v1.cni.cncf.io/networks: '[
{ "name": "ptp-tuning-conflist" }
]'
spec:
containers:
- name: pod-case-05
image: docker.io/centos/tools:latest
command:
- /sbin/init

View File

@@ -1,14 +0,0 @@
---
apiVersion: v1
kind: Pod
metadata:
name: samplepod
annotations:
k8s.v1.cni.cncf.io/networks: macvlan-conf
spec:
containers:
- name: samplepod
command: ["/bin/bash", "-c", "sleep 2000000000000"]
image: dougbtv/centos-network
ports:
- containerPort: 80

View File

@@ -1,21 +0,0 @@
apiVersion: "k8s.cni.cncf.io/v1"
kind: NetworkAttachmentDefinition
metadata:
name: sriov-net-a
annotations:
k8s.v1.cni.cncf.io/resourceName: intel.com/sriov
spec:
config: '{
"type": "sriov",
"vlan": 1000,
"ipam": {
"type": "host-local",
"subnet": "10.56.217.0/24",
"rangeStart": "10.56.217.171",
"rangeEnd": "10.56.217.181",
"routes": [{
"dst": "0.0.0.0/0"
}],
"gateway": "10.56.217.1"
}
}'

47
examples/sriov-pod.yml Normal file
View File

@@ -0,0 +1,47 @@
# This net-attach-def defines SR-IOV CNI config
# Please see https://github.com/intel/sriov-cni and https://github.com/intel/sriov-network-device-plugin
# for its detail.
---
apiVersion: "k8s.cni.cncf.io/v1"
kind: NetworkAttachmentDefinition
metadata:
name: sriov-net-a
annotations:
k8s.v1.cni.cncf.io/resourceName: intel.com/sriov
spec:
config: '{
"type": "sriov",
"vlan": 1000,
"ipam": {
"type": "host-local",
"subnet": "10.56.217.0/24",
"rangeStart": "10.56.217.171",
"rangeEnd": "10.56.217.181",
"routes": [{
"dst": "0.0.0.0/0"
}],
"gateway": "10.56.217.1"
}
}'
---
apiVersion: v1
kind: Pod
metadata:
name: testpod1
labels:
env: test
annotations:
k8s.v1.cni.cncf.io/networks: sriov-net-a
spec:
containers:
- name: appcntr1
image: centos/tools
imagePullPolicy: IfNotPresent
command: [ "/bin/bash", "-c", "--" ]
args: [ "while true; do sleep 300000; done;" ]
resources:
requests:
intel.com/sriov: '1'
limits:
intel.com/sriov: '1'
restartPolicy: "Never"

261
glide.lock generated
View File

@@ -1,261 +0,0 @@
hash: 0c4ea2a342364d2ff3b43242730cb3b1db3b7e8456f6cf43da3c51dbb67e18da
updated: 2018-07-27T03:29:02.093332104+01:00
imports:
- name: github.com/containernetworking/cni
version: 07c1a6da47b7fbf8b357f4949ecce2113e598491
subpackages:
- libcni
- pkg/invoke
- pkg/ip
- pkg/ipam
- pkg/skel
- pkg/types
- pkg/types/020
- pkg/types/current
- pkg/version
- name: github.com/containernetworking/plugins
version: 2b8b1ac0af4568e928d96ccc5f47b075416eeabd
subpackages:
- pkg/ns
- pkg/testutils
- name: github.com/ghodss/yaml
version: 73d445a93680fa1a78ae23a5839bad48f32ba1ee
- name: github.com/gogo/protobuf
version: c0656edd0d9eab7c66d1eb0c568f9039345796f7
subpackages:
- proto
- sortkeys
- name: github.com/golang/glog
version: 44145f04b68cf362d9c4df2182967c2275eaefed
- name: github.com/golang/protobuf
version: b4deda0973fb4c70b50d226b1af49f3da59f5265
subpackages:
- proto
- ptypes
- ptypes/any
- ptypes/duration
- ptypes/timestamp
- name: github.com/google/btree
version: 7d79101e329e5a3adf994758c578dab82b90c017
- name: github.com/google/gofuzz
version: 44d81051d367757e1c7c6a5a86423ece9afcf63c
- name: github.com/googleapis/gnostic
version: 0c5108395e2debce0d731cf0287ddf7242066aba
subpackages:
- OpenAPIv2
- compiler
- extensions
- name: github.com/gregjones/httpcache
version: 787624de3eb7bd915c329cba748687a3b22666a6
subpackages:
- diskcache
- name: github.com/imdario/mergo
version: 6633656539c1639d9d78127b7d47c622b5d7b6dc
- name: github.com/json-iterator/go
version: f2b4162afba35581b6d4a50d3b8f34e33c144682
- name: github.com/modern-go/concurrent
version: bacd9c7ef1dd9b15be4a9909b8ac7a4e313eec94
- name: github.com/modern-go/reflect2
version: 05fbef0ca5da472bbf96c9322b84a53edc03c9fd
- name: github.com/onsi/ginkgo
version: 7f8ab55aaf3b86885aa55b762e803744d1674700
subpackages:
- config
- internal/codelocation
- internal/containernode
- internal/failer
- internal/leafnodes
- internal/remote
- internal/spec
- internal/specrunner
- internal/suite
- internal/testingtproxy
- internal/writer
- reporters
- reporters/stenographer
- types
- name: github.com/onsi/gomega
version: 2152b45fa28a361beba9aab0885972323a444e28
subpackages:
- format
- internal/assertion
- internal/asyncassertion
- internal/oraclematcher
- internal/testingtsupport
- matchers
- matchers/support/goraph/bipartitegraph
- matchers/support/goraph/edge
- matchers/support/goraph/node
- matchers/support/goraph/util
- types
- name: github.com/peterbourgon/diskv
version: 5f041e8faa004a95c88a202771f4cc3e991971e6
- name: github.com/pkg/errors
version: 816c9085562cd7ee03e7f8188a1cfd942858cded
- name: github.com/spf13/pflag
version: 583c0c0531f06d5278b7d917446061adc344b5cd
- name: github.com/vishvananda/netlink
version: 6e453822d85ef5721799774b654d4d02fed62afb
subpackages:
- nl
- name: github.com/vishvananda/netns
version: 54f0e4339ce73702a0607f49922aaa1e749b418d
- name: golang.org/x/crypto
version: 49796115aa4b964c318aad4f3084fdb41e9aa067
subpackages:
- ssh/terminal
- name: golang.org/x/net
version: 1c05540f6879653db88113bc4a2b70aec4bd491f
subpackages:
- context
- http2
- http2/hpack
- idna
- lex/httplex
- name: golang.org/x/sys
version: 95c6576299259db960f6c5b9b69ea52422860fce
subpackages:
- unix
- windows
- name: golang.org/x/text
version: b19bf474d317b857955b12035d2c5acb57ce8b01
subpackages:
- secure/bidirule
- transform
- unicode/bidi
- unicode/norm
- name: golang.org/x/time
version: f51c12702a4d776e4c1fa9b0fabab841babae631
subpackages:
- rate
- name: gopkg.in/inf.v0
version: 3887ee99ecf07df5b447e9b00d9c0b2adaa9f3e4
- name: gopkg.in/yaml.v2
version: 670d4cfef0544295bc27a114dbac37980d83185a
- name: k8s.io/api
version: 2d6f90ab1293a1fb871cf149423ebb72aa7423aa
subpackages:
- admissionregistration/v1alpha1
- admissionregistration/v1beta1
- apps/v1
- apps/v1beta1
- apps/v1beta2
- authentication/v1
- authentication/v1beta1
- authorization/v1
- authorization/v1beta1
- autoscaling/v1
- autoscaling/v2beta1
- batch/v1
- batch/v1beta1
- batch/v2alpha1
- certificates/v1beta1
- core/v1
- events/v1beta1
- extensions/v1beta1
- networking/v1
- policy/v1beta1
- rbac/v1
- rbac/v1alpha1
- rbac/v1beta1
- scheduling/v1alpha1
- scheduling/v1beta1
- settings/v1alpha1
- storage/v1
- storage/v1alpha1
- storage/v1beta1
- name: k8s.io/apimachinery
version: 103fd098999dc9c0c88536f5c9ad2e5da39373ae
subpackages:
- pkg/api/errors
- pkg/api/meta
- pkg/api/resource
- pkg/apis/meta/v1
- pkg/apis/meta/v1/unstructured
- pkg/apis/meta/v1beta1
- pkg/conversion
- pkg/conversion/queryparams
- pkg/fields
- pkg/labels
- pkg/runtime
- pkg/runtime/schema
- pkg/runtime/serializer
- pkg/runtime/serializer/json
- pkg/runtime/serializer/protobuf
- pkg/runtime/serializer/recognizer
- pkg/runtime/serializer/streaming
- pkg/runtime/serializer/versioning
- pkg/selection
- pkg/types
- pkg/util/clock
- pkg/util/errors
- pkg/util/framer
- pkg/util/intstr
- pkg/util/json
- pkg/util/net
- pkg/util/runtime
- pkg/util/sets
- pkg/util/validation
- pkg/util/validation/field
- pkg/util/wait
- pkg/util/yaml
- pkg/version
- pkg/watch
- third_party/forked/golang/reflect
- name: k8s.io/client-go
version: 59698c7d9724b0f95f9dc9e7f7dfdcc3dfeceb82
subpackages:
- discovery
- kubernetes
- kubernetes/scheme
- kubernetes/typed/admissionregistration/v1alpha1
- kubernetes/typed/admissionregistration/v1beta1
- kubernetes/typed/apps/v1
- kubernetes/typed/apps/v1beta1
- kubernetes/typed/apps/v1beta2
- kubernetes/typed/authentication/v1
- kubernetes/typed/authentication/v1beta1
- kubernetes/typed/authorization/v1
- kubernetes/typed/authorization/v1beta1
- kubernetes/typed/autoscaling/v1
- kubernetes/typed/autoscaling/v2beta1
- kubernetes/typed/batch/v1
- kubernetes/typed/batch/v1beta1
- kubernetes/typed/batch/v2alpha1
- kubernetes/typed/certificates/v1beta1
- kubernetes/typed/core/v1
- kubernetes/typed/events/v1beta1
- kubernetes/typed/extensions/v1beta1
- kubernetes/typed/networking/v1
- kubernetes/typed/policy/v1beta1
- kubernetes/typed/rbac/v1
- kubernetes/typed/rbac/v1alpha1
- kubernetes/typed/rbac/v1beta1
- kubernetes/typed/scheduling/v1alpha1
- kubernetes/typed/scheduling/v1beta1
- kubernetes/typed/settings/v1alpha1
- kubernetes/typed/storage/v1
- kubernetes/typed/storage/v1alpha1
- kubernetes/typed/storage/v1beta1
- pkg/apis/clientauthentication
- pkg/apis/clientauthentication/v1alpha1
- pkg/apis/clientauthentication/v1beta1
- pkg/version
- plugin/pkg/client/auth/exec
- rest
- rest/watch
- tools/auth
- tools/clientcmd
- tools/clientcmd/api
- tools/clientcmd/api/latest
- tools/clientcmd/api/v1
- tools/metrics
- tools/reference
- transport
- util/cert
- util/connrotation
- util/flowcontrol
- util/homedir
- util/integer
- util/retry
testImports: []

View File

@@ -1,36 +0,0 @@
package: github.com/intel/multus-cni
ignore:
- bytes
import:
- package: github.com/containernetworking/cni
version: 07c1a6da47b7fbf8b357f4949ecce2113e598491
subpackages:
- pkg/skel
- pkg/types
- pkg/version
- package: github.com/containernetworking/plugins
version: 2b8b1ac0af4568e928d96ccc5f47b075416eeabd
subpackages:
- pkg/ip
- pkg/ipam
- pkg/ns
- package: github.com/onsi/ginkgo
version: 7f8ab55aaf3b86885aa55b762e803744d1674700
- package: github.com/onsi/gomega
version: 2152b45fa28a361beba9aab0885972323a444e28
- package: github.com/golang/glog
- package: github.com/vishvananda/netlink
- package: k8s.io/apimachinery
version: kubernetes-1.11.1
- package: k8s.io/api
version: kubernetes-1.11.1
subpackages:
- core/v1
- package: k8s.io/client-go
version: kubernetes-1.11.1
subpackages:
- kubernetes
- tools/clientcmd
- util/retry
- package: github.com/vishvananda/netns
- package: github.com/pkg/errors

100
go.mod Normal file
View File

@@ -0,0 +1,100 @@
module gopkg.in/k8snetworkplumbingwg/multus-cni.v3
go 1.17
require (
github.com/blang/semver v3.5.1+incompatible
github.com/containernetworking/cni v1.1.2
github.com/containernetworking/plugins v1.1.0
github.com/fsnotify/fsnotify v1.5.1
github.com/go-logr/logr v1.2.3 // indirect
github.com/gorilla/mux v1.8.0
github.com/k8snetworkplumbingwg/network-attachment-definition-client v1.3.0
github.com/onsi/ginkgo v1.16.5
github.com/onsi/gomega v1.17.0
github.com/pkg/errors v0.9.1
github.com/vishvananda/netlink v1.1.1-0.20210330154013-f5de75959ad5
golang.org/x/net v0.0.0-20220425223048-2871e0cb64e4
golang.org/x/sys v0.0.0-20220422013727-9388b58f7150
google.golang.org/grpc v1.40.0
gopkg.in/natefinch/lumberjack.v2 v2.0.0
k8s.io/api v0.22.8
k8s.io/apimachinery v0.22.8
k8s.io/client-go v0.22.8
k8s.io/klog v1.0.0
k8s.io/klog/v2 v2.60.1 // indirect
k8s.io/kube-openapi v0.0.0-20220413171646-5e7f5fdc6da6 // indirect
k8s.io/kubelet v0.22.8
sigs.k8s.io/yaml v1.3.0 // indirect
)
require github.com/prometheus/client_golang v1.12.2
require (
github.com/beorn7/perks v1.0.1 // indirect
github.com/cespare/xxhash/v2 v2.1.2 // indirect
github.com/davecgh/go-spew v1.1.1 // indirect
github.com/evanphx/json-patch v4.12.0+incompatible // indirect
github.com/gogo/protobuf v1.3.2 // indirect
github.com/golang/groupcache v0.0.0-20210331224755-41bb18bfe9da // indirect
github.com/golang/protobuf v1.5.2 // indirect
github.com/google/go-cmp v0.5.5 // indirect
github.com/google/gofuzz v1.1.0 // indirect
github.com/googleapis/gnostic v0.5.5 // indirect
github.com/imdario/mergo v0.3.11 // indirect
github.com/json-iterator/go v1.1.12 // indirect
github.com/matttproud/golang_protobuf_extensions v1.0.2-0.20181231171920-c182affec369 // indirect
github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd // indirect
github.com/modern-go/reflect2 v1.0.2 // indirect
github.com/nxadm/tail v1.4.8 // indirect
github.com/prometheus/client_model v0.2.0 // indirect
github.com/prometheus/common v0.32.1 // indirect
github.com/prometheus/procfs v0.7.3 // indirect
github.com/spf13/pflag v1.0.5 // indirect
github.com/vishvananda/netns v0.0.0-20210104183010-2eb08e3e575f // indirect
golang.org/x/oauth2 v0.0.0-20210819190943-2bc19b11175f // indirect
golang.org/x/term v0.0.0-20210927222741-03fcf44c2211 // indirect
golang.org/x/text v0.3.7 // indirect
golang.org/x/time v0.0.0-20210723032227-1f47c861a9ac // indirect
golang.org/x/xerrors v0.0.0-20220411194840-2f41105eb62f // indirect
google.golang.org/appengine v1.6.7 // indirect
google.golang.org/genproto v0.0.0-20220107163113-42d7afdf6368 // indirect
google.golang.org/protobuf v1.28.0 // indirect
gopkg.in/inf.v0 v0.9.1 // indirect
gopkg.in/tomb.v1 v1.0.0-20141024135613-dd632973f1e7 // indirect
gopkg.in/yaml.v2 v2.4.0 // indirect
gopkg.in/yaml.v3 v3.0.0-20210107192922-496545a6307b // indirect
k8s.io/utils v0.0.0-20211116205334-6203023598ed // indirect
sigs.k8s.io/structured-merge-diff/v4 v4.2.1 // indirect
)
replace (
github.com/gogo/protobuf => github.com/gogo/protobuf v1.3.2
k8s.io/api => k8s.io/api v0.22.8
k8s.io/apiextensions-apiserver => k8s.io/apiextensions-apiserver v0.22.8
k8s.io/apimachinery => k8s.io/apimachinery v0.22.8
k8s.io/apiserver => k8s.io/apiserver v0.22.8
k8s.io/cli-runtime => k8s.io/cli-runtime v0.22.8
k8s.io/client-go => k8s.io/client-go v0.22.8
k8s.io/cloud-provider => k8s.io/cloud-provider v0.22.8
k8s.io/cluster-bootstrap => k8s.io/cluster-bootstrap v0.22.8
k8s.io/code-generator => k8s.io/code-generator v0.22.8
k8s.io/component-base => k8s.io/component-base v0.22.8
k8s.io/component-helpers => k8s.io/component-helpers v0.22.8
k8s.io/controller-manager => k8s.io/controller-manager v0.22.8
k8s.io/cri-api => k8s.io/cri-api v0.22.8
k8s.io/csi-translation-lib => k8s.io/csi-translation-lib v0.22.8
k8s.io/kube-aggregator => k8s.io/kube-aggregator v0.22.8
k8s.io/kube-controller-manager => k8s.io/kube-controller-manager v0.22.8
k8s.io/kube-openapi => k8s.io/kube-openapi v0.0.0-20211109043538-20434351676c
k8s.io/kube-proxy => k8s.io/kube-proxy v0.22.8
k8s.io/kube-scheduler => k8s.io/kube-scheduler v0.22.8
k8s.io/kubectl => k8s.io/kubectl v0.22.8
k8s.io/kubelet => k8s.io/kubelet v0.22.8
k8s.io/kubernetes => k8s.io/kubernetes v1.22.8
k8s.io/legacy-cloud-providers => k8s.io/legacy-cloud-providers v0.22.8
k8s.io/metrics => k8s.io/metrics v0.22.8
k8s.io/mount-utils => k8s.io/mount-utils v0.22.8
k8s.io/pod-security-admission => k8s.io/pod-security-admission v0.22.8
k8s.io/sample-apiserver => k8s.io/sample-apiserver v0.22.8
)

1344
go.sum Normal file

File diff suppressed because it is too large Load Diff

61
hack/build-go.sh Executable file
View File

@@ -0,0 +1,61 @@
#!/usr/bin/env bash
set -e
DEST_DIR="bin"
if [ ! -d ${DEST_DIR} ]; then
mkdir ${DEST_DIR}
fi
# version information
hasGit=true
git version > /dev/null 2>&1 || hasGit=false
GIT_SHA=""
GIT_TREE_STATE=""
GIT_TAG=""
GIT_TAG_LAST=""
RELEASE_STATUS=""
if $hasGit; then
set +e
GIT_SHA=$(git rev-parse --short HEAD)
# Tree state is "dirty" if there are uncommitted changes, untracked files are ignored
GIT_TREE_STATE=$(test -n "`git status --porcelain --untracked-files=no`" && echo "dirty" || echo "clean")
# Empty string if we are not building a tag
GIT_TAG=$(git describe --tags --abbrev=0 --exact-match 2>/dev/null || true)
# Find most recent tag
GIT_TAG_LAST=$(git describe --tags --abbrev=0 2>/dev/null || true)
set -e
fi
# VERSION override mechanism if needed
VERSION=${VERSION:-}
if [[ -n "${VERSION}" || -n "${GIT_TAG}" ]]; then
RELEASE_STATUS=",released"
fi
if [ -z "$VERSION" ]; then
VERSION=$GIT_TAG_LAST
fi
# Add version/commit/date into binary
DATE=$(date -u -d "@${SOURCE_DATE_EPOCH:-$(date +%s)}" --iso-8601=seconds)
COMMIT=${COMMIT:-$(git rev-parse --verify HEAD)}
LDFLAGS="-X gopkg.in/k8snetworkplumbingwg/multus-cni.v3/pkg/multus.version=${VERSION} \
-X gopkg.in/k8snetworkplumbingwg/multus-cni.v3/pkg/multus.commit=${COMMIT} \
-X gopkg.in/k8snetworkplumbingwg/multus-cni.v3/pkg/multus.gitTreeState=${GIT_TREE_STATE} \
-X gopkg.in/k8snetworkplumbingwg/multus-cni.v3/pkg/multus.releaseStatus=${RELEASE_STATUS} \
-X gopkg.in/k8snetworkplumbingwg/multus-cni.v3/pkg/multus.date=${DATE}"
export CGO_ENABLED=0
# build with go modules
export GO111MODULE=on
BUILD_ARGS=(-o ${DEST_DIR}/multus -tags no_openssl)
if [ -n "$MODMODE" ]; then
BUILD_ARGS+=(-mod "$MODMODE")
fi
echo "Building multus"
go build ${BUILD_ARGS[*]} -ldflags "${LDFLAGS}" "$@" ./cmd/multus
echo "Building multus-daemon"
go build -o "${DEST_DIR}"/multus-daemon -ldflags "${LDFLAGS}" ./cmd/multus-daemon
echo "Building multus-shim"
go build -o "${DEST_DIR}"/multus-shim -ldflags "${LDFLAGS}" ./cmd/multus-shim

23
hack/test-go.sh Executable file
View File

@@ -0,0 +1,23 @@
#!/usr/bin/env bash
set -e
# this if... will be removed when gomodules goes default
if [ "$GO111MODULE" == "off" ]; then
echo "Warning: this will be deprecated in near future so please use go modules!"
ORG_PATH="gopkg.in/k8snetworkplumbingwg"
REPO_PATH="${ORG_PATH}/multus-cni"
if [ ! -h gopath/src/${REPO_PATH} ]; then
mkdir -p gopath/src/${ORG_PATH}
ln -s ../../../.. gopath/src/${REPO_PATH} || exit 255
fi
export GO15VENDOREXPERIMENT=1
export GOBIN=${PWD}/bin
export GOPATH=${PWD}/gopath
bash -c "umask 0; cd ${GOPATH}/src/${REPO_PATH}; PATH=${GOROOT}/bin:$(pwd)/bin:${PATH} go test -v -covermode=count -coverprofile=coverage.out ./..."
else
# test with go modules
bash -c "umask 0; go test -v -covermode=count -coverprofile=coverage.out ./..."
fi

17
images/Dockerfile Normal file
View File

@@ -0,0 +1,17 @@
# This Dockerfile is used to build the image available on DockerHub
FROM golang:1.18 as build
# Add everything
ADD . /usr/src/multus-cni
RUN cd /usr/src/multus-cni && \
./hack/build-go.sh
FROM python:slim
LABEL org.opencontainers.image.source https://github.com/k8snetworkplumbingwg/multus-cni
COPY --from=build /usr/src/multus-cni/bin /usr/src/multus-cni/bin
COPY --from=build /usr/src/multus-cni/LICENSE /usr/src/multus-cni/LICENSE
WORKDIR /
ADD ./images/entrypoint.sh /
ENTRYPOINT ["/entrypoint.sh"]

22
images/Dockerfile.arm32 Normal file
View File

@@ -0,0 +1,22 @@
# This Dockerfile is used to build the image available on DockerHub
FROM golang:1.18 as build
# Add everything
ADD . /usr/src/multus-cni
ENV GOARCH "arm"
ENV GOOS "linux"
RUN cd /usr/src/multus-cni && \
./hack/build-go.sh
# build arm container
FROM arm32v7/python:slim
LABEL org.opencontainers.image.source https://github.com/k8snetworkplumbingwg/multus-cni
COPY --from=build /usr/src/multus-cni/bin /usr/src/multus-cni/bin
COPY --from=build /usr/src/multus-cni/LICENSE /usr/src/multus-cni/LICENSE
WORKDIR /
ADD ./images/entrypoint.sh /
ENTRYPOINT ["/entrypoint.sh"]

22
images/Dockerfile.arm64 Normal file
View File

@@ -0,0 +1,22 @@
# This Dockerfile is used to build the image available on DockerHub
FROM golang:1.18 as build
# Add everything
ADD . /usr/src/multus-cni
ENV GOARCH "arm64"
ENV GOOS "linux"
RUN cd /usr/src/multus-cni && \
./hack/build-go.sh
# build arm64 container
FROM arm64v8/python:slim
LABEL org.opencontainers.image.source https://github.com/k8snetworkplumbingwg/multus-cni
COPY --from=build /usr/src/multus-cni/bin /usr/src/multus-cni/bin
COPY --from=build /usr/src/multus-cni/LICENSE /usr/src/multus-cni/LICENSE
WORKDIR /
ADD ./images/entrypoint.sh /
ENTRYPOINT ["/entrypoint.sh"]

View File

@@ -0,0 +1,21 @@
# This dockerfile is specific to building Multus for OpenShift
FROM openshift/origin-release:golang-1.16 as builder
ADD . /usr/src/multus-cni
WORKDIR /usr/src/multus-cni
ENV GO111MODULE=off
RUN ./hack/build-go.sh
FROM openshift/origin-base
LABEL org.opencontainers.image.source https://github.com/k8snetworkplumbingwg/multus-cni
RUN mkdir -p /usr/src/multus-cni/images && mkdir -p /usr/src/multus-cni/bin
COPY --from=builder /usr/src/multus-cni/bin/multus /usr/src/multus-cni/bin
ADD ./images/entrypoint.sh /
LABEL io.k8s.display-name="Multus CNI" \
io.k8s.description="This is a component of OpenShift Container Platform and provides a meta CNI plugin." \
io.openshift.tags="openshift" \
maintainer="Doug Smith <dosmith@redhat.com>"
ENTRYPOINT ["/entrypoint.sh"]

22
images/Dockerfile.ppc64le Normal file
View File

@@ -0,0 +1,22 @@
# This Dockerfile is used to build the image available on DockerHub
FROM golang:1.18 as build
# Add everything
ADD . /usr/src/multus-cni
ENV GOARCH "ppc64le"
ENV GOOS "linux"
RUN cd /usr/src/multus-cni && \
./hack/build-go.sh
# build ppc container
FROM ppc64le/python:slim
LABEL org.opencontainers.image.source https://github.com/k8snetworkplumbingwg/multus-cni
COPY --from=build /usr/src/multus-cni/bin /usr/src/multus-cni/bin
COPY --from=build /usr/src/multus-cni/LICENSE /usr/src/multus-cni/LICENSE
WORKDIR /
ADD ./images/entrypoint.sh /
ENTRYPOINT ["/entrypoint.sh"]

21
images/Dockerfile.s390x Normal file
View File

@@ -0,0 +1,21 @@
# This Dockerfile is used to build the image available on DockerHub
FROM golang:1.18 as build
# Add everything
ADD . /usr/src/multus-cni
ENV GOARCH "s390x"
ENV GOOS "linux"
RUN cd /usr/src/multus-cni && \
./hack/build-go.sh
# build s390x container
FROM s390x/python:slim
LABEL org.opencontainers.image.source https://github.com/k8snetworkplumbingwg/multus-cni
COPY --from=build /usr/src/multus-cni/bin /usr/src/multus-cni/bin
COPY --from=build /usr/src/multus-cni/LICENSE /usr/src/multus-cni/LICENSE
WORKDIR /
ADD ./images/entrypoint.sh /
ENTRYPOINT ["/entrypoint.sh"]

16
images/Dockerfile.thick Normal file
View File

@@ -0,0 +1,16 @@
# This Dockerfile is used to build the image available on DockerHub
FROM golang:1.18 as build
# Add everything
ADD . /usr/src/multus-cni
RUN cd /usr/src/multus-cni && \
./hack/build-go.sh
FROM debian:stable-slim
LABEL org.opencontainers.image.source https://github.com/k8snetworkplumbingwg/multus-cni
COPY --from=build /usr/src/multus-cni/bin /usr/src/multus-cni/bin
COPY --from=build /usr/src/multus-cni/LICENSE /usr/src/multus-cni/LICENSE
WORKDIR /
ENTRYPOINT [ "/usr/src/multus-cni/bin/multus-daemon" ]

View File

@@ -5,7 +5,7 @@ This is used for distribution of Multus in a Docker image.
Typically you'd build this from the root of your Multus clone, as such:
```
$ docker build -t dougbtv/multus .
$ docker build -t dougbtv/multus -f images/Dockerfile .
```
---
@@ -15,7 +15,7 @@ $ docker build -t dougbtv/multus .
You may wish to deploy Multus as a daemonset, you can do so by starting with the example Daemonset shown here:
```
$ kubectl create -f ./images/multus-daemonset.yml
$ kubectl create -f ./deployments/multus-daemonset.yml
```
Note: The likely best practice here is to build your own image given the Dockerfile, and then push it to your preferred registry, and change the `image` fields in the Daemonset YAML to reference that image.
@@ -41,9 +41,7 @@ in lexicographical order in cni-conf-dir).
./entrypoint.sh
-h --help
--cni-conf-dir=/host/etc/cni/net.d
--cni-bin-dir=/host/opt/cni/bin
--multus-conf-file=/usr/src/multus-cni/images/70-multus.conf
--multus-bin-file=/usr/src/multus-cni/bin/multus
--multus-kubeconfig-file-host=/etc/cni/net.d/multus.d/multus.kubeconfig
```
@@ -65,4 +63,4 @@ Example docker run command:
$ docker run -it -v /opt/cni/bin/:/host/opt/cni/bin/ -v /etc/cni/net.d/:/host/etc/cni/net.d/ --entrypoint=/bin/bash dougbtv/multus
```
Originally inspired by and is a portmanteau of the [Flannel daemonset](https://github.com/coreos/flannel/blob/master/Documentation/kube-flannel.yml), the [Calico Daemonset](https://github.com/projectcalico/calico/blob/master/v2.0/getting-started/kubernetes/installation/hosted/k8s-backend-addon-manager/calico-daemonset.yaml), and the [Calico CNI install bash script](https://github.com/projectcalico/cni-plugin/blob/be4df4db2e47aa7378b1bdf6933724bac1f348d0/k8s-install/scripts/install-cni.sh#L104-L153).
Originally inspired by and is a portmanteau of the [Flannel daemonset](https://github.com/coreos/flannel/blob/master/Documentation/kube-flannel.yml), the [Calico Daemonset](https://docs.projectcalico.org/manifests/calico.yaml), and the [Calico CNI install bash script](https://github.com/projectcalico/cni-plugin/blob/be4df4db2e47aa7378b1bdf6933724bac1f348d0/k8s-install/scripts/install-cni.sh#L104-L153).

View File

@@ -1,38 +1,111 @@
#!/bin/bash
# multus thin plugin install shell script
#
# note: this script is designed for quick-install or just 'tasting multus' in your test environment.
# hence it does not cover advanced Kubernetes cluster operation (update, uninstall and so on).
# Always exit on errors.
set -e
# Trap sigterm
function exitonsigterm() {
echo "Trapped sigterm, exiting."
exit 0
}
trap exitonsigterm SIGTERM
# Set our known directories.
CNI_CONF_DIR="/host/etc/cni/net.d"
CNI_BIN_DIR="/host/opt/cni/bin"
ADDITIONAL_BIN_DIR=""
MULTUS_CONF_FILE="/usr/src/multus-cni/images/70-multus.conf"
MULTUS_AUTOCONF_DIR="/host/etc/cni/net.d"
MULTUS_BIN_FILE="/usr/src/multus-cni/bin/multus"
MULTUS_KUBECONFIG_FILE_HOST="/etc/cni/net.d/multus.d/multus.kubeconfig"
MULTUS_TEMP_KUBECONFIG="/tmp/multus.kubeconfig"
MULTUS_MASTER_CNI_FILE_NAME=""
MULTUS_NAMESPACE_ISOLATION=false
MULTUS_GLOBAL_NAMESPACES=""
MULTUS_LOG_TO_STDERR=true
MULTUS_LOG_LEVEL=""
MULTUS_LOG_FILE=""
MULTUS_READINESS_INDICATOR_FILE=""
OVERRIDE_NETWORK_NAME=false
MULTUS_CLEANUP_CONFIG_ON_EXIT=false
RESTART_CRIO=false
CRIO_RESTARTED_ONCE=false
RENAME_SOURCE_CONFIG_FILE=false
SKIP_BINARY_COPY=false
FORCE_CNI_VERSION=false # force-cni-version is only for e2e-kind.
# Give help text for parameters.
function usage()
{
echo -e "This is an entrypoint script for Multus CNI to overlay its binary and "
echo -e "configuration into locations in a filesystem. The configuration & binary file "
echo -e "will be copied to the corresponding configuration directory. When "
echo -e "'--multus-conf-file=auto' is used, 00-multus.conf will be automatically "
echo -e "generated from the CNI configuration file of the master plugin (the first file "
echo -e "in lexicographical order in cni-conf-dir)."
echo -e "This is an entrypoint script for Multus CNI to overlay its configuration into"
echo -e "locations in a filesystem. The configuration file will be copied to the"
echo -e "corresponding configuration directory. When '--multus-conf-file=auto' is used,"
echo -e "00-multus.conf will be automatically generated from the CNI configuration file"
echo -e "of the master plugin (the first file in lexicographical order in cni-conf-dir)."
echo -e "When '--multus-master-cni-file-name' is used, 00-multus.conf will be"
echo -e "automatically generated from the specific file rather than the first file."
echo -e ""
echo -e "./entrypoint.sh"
echo -e "\t-h --help"
echo -e "\t--cni-conf-dir=$CNI_CONF_DIR"
echo -e "\t--cni-bin-dir=$CNI_BIN_DIR"
echo -e "\t--cni-conf-dir=$CNI_CONF_DIR"
echo -e "\t--cni-version=<cniVersion (e.g. 0.3.1)>"
echo -e "\t--multus-conf-file=$MULTUS_CONF_FILE"
echo -e "\t--multus-bin-file=$MULTUS_BIN_FILE"
echo -e "\t--skip-multus-binary-copy=$SKIP_BINARY_COPY"
echo -e "\t--multus-kubeconfig-file-host=$MULTUS_KUBECONFIG_FILE_HOST"
echo -e "\t--multus-master-cni-file-name=$MULTUS_MASTER_CNI_FILE_NAME (empty by default, example: 10-calico.conflist)"
echo -e "\t--namespace-isolation=$MULTUS_NAMESPACE_ISOLATION"
echo -e "\t--global-namespaces=$MULTUS_GLOBAL_NAMESPACES (used only with --namespace-isolation=true)"
echo -e "\t--multus-autoconfig-dir=$MULTUS_AUTOCONF_DIR (used only with --multus-conf-file=auto)"
echo -e "\t--multus-log-to-stderr=$MULTUS_LOG_TO_STDERR (empty by default, used only with --multus-conf-file=auto)"
echo -e "\t--multus-log-level=$MULTUS_LOG_LEVEL (empty by default, used only with --multus-conf-file=auto)"
echo -e "\t--multus-log-file=$MULTUS_LOG_FILE (empty by default, used only with --multus-conf-file=auto)"
echo -e "\t--override-network-name=false (used only with --multus-conf-file=auto)"
echo -e "\t--cleanup-config-on-exit=false (used only with --multus-conf-file=auto)"
echo -e "\t--rename-conf-file=false (used only with --multus-conf-file=auto)"
echo -e "\t--readiness-indicator-file=$MULTUS_READINESS_INDICATOR_FILE (used only with --multus-conf-file=auto)"
echo -e "\t--additional-bin-dir=$ADDITIONAL_BIN_DIR (adds binDir option to configuration, used only with --multus-conf-file=auto)"
echo -e "\t--restart-crio=false (restarts CRIO after config file is generated)"
}
function log()
{
echo "$(date --iso-8601=seconds) ${1}"
}
function error()
{
log "ERR: {$1}"
}
function warn()
{
log "WARN: {$1}"
}
function checkCniVersion {
cniversion_python_tmpfile=$(mktemp)
cat << EOF > $cniversion_python_tmpfile
import json, sys
def version(v):
return [int(x) for x in v.split(".")]
v_040 = version("0.4.0")
v_top_level = sys.argv[2]
with open(sys.argv[1], "r") as f:
v_nested = json.load(f)["cniVersion"]
if version(v_top_level) >= v_040 and version(v_nested) < v_040:
msg = "Multus cni version is %s while master plugin cni version is %s"
print(msg % (v_top_level, v_nested))
EOF
python3 $cniversion_python_tmpfile $1 $2
}
# Parse parameters given as arguments to this script.
@@ -44,6 +117,16 @@ while [ "$1" != "" ]; do
usage
exit
;;
--cni-version)
CNI_VERSION=$VALUE
;;
# force-cni-version is only for e2e-kind testing
--force-cni-version)
FORCE_CNI_VERSION=$VALUE
;;
--cni-bin-dir)
CNI_BIN_DIR=$VALUE
;;
--cni-conf-dir)
CNI_CONF_DIR=$VALUE
;;
@@ -53,23 +136,53 @@ while [ "$1" != "" ]; do
--multus-conf-file)
MULTUS_CONF_FILE=$VALUE
;;
--multus-bin-file)
MULTUS_BIN_FILE=$VALUE
;;
--multus-kubeconfig-file-host)
MULTUS_KUBECONFIG_FILE_HOST=$VALUE
;;
--multus-master-cni-file-name)
MULTUS_MASTER_CNI_FILE_NAME=$VALUE
;;
--namespace-isolation)
MULTUS_NAMESPACE_ISOLATION=$VALUE
;;
--global-namespaces)
MULTUS_GLOBAL_NAMESPACES=$VALUE
;;
--multus-log-to-stderr)
MULTUS_LOG_TO_STDERR=$VALUE
;;
--multus-log-level)
MULTUS_LOG_LEVEL=$VALUE
;;
--multus-log-file)
MULTUS_LOG_FILE=$VALUE
;;
--multus-autoconfig-dir)
MULTUS_AUTOCONF_DIR=$VALUE
;;
--override-network-name)
OVERRIDE_NETWORK_NAME=$VALUE
;;
--cleanup-config-on-exit)
MULTUS_CLEANUP_CONFIG_ON_EXIT=$VALUE
;;
--restart-crio)
RESTART_CRIO=$VALUE
;;
--rename-conf-file)
RENAME_SOURCE_CONFIG_FILE=$VALUE
;;
--additional-bin-dir)
ADDITIONAL_BIN_DIR=$VALUE
;;
--skip-multus-binary-copy)
SKIP_BINARY_COPY=$VALUE
;;
--readiness-indicator-file)
MULTUS_READINESS_INDICATOR_FILE=$VALUE
;;
*)
echo "WARNING: unknown parameter \"$PARAM\""
warn "unknown parameter \"$PARAM\""
;;
esac
shift
@@ -87,14 +200,19 @@ fi
for i in "${arr[@]}"
do
if [ ! -e "$i" ]; then
echo "Location $i does not exist"
warn "Location $i does not exist"
exit 1;
fi
done
# Copy files into place and atomically move into final binary name
cp -f $MULTUS_BIN_FILE $CNI_BIN_DIR/_multus
mv -f $CNI_BIN_DIR/_multus $CNI_BIN_DIR/multus
if [ "$SKIP_BINARY_COPY" = false ]; then
cp -f $MULTUS_BIN_FILE $CNI_BIN_DIR/_multus
mv -f $CNI_BIN_DIR/_multus $CNI_BIN_DIR/multus
else
log "Entrypoint skipped copying Multus binary."
fi
if [ "$MULTUS_CONF_FILE" != "auto" ]; then
cp -f $MULTUS_CONF_FILE $CNI_CONF_DIR
fi
@@ -106,7 +224,7 @@ MULTUS_KUBECONFIG=$CNI_CONF_DIR/multus.d/multus.kubeconfig
# ------------------------------- Generate a "kube-config"
# Inspired by: https://tinyurl.com/y7r2knme
SERVICE_ACCOUNT_PATH=/var/run/secrets/kubernetes.io/serviceaccount
SERVICE_ACCOUNT_PATH=/run/secrets/kubernetes.io/serviceaccount
KUBE_CA_FILE=${KUBE_CA_FILE:-$SERVICE_ACCOUNT_PATH/ca.crt}
SERVICEACCOUNT_TOKEN=$(cat $SERVICE_ACCOUNT_PATH/token)
SKIP_TLS_VERIFY=${SKIP_TLS_VERIFY:-false}
@@ -116,10 +234,10 @@ SKIP_TLS_VERIFY=${SKIP_TLS_VERIFY:-false}
if [ -f "$SERVICE_ACCOUNT_PATH/token" ]; then
# We're running as a k8d pod - expect some variables.
if [ -z ${KUBERNETES_SERVICE_HOST} ]; then
echo "KUBERNETES_SERVICE_HOST not set"; exit 1;
error "KUBERNETES_SERVICE_HOST not set"; exit 1;
fi
if [ -z ${KUBERNETES_SERVICE_PORT} ]; then
echo "KUBERNETES_SERVICE_PORT not set"; exit 1;
error "KUBERNETES_SERVICE_PORT not set"; exit 1;
fi
if [ "$SKIP_TLS_VERIFY" == "true" ]; then
@@ -132,16 +250,17 @@ if [ -f "$SERVICE_ACCOUNT_PATH/token" ]; then
# to skip TLS verification for now. We should eventually support
# writing more complete kubeconfig files. This is only used
# if the provided CNI network config references it.
touch $MULTUS_KUBECONFIG
chmod ${KUBECONFIG_MODE:-600} $MULTUS_KUBECONFIG
cat > $MULTUS_KUBECONFIG <<EOF
touch $MULTUS_TEMP_KUBECONFIG
chmod ${KUBECONFIG_MODE:-600} $MULTUS_TEMP_KUBECONFIG
# Write the kubeconfig to a temp file first.
cat > $MULTUS_TEMP_KUBECONFIG <<EOF
# Kubeconfig file for Multus CNI plugin.
apiVersion: v1
kind: Config
clusters:
- name: local
cluster:
server: ${KUBERNETES_SERVICE_PROTOCOL:-https}://${KUBERNETES_SERVICE_HOST}:${KUBERNETES_SERVICE_PORT}
server: ${KUBERNETES_SERVICE_PROTOCOL:-https}://[${KUBERNETES_SERVICE_HOST}]:${KUBERNETES_SERVICE_PORT}
$TLS_CFG
users:
- name: multus
@@ -155,32 +274,45 @@ contexts:
current-context: multus-context
EOF
# Atomically move the temp kubeconfig to its permanent home.
mv -f $MULTUS_TEMP_KUBECONFIG $MULTUS_KUBECONFIG
else
echo "WARNING: Doesn't look like we're running in a kubernetes environment (no serviceaccount token)"
warn "Doesn't look like we're running in a kubernetes environment (no serviceaccount token)"
fi
# ---------------------- end Generate a "kube-config".
# ------------------------------- Generate "00-multus.conf"
function generateMultusConf {
if [ "$MULTUS_CONF_FILE" == "auto" ]; then
echo "Generating Multus configuration file ..."
log "Generating Multus configuration file using files in $MULTUS_AUTOCONF_DIR..."
found_master=false
tries=0
while [ $found_master == false ]; do
MASTER_PLUGIN="$(ls $CNI_CONF_DIR | grep -E '\.conf(list)?$' | grep -Ev '00-multus\.conf' | head -1)"
if [ "$MULTUS_MASTER_CNI_FILE_NAME" != "" ]; then
MASTER_PLUGIN="$MULTUS_MASTER_CNI_FILE_NAME"
if [ ! -f "$MULTUS_AUTOCONF_DIR/$MASTER_PLUGIN" ]; then
error "Cannot find master cni file $MULTUS_AUTOCONF_DIR/$MASTER_PLUGIN"
exit 1;
fi
else
MASTER_PLUGIN="$(ls $MULTUS_AUTOCONF_DIR | grep -E '\.conf(list)?$' | grep -Ev '00-multus\.conf' | head -1)"
fi
if [ "$MASTER_PLUGIN" == "" ]; then
if [ $tries -lt 600 ]; then
if ! (($tries % 5)); then
echo "Attemping to find master plugin configuration, attempt $tries"
log "Attempting to find master plugin configuration, attempt $tries"
fi
let "tries+=1"
sleep 1;
else
echo "Error: Multus could not be configured: no master plugin was found."
error "Multus could not be configured: no master plugin was found."
exit 1;
fi
else
log "Using MASTER_PLUGIN: $MASTER_PLUGIN"
found_master=true
@@ -189,6 +321,17 @@ if [ "$MULTUS_CONF_FILE" == "auto" ]; then
ISOLATION_STRING="\"namespaceIsolation\": true,"
fi
GLOBAL_NAMESPACES_STRING=""
if [ ! -z "${MULTUS_GLOBAL_NAMESPACES// }" ]; then
GLOBAL_NAMESPACES_STRING="\"globalNamespaces\": \"$MULTUS_GLOBAL_NAMESPACES\","
fi
LOG_TO_STDERR_STRING=""
if [ "$MULTUS_LOG_TO_STDERR" == false ]; then
LOG_TO_STDERR_STRING="\"logToStderr\": false,"
fi
LOG_LEVEL_STRING=""
if [ ! -z "${MULTUS_LOG_LEVEL// }" ]; then
case "$MULTUS_LOG_LEVEL" in
@@ -201,9 +344,9 @@ if [ "$MULTUS_CONF_FILE" == "auto" ]; then
verbose)
;;
*)
echo "ERROR: Log levels should be one of: debug/verbose/error/panic, did not understand $MULTUS_LOG_LEVEL"
error "Log levels should be one of: debug/verbose/error/panic, did not understand $MULTUS_LOG_LEVEL"
usage
exit 1
exit 1
esac
LOG_LEVEL_STRING="\"logLevel\": \"$MULTUS_LOG_LEVEL\","
fi
@@ -213,30 +356,138 @@ if [ "$MULTUS_CONF_FILE" == "auto" ]; then
LOG_FILE_STRING="\"logFile\": \"$MULTUS_LOG_FILE\","
fi
MASTER_PLUGIN_JSON="$(cat $CNI_CONF_DIR/$MASTER_PLUGIN)"
CNI_VERSION_STRING=""
if [ ! -z "${CNI_VERSION// }" ]; then
CNI_VERSION_STRING="\"cniVersion\": \"$CNI_VERSION\","
fi
ADDITIONAL_BIN_DIR_STRING=""
if [ ! -z "${ADDITIONAL_BIN_DIR// }" ]; then
ADDITIONAL_BIN_DIR_STRING="\"binDir\": \"$ADDITIONAL_BIN_DIR\","
fi
READINESS_INDICATOR_FILE_STRING=""
if [ ! -z "${MULTUS_READINESS_INDICATOR_FILE// }" ]; then
READINESS_INDICATOR_FILE_STRING="\"readinessindicatorfile\": \"$MULTUS_READINESS_INDICATOR_FILE\","
fi
if [ "$OVERRIDE_NETWORK_NAME" == "true" ]; then
MASTER_PLUGIN_NET_NAME="$(cat $MULTUS_AUTOCONF_DIR/$MASTER_PLUGIN | \
python3 -c 'import json,sys;print(json.load(sys.stdin)["name"])')"
else
MASTER_PLUGIN_NET_NAME="multus-cni-network"
fi
capabilities_python_filter_tmpfile=$(mktemp)
cat << EOF > $capabilities_python_filter_tmpfile
import json,sys
conf = json.load(sys.stdin)
capabilities = {}
if 'plugins' in conf:
for capa in [p['capabilities'] for p in conf['plugins'] if 'capabilities' in p]:
capabilities.update({capability:enabled for (capability,enabled) in capa.items() if enabled})
elif 'capabilities' in conf:
capabilities.update({capability:enabled for (capability,enabled) in conf['capabilities'] if enabled})
if len(capabilities) > 0:
print("""\"capabilities\": """ + json.dumps(capabilities) + ",")
else:
print("")
EOF
NESTED_CAPABILITIES_STRING="$(cat $MULTUS_AUTOCONF_DIR/$MASTER_PLUGIN | \
python3 $capabilities_python_filter_tmpfile)"
rm $capabilities_python_filter_tmpfile
log "Nested capabilities string: $NESTED_CAPABILITIES_STRING"
MASTER_PLUGIN_LOCATION=$MULTUS_AUTOCONF_DIR/$MASTER_PLUGIN
if [ "$FORCE_CNI_VERSION" == true ]; then
MASTER_PLUGIN_JSON="$(cat $MASTER_PLUGIN_LOCATION | sed -e "s/\"cniVersion.*/\"cniVersion\": \"$CNI_VERSION\",/g")"
else
MASTER_PLUGIN_JSON="$(cat $MASTER_PLUGIN_LOCATION)"
log "Using $MASTER_PLUGIN_LOCATION as a source to generate the Multus configuration"
CHECK_CNI_VERSION=$(checkCniVersion $MASTER_PLUGIN_LOCATION $CNI_VERSION)
if [ "$CHECK_CNI_VERSION" != "" ] ; then
error "$CHECK_CNI_VERSION"
exit 1
fi
fi
CONF=$(cat <<-EOF
{
"name": "multus-cni-network",
"type": "multus",
{
$CNI_VERSION_STRING
"name": "$MASTER_PLUGIN_NET_NAME",
"type": "multus",
$NESTED_CAPABILITIES_STRING
$ISOLATION_STRING
$GLOBAL_NAMESPACES_STRING
$LOG_TO_STDERR_STRING
$LOG_LEVEL_STRING
$LOG_FILE_STRING
"kubeconfig": "$MULTUS_KUBECONFIG_FILE_HOST",
"delegates": [
$MASTER_PLUGIN_JSON
]
}
$ADDITIONAL_BIN_DIR_STRING
$READINESS_INDICATOR_FILE_STRING
"kubeconfig": "$MULTUS_KUBECONFIG_FILE_HOST",
"delegates": [
$MASTER_PLUGIN_JSON
]
}
EOF
)
echo $CONF > $CNI_CONF_DIR/00-multus.conf
echo "Config file created @ $CNI_CONF_DIR/00-multus.conf"
)
tmpfile=$(mktemp)
echo $CONF > $tmpfile
mv $tmpfile $CNI_CONF_DIR/00-multus.conf
log "Config file created @ $CNI_CONF_DIR/00-multus.conf"
echo $CONF
# If we're not performing the cleanup on exit, we can safely rename the config file.
if [ "$RENAME_SOURCE_CONFIG_FILE" == true ]; then
mv ${MULTUS_AUTOCONF_DIR}/${MASTER_PLUGIN} ${MULTUS_AUTOCONF_DIR}/${MASTER_PLUGIN}.old
log "Original master file moved to ${MULTUS_AUTOCONF_DIR}/${MASTER_PLUGIN}.old"
fi
if [ "$RESTART_CRIO" == true ]; then
# Restart CRIO only once.
if [ "$CRIO_RESTARTED_ONCE" == false ]; then
log "Restarting crio"
systemctl restart crio
CRIO_RESTARTED_ONCE=true
fi
fi
fi
done
fi
}
generateMultusConf
# ---------------------- end Generate "00-multus.conf".
echo "Entering sleep... (success)"
# Enter either sleep loop, or watch loop...
if [ "$MULTUS_CLEANUP_CONFIG_ON_EXIT" == true ]; then
log "Entering watch loop..."
while true; do
# Check and see if the original master plugin configuration exists...
if [ ! -f "$MASTER_PLUGIN_LOCATION" ]; then
log "Master plugin @ $MASTER_PLUGIN_LOCATION has been deleted. Allowing 45 seconds for its restoration..."
sleep 10
for i in {1..35}
do
if [ -f "$MASTER_PLUGIN_LOCATION" ]; then
log "Master plugin @ $MASTER_PLUGIN_LOCATION was restored. Regenerating given configuration."
break
fi
sleep 1
done
# Sleep forever.
sleep infinity
generateMultusConf
log "Continuing watch loop after configuration regeneration..."
fi
sleep 1
done
else
log "Entering sleep (success)..."
if tty -s; then
read
else
sleep infinity
fi
fi

View File

@@ -1,475 +0,0 @@
# This is a modified Flannel daemonset.
# it is based on: https://raw.githubusercontent.com/coreos/flannel/master/Documentation/kube-flannel.yml
# Notably, it removes the creation of an configuration file in/etc/cni/net.d/
---
kind: ClusterRole
apiVersion: rbac.authorization.k8s.io/v1beta1
metadata:
name: flannel
rules:
- apiGroups:
- ""
resources:
- pods
verbs:
- get
- apiGroups:
- ""
resources:
- nodes
verbs:
- list
- watch
- apiGroups:
- ""
resources:
- nodes/status
verbs:
- patch
---
kind: ClusterRoleBinding
apiVersion: rbac.authorization.k8s.io/v1beta1
metadata:
name: flannel
roleRef:
apiGroup: rbac.authorization.k8s.io
kind: ClusterRole
name: flannel
subjects:
- kind: ServiceAccount
name: flannel
namespace: kube-system
---
apiVersion: v1
kind: ServiceAccount
metadata:
name: flannel
namespace: kube-system
---
kind: ConfigMap
apiVersion: v1
metadata:
name: kube-flannel-cfg
namespace: kube-system
labels:
tier: node
app: flannel
data:
# ------------------------------- Intentionally removed, Multus daemonset configures /etc/cni/net.d
#cni-conf.json: |
# {
# "name": "cbr0",
# "plugins": [
# {
# "type": "flannel",
# "delegate": {
# "hairpinMode": true,
# "isDefaultGateway": true
# }
# },
# {
# "type": "portmap",
# "capabilities": {
# "portMappings": true
# }
# }
# ]
# }
net-conf.json: |
{
"Network": "10.244.0.0/16",
"Backend": {
"Type": "vxlan"
}
}
---
apiVersion: extensions/v1beta1
kind: DaemonSet
metadata:
name: kube-flannel-ds-amd64
namespace: kube-system
labels:
tier: node
app: flannel
spec:
template:
metadata:
labels:
tier: node
app: flannel
spec:
hostNetwork: true
nodeSelector:
beta.kubernetes.io/arch: amd64
tolerations:
- operator: Exists
effect: NoSchedule
serviceAccountName: flannel
# ------------------------------- Intentionally removed, Multus daemonset configures /etc/cni/net.d
# initContainers:
# - name: install-cni
# image: quay.io/coreos/flannel:v0.10.0-amd64
# command:
# - cp
# args:
# - -f
# - /etc/kube-flannel/cni-conf.json
# - /etc/cni/net.d/10-flannel.conflist
# volumeMounts:
# - name: cni
# mountPath: /etc/cni/net.d
# - name: flannel-cfg
# mountPath: /etc/kube-flannel/
containers:
- name: kube-flannel
image: quay.io/coreos/flannel:v0.10.0-amd64
command:
- /opt/bin/flanneld
args:
- --ip-masq
- --kube-subnet-mgr
resources:
requests:
cpu: "100m"
memory: "50Mi"
limits:
cpu: "100m"
memory: "50Mi"
securityContext:
privileged: true
env:
- name: POD_NAME
valueFrom:
fieldRef:
fieldPath: metadata.name
- name: POD_NAMESPACE
valueFrom:
fieldRef:
fieldPath: metadata.namespace
volumeMounts:
- name: run
mountPath: /run
- name: flannel-cfg
mountPath: /etc/kube-flannel/
volumes:
- name: run
hostPath:
path: /run
- name: cni
hostPath:
path: /etc/cni/net.d
- name: flannel-cfg
configMap:
name: kube-flannel-cfg
---
apiVersion: extensions/v1beta1
kind: DaemonSet
metadata:
name: kube-flannel-ds-arm64
namespace: kube-system
labels:
tier: node
app: flannel
spec:
template:
metadata:
labels:
tier: node
app: flannel
spec:
hostNetwork: true
nodeSelector:
beta.kubernetes.io/arch: arm64
tolerations:
- operator: Exists
effect: NoSchedule
serviceAccountName: flannel
initContainers:
- name: install-cni
image: quay.io/coreos/flannel:v0.10.0-arm64
command:
- cp
args:
- -f
- /etc/kube-flannel/cni-conf.json
- /etc/cni/net.d/10-flannel.conflist
volumeMounts:
- name: cni
mountPath: /etc/cni/net.d
- name: flannel-cfg
mountPath: /etc/kube-flannel/
containers:
- name: kube-flannel
image: quay.io/coreos/flannel:v0.10.0-arm64
command:
- /opt/bin/flanneld
args:
- --ip-masq
- --kube-subnet-mgr
resources:
requests:
cpu: "100m"
memory: "50Mi"
limits:
cpu: "100m"
memory: "50Mi"
securityContext:
privileged: true
env:
- name: POD_NAME
valueFrom:
fieldRef:
fieldPath: metadata.name
- name: POD_NAMESPACE
valueFrom:
fieldRef:
fieldPath: metadata.namespace
volumeMounts:
- name: run
mountPath: /run
- name: flannel-cfg
mountPath: /etc/kube-flannel/
volumes:
- name: run
hostPath:
path: /run
- name: cni
hostPath:
path: /etc/cni/net.d
- name: flannel-cfg
configMap:
name: kube-flannel-cfg
---
apiVersion: extensions/v1beta1
kind: DaemonSet
metadata:
name: kube-flannel-ds-arm
namespace: kube-system
labels:
tier: node
app: flannel
spec:
template:
metadata:
labels:
tier: node
app: flannel
spec:
hostNetwork: true
nodeSelector:
beta.kubernetes.io/arch: arm
tolerations:
- operator: Exists
effect: NoSchedule
serviceAccountName: flannel
initContainers:
- name: install-cni
image: quay.io/coreos/flannel:v0.10.0-arm
command:
- cp
args:
- -f
- /etc/kube-flannel/cni-conf.json
- /etc/cni/net.d/10-flannel.conflist
volumeMounts:
- name: cni
mountPath: /etc/cni/net.d
- name: flannel-cfg
mountPath: /etc/kube-flannel/
containers:
- name: kube-flannel
image: quay.io/coreos/flannel:v0.10.0-arm
command:
- /opt/bin/flanneld
args:
- --ip-masq
- --kube-subnet-mgr
resources:
requests:
cpu: "100m"
memory: "50Mi"
limits:
cpu: "100m"
memory: "50Mi"
securityContext:
privileged: true
env:
- name: POD_NAME
valueFrom:
fieldRef:
fieldPath: metadata.name
- name: POD_NAMESPACE
valueFrom:
fieldRef:
fieldPath: metadata.namespace
volumeMounts:
- name: run
mountPath: /run
- name: flannel-cfg
mountPath: /etc/kube-flannel/
volumes:
- name: run
hostPath:
path: /run
- name: cni
hostPath:
path: /etc/cni/net.d
- name: flannel-cfg
configMap:
name: kube-flannel-cfg
---
apiVersion: extensions/v1beta1
kind: DaemonSet
metadata:
name: kube-flannel-ds-ppc64le
namespace: kube-system
labels:
tier: node
app: flannel
spec:
template:
metadata:
labels:
tier: node
app: flannel
spec:
hostNetwork: true
nodeSelector:
beta.kubernetes.io/arch: ppc64le
tolerations:
- operator: Exists
effect: NoSchedule
serviceAccountName: flannel
initContainers:
- name: install-cni
image: quay.io/coreos/flannel:v0.10.0-ppc64le
command:
- cp
args:
- -f
- /etc/kube-flannel/cni-conf.json
- /etc/cni/net.d/10-flannel.conflist
volumeMounts:
- name: cni
mountPath: /etc/cni/net.d
- name: flannel-cfg
mountPath: /etc/kube-flannel/
containers:
- name: kube-flannel
image: quay.io/coreos/flannel:v0.10.0-ppc64le
command:
- /opt/bin/flanneld
args:
- --ip-masq
- --kube-subnet-mgr
resources:
requests:
cpu: "100m"
memory: "50Mi"
limits:
cpu: "100m"
memory: "50Mi"
securityContext:
privileged: true
env:
- name: POD_NAME
valueFrom:
fieldRef:
fieldPath: metadata.name
- name: POD_NAMESPACE
valueFrom:
fieldRef:
fieldPath: metadata.namespace
volumeMounts:
- name: run
mountPath: /run
- name: flannel-cfg
mountPath: /etc/kube-flannel/
volumes:
- name: run
hostPath:
path: /run
- name: cni
hostPath:
path: /etc/cni/net.d
- name: flannel-cfg
configMap:
name: kube-flannel-cfg
---
apiVersion: extensions/v1beta1
kind: DaemonSet
metadata:
name: kube-flannel-ds-s390x
namespace: kube-system
labels:
tier: node
app: flannel
spec:
template:
metadata:
labels:
tier: node
app: flannel
spec:
hostNetwork: true
nodeSelector:
beta.kubernetes.io/arch: s390x
tolerations:
- operator: Exists
effect: NoSchedule
serviceAccountName: flannel
initContainers:
- name: install-cni
image: quay.io/coreos/flannel:v0.10.0-s390x
command:
- cp
args:
- -f
- /etc/kube-flannel/cni-conf.json
- /etc/cni/net.d/10-flannel.conflist
volumeMounts:
- name: cni
mountPath: /etc/cni/net.d
- name: flannel-cfg
mountPath: /etc/kube-flannel/
containers:
- name: kube-flannel
image: quay.io/coreos/flannel:v0.10.0-s390x
command:
- /opt/bin/flanneld
args:
- --ip-masq
- --kube-subnet-mgr
resources:
requests:
cpu: "100m"
memory: "50Mi"
limits:
cpu: "100m"
memory: "50Mi"
securityContext:
privileged: true
env:
- name: POD_NAME
valueFrom:
fieldRef:
fieldPath: metadata.name
- name: POD_NAMESPACE
valueFrom:
fieldRef:
fieldPath: metadata.namespace
volumeMounts:
- name: run
mountPath: /run
- name: flannel-cfg
mountPath: /etc/kube-flannel/
volumes:
- name: run
hostPath:
path: /run
- name: cni
hostPath:
path: /etc/cni/net.d
- name: flannel-cfg
configMap:
name: kube-flannel-cfg

Some files were not shown because too many files have changed in this diff Show More