github.com/cilium/cilium@v1.16.2/Documentation/contributing/testing/e2e_legacy.rst (about) 1 .. only:: not (epub or latex or html) 2 3 WARNING: You are looking at unreleased Cilium documentation. 4 Please use the official rendered version released here: 5 https://docs.cilium.io 6 7 .. _testsuite-legacy: 8 9 End-To-End Testing Framework (Legacy) 10 ===================================== 11 12 .. warning:: 13 The Ginkgo end-to-end testing framework is deprecated. New end-to-end 14 tests should be implemented using the `cilium-cli 15 <https://github.com/cilium/cilium-cli/#connectivity-check>`_ connectivity 16 testing framework. For more information, see :ref:`testsuite`. 17 18 Introduction 19 ~~~~~~~~~~~~ 20 21 This section provides an overview of the two modes available for running 22 Cilium's end-to-end tests locally: Vagrant and similar to GitHub Actions (GHA). 23 It offers instructions on setting up and running tests in these modes. 24 25 Before proceeding, it is recommended to familiarize yourself with Ginkgo by 26 reading the `Ginkgo Getting-Started Guide 27 <https://onsi.github.io/ginkgo/#getting-started>`_. You 28 can also run the `example tests 29 <https://github.com/onsi/composition-ginkgo-example>`_ to get a feel for the 30 Ginkgo workflow. 31 32 The tests in the ``test`` directory are built on top of Ginkgo and utilize the 33 Ginkgo ``focus`` concept to determine which virtual machines (VMs), in ``vagrant`` 34 mode are necessary to run specific tests. All test names must begin with one of 35 the following prefixes: 36 37 - ``Runtime``: Tests Cilium in a runtime environment running on a single node. 38 - ``K8s``: Sets up a small multi-node Kubernetes environment for testing features 39 beyond a single host and Kubernetes-specific functionalities. 40 41 42 Running Tests with GitHub Actions (GHA) 43 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ 44 45 GitHub Actions provide an alternative mode for running Cilium's end-to-end tests. 46 The configuration is set up to closely match the environment used in GHA. Refer 47 to the relevant documentation for instructions on running tests using GHA. 48 49 Running Tests with Vagrant 50 ^^^^^^^^^^^^^^^^^^^^^^^^^^ 51 52 To run tests locally using Vagrant, the test scripts invoke ``vagrant`` to create 53 virtual machine(s). These tests utilize the Ginkgo testing framework, leveraging 54 its rich capabilities and the benefits of Go's compilation-time checks and 55 strong typing. 56 57 Running End-To-End Tests 58 ~~~~~~~~~~~~~~~~~~~~~~~~ 59 60 Running Locally Ginkgo Tests based on Ginkgo's GitHub Workflow 61 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ 62 63 Although it is not possible to run ``conformance-ginkgo.yaml`` or 64 ``conformance-runtime.yaml`` locally, it is possible to setup an environment 65 similar to the one used on GitHub. 66 67 The following example will provide the steps to run one of the tests of the 68 focus ``f09-datapath-misc-2`` on Kubernetes ``1.27`` with the kernel ``net-next`` 69 for the commit SHA ``7b368923823e63c9824ea2b5ee4dc026bc4d5cd8``. 70 71 You can also perform these steps automatically using the script 72 ``contrib/scripts/run-gh-ginkgo-workflow.sh``. Run this script with ``-h`` for 73 usage information. 74 75 #. Download dependencies locally (``helm``, ``ginkgo``). 76 77 For ``helm``, the instructions can be found `here <https://helm.sh/docs/intro/install/>`_ 78 79 .. code-block:: shell-session 80 81 $ HELM_VERSION=3.7.0 82 $ wget "https://get.helm.sh/helm-v${HELM_VERSION}-linux-amd64.tar.gz" 83 $ tar -xf "helm-v${HELM_VERSION}-linux-amd64.tar.gz" 84 $ mv linux-amd64/helm ./helm 85 86 Store these dependencies under a specific directory that will be used to run 87 Qemu in the next steps. 88 89 For ``ginkgo``, we will be using the same version used on GitHub action: 90 91 .. code-block:: shell-session 92 93 $ cd ~/ 94 $ go install github.com/onsi/ginkgo/ginkgo@v1.16.5 95 $ ${GOPATH}/bin/ginkgo version 96 Ginkgo Version 1.16.5 97 98 #. Build the Ginkgo tests locally. This will create a binary named ``test.test`` 99 which we can use later on to run our tests. 100 101 .. code-block:: shell-session 102 103 $ cd github.com/cilium/cilium/test 104 $ ${GOPATH}/bin/ginkgo build 105 106 #. Provision VMs using Qemu: 107 108 * Retrieve the image tag for the k8s and kernel versions that will be used for 109 testing by checking the file ``.github/actions/ginkgo/main-k8s-versions.yaml``. 110 111 For example: 112 113 - kernel: ``bpf-next-20230526.105339@sha256:4133d4e09b1e86ac175df8d899873180281bb4220dc43e2566c47b0241637411`` 114 - k8s: ``kindest/node:v1.27.1@sha256:b7d12ed662b873bd8510879c1846e87c7e676a79fefc93e17b2a52989d3ff42b`` 115 116 * Store the compressed VM image under a directory (``/tmp/_images``). 117 118 .. code-block:: shell-session 119 120 $ mkdir -p /tmp/_images 121 $ kernel_tag="bpf-next-20230526.105339@sha256:4133d4e09b1e86ac175df8d899873180281bb4220dc43e2566c47b0241637411" 122 $ docker run -v /tmp/_images:/mnt/images \ 123 "quay.io/lvh-images/kind:${kernel_tag}" \ 124 cp -r /data/images/. /mnt/images/ 125 126 * Uncompress the VM image into a directory. 127 128 .. code-block:: shell-session 129 130 $ zstd -d /tmp/_images/kind_*.qcow2.zst -o /tmp/_images/datapath-conformance.qcow2 131 132 * Provision the VM. **Qemu will use the current terminal to provision the VM 133 and will mount the current directory into the VM under** ``/host``. 134 135 .. code-block:: shell-session 136 137 $ qemu-system-x86_64 \ 138 -nodefaults \ 139 -no-reboot \ 140 -smp 4 \ 141 -m 12G \ 142 -enable-kvm \ 143 -cpu host \ 144 -hda /tmp/_images/datapath-conformance.qcow2 \ 145 -netdev user,id=user.0,hostfwd=tcp::2222-:22 \ 146 -device virtio-net-pci,netdev=user.0 \ 147 -fsdev local,id=host_id,path=./,security_model=none \ 148 -device virtio-9p-pci,fsdev=host_id,mount_tag=host_mount \ 149 -serial mon:stdio 150 151 #. Installing dependencies in the VM (``helm``). 152 153 .. code-block:: shell-session 154 155 $ ssh -p 2222 -o "StrictHostKeyChecking=no" root@localhost 156 # echo "nameserver 8.8.8.8" > /etc/resolv.conf 157 # git config --global --add safe.directory /host 158 # cp /host/helm /usr/bin 159 160 .. _install_kind: 161 162 #. The VM is ready to be used for tests. Similarly to the GitHub Action, Kind 163 will also be used to run the CI. The provisioning of Kind is different 164 depending on the kernel version that is used, i.e., ginkgo tests are meant 165 to run on differently when running on bpf-next. 166 167 .. code-block:: shell-session 168 169 $ ssh -p 2222 -o "StrictHostKeyChecking=no" root@localhost 170 # cd /host/ 171 # kernel_tag="bpf-next-20230526.105339@sha256:4133d4e09b1e86ac175df8d899873180281bb4220dc43e2566c47b0241637411" 172 # kubernetes_image="kindest/node:v1.27.1@sha256:b7d12ed662b873bd8510879c1846e87c7e676a79fefc93e17b2a52989d3ff42b" 173 # ip_family="dual" # replace with "ipv4" if k8s 1.19 174 # 175 # if [[ "${kernel_tag}" == bpf-next-* ]]; then 176 # ./contrib/scripts/kind.sh "" 2 "" "${kubernetes_image}" "none" "${ip_family}" 177 # kubectl label node kind-worker2 cilium.io/ci-node=kind-worker2 178 # # Avoid re-labeling this node by setting "node-role.kubernetes.io/controlplane" 179 # kubectl label node kind-worker2 node-role.kubernetes.io/controlplane= 180 # else 181 # ./contrib/scripts/kind.sh "" 1 "" "${kubernetes_image}" "iptables" "${ip_family}" 182 # fi 183 ## Some tests using demo-customcalls.yaml are mounting this directoy 184 # mkdir -p /home/vagrant/go/src/github.com/cilium 185 # ln -s /host /home/vagrant/go/src/github.com/cilium/cilium 186 # git config --global --add safe.directory /cilium 187 188 Verify that kind is running inside the VM: 189 190 .. code-block:: shell-session 191 192 $ ssh -p 2222 -o "StrictHostKeyChecking=no" root@localhost 193 # kubectl get pods -A 194 NAMESPACE NAME READY STATUS RESTARTS AGE 195 kube-system coredns-787d4945fb-hqzpb 0/1 Pending 0 42s 196 kube-system coredns-787d4945fb-tkq86 0/1 Pending 0 42s 197 kube-system etcd-kind-control-plane 1/1 Running 0 57s 198 kube-system kube-apiserver-kind-control-plane 1/1 Running 0 57s 199 kube-system kube-controller-manager-kind-control-plane 1/1 Running 0 56s 200 kube-system kube-scheduler-kind-control-plane 1/1 Running 0 56s 201 local-path-storage local-path-provisioner-6bd6454576-648bk 0/1 Pending 0 42s 202 203 #. Now that Kind is provisioned, the tests can be executed inside the VM. 204 Let us first retrieve the focus regex, under ``cliFocus``, of 205 ``f09-datapath-misc-2`` from ``.github/actions/ginkgo/main-focus.yaml``. 206 207 * ``cliFocus="K8sDatapathConfig Check|K8sDatapathConfig IPv4Only|K8sDatapathConfig High-scale|K8sDatapathConfig Iptables|K8sDatapathConfig IPv4Only|K8sDatapathConfig IPv6|K8sDatapathConfig Transparent"`` 208 209 Run the binary ``test.test`` that was compiled in the previous step. The 210 following code block is exactly the same as used on the GitHub workflow with 211 one exception: the flag ``-cilium.holdEnvironment=true``. This flag 212 will hold the testing environment in case the test fails to allow for further 213 diagnosis of the current cluster. 214 215 .. code-block:: shell-session 216 217 $ ssh -p 2222 -o "StrictHostKeyChecking=no" root@localhost 218 # cd /host/test 219 # kernel_tag="bpf-next-20230526.105339@sha256:4133d4e09b1e86ac175df8d899873180281bb4220dc43e2566c47b0241637411" 220 # k8s_version="1.27" 221 # 222 # export K8S_NODES=2 223 # export NETNEXT=0 224 # export K8S_VERSION="${k8s_version}" 225 # export CNI_INTEGRATION=kind 226 # export INTEGRATION_TESTS=true 227 # 228 # if [[ "${kernel_tag}" == bpf-next-* ]]; then 229 # export KERNEL=net-next 230 # export NETNEXT=1 231 # export KUBEPROXY=0 232 # export K8S_NODES=3 233 # export NO_CILIUM_ON_NODES=kind-worker2 234 # elif [[ "${kernel_tag}" == 5.4-* ]]; then 235 # export KERNEL=54 236 # fi 237 # 238 # # GitHub actions do not support IPv6 connectivity to outside 239 # # world. If the infrastructure environment supports it, then 240 # # this line can be removed 241 # export CILIUM_NO_IPV6_OUTSIDE=true 242 # 243 # commit_sha="7b368923823e63c9824ea2b5ee4dc026bc4d5cd8" 244 # cliFocus="K8sDatapathConfig Check|K8sDatapathConfig IPv4Only|K8sDatapathConfig High-scale|K8sDatapathConfig Iptables|K8sDatapathConfig IPv4Only|K8sDatapathConfig IPv6|K8sDatapathConfig Transparent" 245 # quay_org="cilium" 246 # 247 # ./test.test \ 248 --ginkgo.focus="${cliFocus}" \ 249 --ginkgo.skip="" \ 250 --ginkgo.seed=1679952881 \ 251 --ginkgo.v -- \ 252 -cilium.provision=false \ 253 -cilium.image=quay.io/${quay_org}/cilium-ci \ 254 -cilium.tag=${commit_sha} \ 255 -cilium.operator-image=quay.io/${quay_org}/operator \ 256 -cilium.operator-tag=${commit_sha} \ 257 -cilium.hubble-relay-image=quay.io/${quay_org}/hubble-relay-ci \ 258 -cilium.hubble-relay-tag=${commit_sha} \ 259 -cilium.kubeconfig=/root/.kube/config \ 260 -cilium.provision-k8s=false \ 261 -cilium.operator-suffix=-ci \ 262 -cilium.holdEnvironment=true 263 Using CNI_INTEGRATION="kind" 264 Running Suite: Suite-k8s-1.27 265 ============================= 266 Random Seed: 1679952881 267 Will run 7 of 132 specs 268 269 #. Wait until the test execution completes. 270 271 .. code-block:: shell-session 272 273 Ran 7 of 132 Specs in 721.007 seconds 274 SUCCESS! -- 7 Passed | 0 Failed | 0 Pending | 125 Skipped 275 276 #. Clean up. 277 278 Once tests are performed, terminate qemu to halt the VM: 279 280 .. code-block:: shell-session 281 282 $ pkill qemu-system-x86 283 284 The VM state is kept in ``/tmp/_images/datapath-conformance.qcow2`` and the 285 dependencies are installed. Thus steps up to and excluding step 286 :ref:`installing kind <install_kind>` can be skipped next time and the VM 287 state can be re-used from step :ref:`installing kind <install_kind>` onwards. 288 289 Running All Ginkgo Tests 290 ^^^^^^^^^^^^^^^^^^^^^^^^ 291 292 Running all of the Ginkgo tests may take an hour or longer. To run all the 293 ginkgo tests, invoke the make command as follows from the root of the cilium 294 repository: 295 296 .. code-block:: shell-session 297 298 $ sudo make -C test/ test 299 300 The first time that this is invoked, the testsuite will pull the 301 `testing VMs <https://app.vagrantup.com/cilium/boxes/ginkgo>`_ and provision 302 Cilium into them. This may take several minutes, depending on your internet 303 connection speed. Subsequent runs of the test will reuse the image. 304 305 Running Runtime Tests 306 ^^^^^^^^^^^^^^^^^^^^^ 307 308 To run all of the runtime tests, execute the following command from the ``test`` directory: 309 310 .. code-block:: shell-session 311 312 INTEGRATION_TESTS=true ginkgo --focus="Runtime" 313 314 Ginkgo searches for all tests in all subdirectories that are "named" beginning 315 with the string "Runtime" and contain any characters after it. For instance, 316 here is an example showing what tests will be ran using Ginkgo's dryRun option: 317 318 .. code-block:: shell-session 319 320 $ INTEGRATION_TESTS=true ginkgo --focus="Runtime" -dryRun 321 Running Suite: runtime 322 ====================== 323 Random Seed: 1516125117 324 Will run 42 of 164 specs 325 ................ 326 RuntimePolicyEnforcement Policy Enforcement Always 327 Always to Never with policy 328 /Users/ianvernon/go/src/github.com/cilium/cilium/test/runtime/Policies.go:258 329 • 330 ------------------------------ 331 RuntimePolicyEnforcement Policy Enforcement Always 332 Always to Never without policy 333 /Users/ianvernon/go/src/github.com/cilium/cilium/test/runtime/Policies.go:293 334 • 335 ------------------------------ 336 RuntimePolicyEnforcement Policy Enforcement Never 337 Container creation 338 /Users/ianvernon/go/src/github.com/cilium/cilium/test/runtime/Policies.go:332 339 • 340 ------------------------------ 341 RuntimePolicyEnforcement Policy Enforcement Never 342 Never to default with policy 343 /Users/ianvernon/go/src/github.com/cilium/cilium/test/runtime/Policies.go:349 344 ................. 345 Ran 42 of 164 Specs in 0.002 seconds 346 SUCCESS! -- 0 Passed | 0 Failed | 0 Pending | 122 Skipped PASS 347 348 Ginkgo ran 1 suite in 1.830262168s 349 Test Suite Passed 350 351 The output has been truncated. For more information about this functionality, 352 consult the aforementioned Ginkgo documentation. 353 354 .. _running_k8s_tests: 355 356 Running Kubernetes Tests 357 ^^^^^^^^^^^^^^^^^^^^^^^^ 358 359 To run all of the Kubernetes tests, run the following command from the ``test`` directory: 360 361 .. code-block:: shell-session 362 363 INTEGRATION_TESTS=true ginkgo --focus="K8s" 364 365 To run a specific test from the Kubernetes tests suite, run the following command 366 from the ``test`` directory: 367 368 .. code-block:: shell-session 369 370 INTEGRATION_TESTS=true ginkgo --focus="K8s.*Check iptables masquerading with random-fully" 371 372 Similar to the Runtime test suite, Ginkgo searches for all tests in all 373 subdirectories that are "named" beginning with the string "K8s" and 374 contain any characters after it. 375 376 The Kubernetes tests support the following Kubernetes versions: 377 378 * 1.19 379 * 1.20 380 * 1.21 381 * 1.22 382 * 1.23 383 * 1.24 384 * 1.25 385 * 1.26 386 * 1.27 387 * 1.28 388 389 By default, the Vagrant VMs are provisioned with Kubernetes 1.23. To run with any other 390 supported version of Kubernetes, run the test suite with the following format: 391 392 .. code-block:: shell-session 393 394 INTEGRATION_TESTS=true K8S_VERSION=<version> ginkgo --focus="K8s" 395 396 .. note:: 397 398 When provisioning VMs with the net-next kernel (``NETNEXT=1``) on 399 VirtualBox which version does not match a version of the VM image 400 VirtualBox Guest Additions, Vagrant will install a new version of 401 the Additions with ``mount.vboxsf``. The latter is not compatible with 402 ``vboxsf.ko`` shipped within the VM image, and thus syncing of shared 403 folders will not work. 404 405 To avoid this, one can prevent Vagrant from installing the Additions by 406 putting the following into ``$HOME/.vagrant.d/Vagrantfile``: 407 408 .. code-block:: ruby 409 410 Vagrant.configure('2') do |config| 411 if Vagrant.has_plugin?("vagrant-vbguest") then 412 config.vbguest.auto_update = false 413 end 414 415 config.vm.provider :virtualbox do |vbox| 416 vbox.check_guest_additions = false 417 end 418 end 419 420 Available CLI Options 421 ^^^^^^^^^^^^^^^^^^^^^ 422 423 For more advanced workflows, check the list of available custom options for the Cilium 424 framework in the ``test/`` directory and interact with ginkgo directly: 425 426 .. code-block:: shell-session 427 428 $ cd test/ 429 $ ginkgo . -- -cilium.help 430 -cilium.SSHConfig string 431 Specify a custom command to fetch SSH configuration (eg: 'vagrant ssh-config') 432 -cilium.help 433 Display this help message. 434 -cilium.holdEnvironment 435 On failure, hold the environment in its current state 436 -cilium.hubble-relay-image string 437 Specifies which image of hubble-relay to use during tests 438 -cilium.hubble-relay-tag string 439 Specifies which tag of hubble-relay to use during tests 440 -cilium.image string 441 Specifies which image of cilium to use during tests 442 -cilium.kubeconfig string 443 Kubeconfig to be used for k8s tests 444 -cilium.multinode 445 Enable tests across multiple nodes. If disabled, such tests may silently pass (default true) 446 -cilium.operator-image string 447 Specifies which image of cilium-operator to use during tests 448 -cilium.operator-tag string 449 Specifies which tag of cilium-operator to use during tests 450 -cilium.passCLIEnvironment 451 Pass the environment invoking ginkgo, including PATH, to subcommands 452 -cilium.provision 453 Provision Vagrant boxes and Cilium before running test (default true) 454 -cilium.provision-k8s 455 Specifies whether Kubernetes should be deployed and installed via kubeadm or not (default true) 456 -cilium.runQuarantined 457 Run tests that are under quarantine. 458 -cilium.showCommands 459 Output which commands are ran to stdout 460 -cilium.skipLogs 461 skip gathering logs if a test fails 462 -cilium.tag string 463 Specifies which tag of cilium to use during tests 464 -cilium.testScope string 465 Specifies scope of test to be ran (k8s, runtime) 466 -cilium.timeout duration 467 Specifies timeout for test run (default 24h0m0s) 468 469 Ginkgo ran 1 suite in 4.312100241s 470 Test Suite Failed 471 472 For more information about other built-in options to Ginkgo, consult the 473 `ginkgo-documentation`_. 474 475 .. _ginkgo-documentation: 476 477 Running Specific Tests Within a Test Suite 478 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ 479 480 If you want to run one specified test, there are a few options: 481 482 * By modifying code: add the prefix "FIt" on the test you want to run; this 483 marks the test as focused. Ginkgo will skip other tests and will only run the 484 "focused" test. For more information, consult the `Focused Specs`_ 485 documentation from Ginkgo. 486 487 .. code-block:: go 488 489 It("Example test", func(){ 490 Expect(true).Should(BeTrue()) 491 }) 492 493 FIt("Example focused test", func(){ 494 Expect(true).Should(BeTrue()) 495 }) 496 497 498 * From the command line: specify a more granular focus if you want to focus on, say, Runtime L7 tests: 499 500 .. code-block:: shell-session 501 502 INTEGRATION_TESTS=true ginkgo --focus "Runtime.*L7" 503 504 505 This will focus on tests that contain "Runtime", followed by any 506 number of any characters, followed by "L7". ``--focus`` is a regular 507 expression and quotes are required if it contains spaces and to escape 508 shell expansion of ``*``. 509 510 .. _Focused Specs: https://onsi.github.io/ginkgo/#focused-specs 511 512 Compiling the tests without running them 513 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ 514 515 To validate that the Go code you've written for testing is correct without 516 needing to run the full test, you can build the test directory: 517 518 .. code-block:: shell-session 519 520 make -C test/ build 521 522 Updating Cilium images for Kubernetes tests 523 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ 524 525 Sometimes when running the CI suite for a feature under development, it's common 526 to re-run the CI suite on the CI VMs running on a local development machine after 527 applying some changes to Cilium. For this the new Cilium images have to be 528 built, and then used by the CI suite. To do so, one can run the following 529 commands on the ``k8s1`` VM: 530 531 .. code-block:: shell-session 532 533 cd go/src/github.com/cilium/cilium 534 535 make LOCKDEBUG=1 docker-cilium-image 536 docker tag quay.io/cilium/cilium:latest \ 537 k8s1:5000/cilium/cilium-dev:latest 538 docker push k8s1:5000/cilium/cilium-dev:latest 539 540 make -B LOCKDEBUG=1 docker-operator-generic-image 541 docker tag quay.io/cilium/operator-generic:latest \ 542 k8s1:5000/cilium/operator-generic:latest 543 docker push k8s1:5000/cilium/operator-generic:latest 544 545 The commands were adapted from the ``test/provision/compile.sh`` script. 546 547 Test Reports 548 ~~~~~~~~~~~~ 549 550 The Cilium Ginkgo framework formulates JUnit reports for each test. The 551 following files currently are generated depending upon the test suite that is ran: 552 553 * runtime.xml 554 * K8s.xml 555 556 Best Practices for Writing Tests 557 ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ 558 559 * Provide informative output to console during a test using the `By construct <https://onsi.github.io/ginkgo/#documenting-complex-specs-by>`_. This helps with debugging and gives those who did not write the test a good idea of what is going on. The lower the barrier of entry is for understanding tests, the better our tests will be! 560 * Leave the testing environment in the same state that it was in when the test started by deleting resources, resetting configuration, etc. 561 * Gather logs in the case that a test fails. If a test fails while running on Jenkins, a postmortem needs to be done to analyze why. So, dumping logs to a location where Jenkins can pick them up is of the highest imperative. Use the following code in an ``AfterFailed`` method: 562 563 .. code-block:: go 564 565 AfterFailed(func() { 566 vm.ReportFailed() 567 }) 568 569 570 Ginkgo Extensions 571 ~~~~~~~~~~~~~~~~~ 572 573 In Cilium, some Ginkgo features are extended to cover some uses cases that are 574 useful for testing Cilium. 575 576 BeforeAll 577 ^^^^^^^^^ 578 579 This function will run before all `BeforeEach`_ within a `Describe or Context`_. 580 This method is an equivalent to ``SetUp`` or initialize functions in common 581 unit test frameworks. 582 583 .. _BeforeEach: https://onsi.github.io/ginkgo/#extracting-common-setup-beforeeach 584 .. _Describe or Context: https://onsi.github.io/ginkgo/#organizing-specs-with-container-nodes 585 586 AfterAll 587 ^^^^^^^^ 588 589 This method will run after all `AfterEach`_ functions defined in a `Describe or Context`_. 590 This method is used for tearing down objects created which are used by all 591 ``Its`` within the given ``Context`` or ``Describe``. It is ran after all Its 592 have ran, this method is a equivalent to ``tearDown`` or ``finalize`` methods in 593 common unit test frameworks. 594 595 A good use case for using ``AfterAll`` method is to remove containers or pods 596 that are needed for multiple ``Its`` in the given ``Context`` or ``Describe``. 597 598 .. _AfterEach: BeforeEach_ 599 600 JustAfterEach 601 ^^^^^^^^^^^^^ 602 603 This method will run just after each test and before ``AfterFailed`` and 604 ``AfterEach``. The main reason of this method is to perform some assertions 605 for a group of tests. A good example of using a global ``JustAfterEach`` 606 function is for deadlock detection, which checks the Cilium logs for deadlocks 607 that may have occurred in the duration of the tests. 608 609 AfterFailed 610 ^^^^^^^^^^^ 611 612 This method will run before all ``AfterEach`` and after ``JustAfterEach``. This 613 function is only called when the test failed.This construct is used to gather 614 logs, the status of Cilium, etc, which provide data for analysis when tests 615 fail. 616 617 Example Test Layout 618 ^^^^^^^^^^^^^^^^^^^ 619 620 Here is an example layout of how a test may be written with the aforementioned 621 constructs: 622 623 Test description diagram:: 624 625 Describe 626 BeforeAll(A) 627 AfterAll(A) 628 AfterFailed(A) 629 AfterEach(A) 630 JustAfterEach(A) 631 TESTA1 632 TESTA2 633 TESTA3 634 Context 635 BeforeAll(B) 636 AfterAll(B) 637 AfterFailed(B) 638 AfterEach(B) 639 JustAfterEach(B) 640 TESTB1 641 TESTB2 642 TESTB3 643 644 645 Test execution flow:: 646 647 Describe 648 BeforeAll 649 TESTA1; JustAfterEach(A), AfterFailed(A), AfterEach(A) 650 TESTA2; JustAfterEach(A), AfterFailed(A), AfterEach(A) 651 TESTA3; JustAfterEach(A), AfterFailed(A), AfterEach(A) 652 Context 653 BeforeAll(B) 654 TESTB1: 655 JustAfterEach(B); JustAfterEach(A) 656 AfterFailed(B); AfterFailed(A); 657 AfterEach(B) ; AfterEach(A); 658 TESTB2: 659 JustAfterEach(B); JustAfterEach(A) 660 AfterFailed(B); AfterFailed(A); 661 AfterEach(B) ; AfterEach(A); 662 TESTB3: 663 JustAfterEach(B); JustAfterEach(A) 664 AfterFailed(B); AfterFailed(A); 665 AfterEach(B) ; AfterEach(A); 666 AfterAll(B) 667 AfterAll(A) 668 669 Debugging: 670 ~~~~~~~~~~ 671 672 You can retrieve all run commands and their output in the report directory 673 (``./test/test_results``). Each test creates a new folder, which contains 674 a file called log where all information is saved, in case of a failing 675 test an exhaustive data will be added. 676 677 .. code-block:: shell-session 678 679 $ head test/test_results/RuntimeKafkaKafkaPolicyIngress/logs 680 level=info msg=Starting testName=RuntimeKafka 681 level=info msg="Vagrant: running command \"vagrant ssh-config runtime\"" 682 cmd: "sudo cilium-dbg status" exitCode: 0 683 KVStore: Ok Consul: 172.17.0.3:8300 684 ContainerRuntime: Ok 685 Kubernetes: Disabled 686 Kubernetes APIs: [""] 687 Cilium: Ok OK 688 NodeMonitor: Disabled 689 Allocated IPv4 addresses: 690 691 692 Running with delve 693 ^^^^^^^^^^^^^^^^^^ 694 695 `Delve <https://github.com/derekparker/delve>`_ is a debugging tool for Go 696 applications. If you want to run your test with delve, you should add a new 697 breakpoint using 698 `runtime.BreakPoint() <https://golang.org/pkg/runtime/#Breakpoint>`_ in the 699 code, and run ginkgo using ``dlv``. 700 701 Example how to run ginkgo using ``dlv``: 702 703 .. code-block:: shell-session 704 705 dlv test . -- --ginkgo.focus="Runtime" -ginkgo.v=true --cilium.provision=false 706 707 Running End-To-End Tests In Other Environments via kubeconfig 708 ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ 709 710 The end-to-end tests can be run with an arbitrary kubeconfig file. Normally the 711 CI will use the kubernetes created via vagrant but this can be overridden with 712 ``--cilium.kubeconfig``. When used, ginkgo will not start a VM nor compile 713 cilium. It will also skip some setup tasks like labeling nodes for testing. 714 715 This mode expects: 716 717 - The current directory is ``cilium/test`` 718 719 - A test focus with ``--focus``. ``--focus="K8s"`` selects all kubernetes tests. 720 If not passing ``--focus=K8s`` then you must pass ``-cilium.testScope=K8s``. 721 722 - Cilium images as full URLs specified with the ``--cilium.image`` and 723 ``--cilium.operator-image`` options. 724 725 - A working kubeconfig with the ``--cilium.kubeconfig`` option 726 727 - A populated K8S_VERSION environment variable set to the version of the cluster 728 729 - If appropriate, set the ``CNI_INTEGRATION`` environment variable set to one 730 of ``gke``, ``eks``, ``eks-chaining``, ``microk8s`` or ``minikube``. This selects 731 matching configuration overrides for cilium. 732 Leaving this unset for non-matching integrations is also correct. 733 734 For k8s environments that invoke an authentication agent, such as EKS and 735 ``aws-iam-authenticator``, set ``--cilium.passCLIEnvironment=true`` 736 737 An example invocation is 738 739 .. code-block:: shell-session 740 741 INTEGRATION_TESTS=true CNI_INTEGRATION=eks K8S_VERSION=1.16 ginkgo --focus="K8s" -- -cilium.provision=false -cilium.kubeconfig=`echo ~/.kube/config` -cilium.image="quay.io/cilium/cilium-ci" -cilium.operator-image="quay.io/cilium/operator" -cilium.operator-suffix="-ci" -cilium.passCLIEnvironment=true 742 743 744 To run tests with Kind, try 745 746 .. code-block:: shell-session 747 748 K8S_VERSION=1.25 ginkgo --focus=K8s -- -cilium.provision=false --cilium.image=localhost:5000/cilium/cilium-dev -cilium.tag=local --cilium.operator-image=localhost:5000/cilium/operator -cilium.operator-tag=local -cilium.kubeconfig=`echo ~/.kube/config` -cilium.provision-k8s=false -cilium.testScope=K8s -cilium.operator-suffix= 749 750 751 Running in GKE 752 ^^^^^^^^^^^^^^ 753 754 1- Setup a cluster as in :ref:`k8s_install_quick` or utilize an existing 755 cluster. 756 757 .. note:: You do not need to deploy Cilium in this step, as the End-To-End 758 Testing Framework handles the deployment of Cilium. 759 760 .. note:: The tests require machines larger than ``n1-standard-4``. This can be 761 set with ``--machine-type n1-standard-4`` on cluster creation. 762 763 764 2- Invoke the tests from ``cilium/test`` with options set as explained in 765 `Running End-To-End Tests In Other Environments via kubeconfig`_ 766 767 .. note:: The tests require the ``NATIVE_CIDR`` environment variable to be set to 768 the value of the cluster IPv4 CIDR returned by the ``gcloud container 769 clusters describe`` command. 770 771 .. code-block:: shell-session 772 773 export CLUSTER_NAME=cluster1 774 export CLUSTER_ZONE=us-west2-a 775 export NATIVE_CIDR="$(gcloud container clusters describe $CLUSTER_NAME --zone $CLUSTER_ZONE --format 'value(clusterIpv4Cidr)')" 776 777 INTEGRATION_TESTS=true CNI_INTEGRATION=gke K8S_VERSION=1.17 ginkgo --focus="K8sDemo" -- -cilium.provision=false -cilium.kubeconfig=`echo ~/.kube/config` -cilium.image="quay.io/cilium/cilium-ci" -cilium.operator-image="quay.io/cilium/operator" -cilium.operator-suffix="-ci" -cilium.hubble-relay-image="quay.io/cilium/hubble-relay-ci" -cilium.passCLIEnvironment=true 778 779 .. note:: The kubernetes version defaults to 1.23 but can be configured with 780 versions between 1.16 and 1.23. Version should match the server 781 version reported by ``kubectl version``. 782 783 AKS (experimental) 784 ^^^^^^^^^^^^^^^^^^ 785 786 .. note:: The tests require the ``NATIVE_CIDR`` environment variable to be set to 787 the value of the cluster IPv4 CIDR. 788 789 1. Setup a cluster as in :ref:`k8s_install_quick` or utilize an existing 790 cluster. You do not need to deploy Cilium in this step, as the End-To-End 791 Testing Framework handles the deployment of Cilium. 792 793 2. Invoke the tests from ``cilium/test`` with options set as explained in 794 `Running End-To-End Tests In Other Environments via kubeconfig`_ 795 796 .. code-block:: shell-session 797 798 export NATIVE_CIDR="10.241.0.0/16" 799 INTEGRATION_TESTS=true CNI_INTEGRATION=aks K8S_VERSION=1.17 ginkgo --focus="K8s" -- -cilium.provision=false -cilium.kubeconfig=`echo ~/.kube/config` -cilium.passCLIEnvironment=true -cilium.image="mcr.microsoft.com/oss/cilium/cilium" -cilium.tag="1.12.1" -cilium.operator-image="mcr.microsoft.com/oss/cilium/operator" -cilium.operator-suffix="" -cilium.operator-tag="1.12.1" 800 801 AWS EKS (experimental) 802 ^^^^^^^^^^^^^^^^^^^^^^ 803 804 Not all tests can succeed on EKS. Many do, however and may be useful. 805 :gh-issue:`9678#issuecomment-749350425` contains a list of tests that are still 806 failing. 807 808 1. Setup a cluster as in :ref:`k8s_install_quick` or utilize an existing 809 cluster. 810 811 2. Source the testing integration script from ``cilium/contrib/testing/integrations.sh``. 812 813 3. Invoke the ``gks`` function by passing which ``cilium`` docker image to run 814 and the test focus. The command also accepts additional ginkgo arguments. 815 816 .. code-block:: shell-session 817 818 gks quay.io/cilium/cilium:latest K8sDemo 819 820 821 Adding new Managed Kubernetes providers 822 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ 823 824 All Managed Kubernetes test support relies on using a pre-configured kubeconfig 825 file. This isn't always adequate, however, and adding defaults specific to 826 each provider is possible. The `commit adding GKE <https://github.com/cilium/cilium/commit/c2d8445fd725c515a635c8c3ad3be901a08084eb>`_ 827 support is a good reference. 828 829 1. Add a map of helm settings to act as an override for this provider in 830 `test/helpers/kubectl.go <https://github.com/cilium/cilium/blob/26dec4c4f4311df2b1a6c909b27ff7fe6e46929f/test/helpers/kubectl.go#L80-L102>`_. 831 These should be the helm settings used when generating cilium specs for this 832 provider. 833 834 2. Add a unique `CI Integration constant <https://github.com/cilium/cilium/blob/26dec4c4f4311df2b1a6c909b27ff7fe6e46929f/test/helpers/kubectl.go#L66-L67>`_. 835 This value is passed in when invoking ginkgo via the ``CNI_INTEGRATON`` 836 environment variable. 837 838 3. Update the `helm overrides <https://github.com/cilium/cilium/blob/26dec4c4f4311df2b1a6c909b27ff7fe6e46929f/test/helpers/kubectl.go#L138-L147>`_ 839 mapping with the constant and the helm settings. 840 841 4. For cases where a test should be skipped use the ``SkipIfIntegration``. To 842 skip whole contexts, use ``SkipContextIf``. More complex logic can be 843 expressed with functions like ``IsIntegration``. These functions are all 844 part of the `test/helpers <https://github.com/cilium/cilium/tree/26dec4c4f4311df2b1a6c909b27ff7fe6e46929f/test/helpers>`_ 845 package. 846 847 Running End-To-End Tests In Other Environments via SSH 848 ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ 849 850 If you want to run tests in an arbitrary environment with SSH access, you can 851 use ``--cilium.SSHConfig`` to provide the SSH configuration of the endpoint on 852 which tests will be run. The tests presume the following on the remote 853 instance: 854 855 - Cilium source code is located in the directory ``/home/vagrant/go/src/github.com/cilium/cilium/``. 856 - Cilium is installed and running. 857 858 The ssh connection needs to be defined as a ``ssh-config`` file and need to have 859 the following targets: 860 861 - runtime: To run runtime tests 862 - k8s{1..2}-${K8S_VERSION}: to run Kubernetes tests. These instances must have 863 Kubernetes installed and running as a prerequisite for running tests. 864 865 An example ``ssh-config`` can be the following: 866 867 :: 868 869 Host runtime 870 HostName 127.0.0.1 871 User vagrant 872 Port 2222 873 UserKnownHostsFile /dev/null 874 StrictHostKeyChecking no 875 PasswordAuthentication no 876 IdentityFile /home/eloy/.go/src/github.com/cilium/cilium/test/.vagrant/machines/runtime/virtualbox/private_key 877 IdentitiesOnly yes 878 LogLevel FATAL 879 880 To run this you can use the following command: 881 882 .. code-block:: shell-session 883 884 ginkgo -- --cilium.provision=false --cilium.SSHConfig="cat ssh-config" 885 886 887 VMs for Testing 888 ~~~~~~~~~~~~~~~ 889 890 The VMs used for testing are defined in ``test/Vagrantfile``. There are a variety of 891 configuration options that can be passed as environment variables: 892 893 +----------------------+-------------------+--------------+------------------------------------------------------------------+ 894 | ENV variable | Default Value | Options | Description | 895 +======================+===================+==============+==================================================================+ 896 | K8S\_NODES | 2 | 0..100 | Number of Kubernetes nodes in the cluster | 897 +----------------------+-------------------+--------------+------------------------------------------------------------------+ 898 | NO_CILIUM_ON_NODE[S] | none | \* | Comma-separated list of K8s nodes that should not run Cilium | 899 +----------------------+-------------------+--------------+------------------------------------------------------------------+ 900 | NFS | 0 | 1 | If Cilium folder needs to be shared using NFS | 901 +----------------------+-------------------+--------------+------------------------------------------------------------------+ 902 | IPv6 | 0 | 0-1 | If 1 the Kubernetes cluster will use IPv6 | 903 +----------------------+-------------------+--------------+------------------------------------------------------------------+ 904 | CONTAINER\_RUNTIME | docker | containerd | To set the default container runtime in the Kubernetes cluster | 905 +----------------------+-------------------+--------------+------------------------------------------------------------------+ 906 | K8S\_VERSION | 1.18 | 1.\*\* | Kubernetes version to install | 907 +----------------------+-------------------+--------------+------------------------------------------------------------------+ 908 | KUBEPROXY | 1 | 0-1 | If 0 the Kubernetes' kube-proxy won't be installed | 909 +----------------------+-------------------+--------------+------------------------------------------------------------------+ 910 | SERVER\_BOX | cilium/ubuntu-dev | \* | Vagrantcloud base image | 911 +----------------------+-------------------+--------------+------------------------------------------------------------------+ 912 | VM\_CPUS | 2 | 0..100 | Number of CPUs that need to have the VM | 913 +----------------------+-------------------+--------------+------------------------------------------------------------------+ 914 | VM\_MEMORY | 4096 | \d+ | RAM size in Megabytes | 915 +----------------------+-------------------+--------------+------------------------------------------------------------------+ 916 917 VM images 918 ~~~~~~~~~ 919 920 The test suite relies on Vagrant to automatically download the required VM 921 image, if it is not already available on the system. VM images weight several 922 gigabytes so this may take some time, but faster tools such as `aria2`_ can 923 speed up the process by opening multiple connections. The script 924 `contrib/scripts/add_vagrant_box.sh`_ can be useful to manually download 925 selected images with aria2 prior to launching the test suite, or to 926 periodically update images in a ``cron`` job:: 927 928 $ bash contrib/scripts/add_vagrant_box.sh -h 929 usage: add_vagrant_box.sh [options] [vagrant_box_defaults.rb path] 930 path to vagrant_box_defaults.rb defaults to ./vagrant_box_defaults.rb 931 932 options: 933 -a use aria2c instead of curl 934 -b <box> download selected box (defaults: ubuntu ubuntu-next) 935 -d <dir> download to dir instead of /tmp/ 936 -l download latest versions instead of using vagrant_box_defaults 937 -h display this help 938 939 examples: 940 download boxes ubuntu and ubuntu-next from vagrant_box_defaults.rb: 941 $ add-vagrant-boxes.sh $HOME/go/src/github.com/cilium/cilium/vagrant_box_defaults.rb 942 download latest version for ubuntu-dev and ubuntu-next: 943 $ add-vagrant-boxes.sh -l -b ubuntu-dev -b ubuntu-next 944 same as above, downloading into /tmp/foo and using aria2c: 945 $ add-vagrant-boxes.sh -al -d /tmp/foo -b ubuntu-dev -b ubuntu-next 946 947 .. _aria2: https://aria2.github.io/ 948 .. _contrib/scripts/add_vagrant_box.sh: 949 https://github.com/cilium/cilium/blob/main/contrib/scripts/add_vagrant_box.sh 950 951 Known Issues and Workarounds 952 ~~~~~~~~~~~~~~~~~~~~~~~~~~~~ 953 954 VirtualBox hostonlyifs and DHCP related errors 955 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ 956 957 If you see the following error, take a look at this `GitHub issue 958 <https://github.com/hashicorp/vagrant/issues/3083#issuecomment-41156076>`_ for 959 workarounds. 960 961 :: 962 963 A host only network interface you're attempting to configure via DHCP 964 already has a conflicting host only adapter with DHCP enabled. The 965 DHCP on this adapter is incompatible with the DHCP settings. Two 966 host only network interfaces are not allowed to overlap, and each 967 host only network interface can have only one DHCP server. Please 968 reconfigure your host only network or remove the virtual machine 969 using the other host only network. 970 971 Also, consider upgrading VirtualBox and Vagrant to the latest versions. 972 973 Further Assistance 974 ~~~~~~~~~~~~~~~~~~ 975 976 Have a question about how the tests work or want to chat more about improving the 977 testing infrastructure for Cilium? Hop on over to the ``#testing`` channel on 978 `Cilium Slack`_.