From aa56022e0fba3c358e46e8671d9a0cd36094ebaa Mon Sep 17 00:00:00 2001 From: Victor Morales Date: Tue, 27 Nov 2018 05:13:11 -0800 Subject: Integrate OVN4NFV plugin This change includes the files to install, configure and test the OVN4NFV plugin. Change-Id: I0c431e475bd391e13680c734cff555e4dfc055ae Signed-off-by: Victor Morales Issue-ID: MULTICLOUD-304 --- vagrant/Vagrantfile | 3 +- vagrant/insecure_keys/key.pub | 1 + vagrant/installer.sh | 3 +- vagrant/playbooks/configure-ovn4nfv.yml | 98 ++++++++++++++++++ vagrant/playbooks/krd-vars.yml | 6 ++ vagrant/tests/_common.sh | 171 ++++++++++++++++++++++++-------- vagrant/tests/_functions.sh | 60 +++++++++++ vagrant/tests/integration_vcFW.sh | 11 +- vagrant/tests/ovn4nfv.sh | 46 +++++++++ 9 files changed, 357 insertions(+), 42 deletions(-) create mode 100644 vagrant/insecure_keys/key.pub create mode 100644 vagrant/playbooks/configure-ovn4nfv.yml create mode 100755 vagrant/tests/ovn4nfv.sh (limited to 'vagrant') diff --git a/vagrant/Vagrantfile b/vagrant/Vagrantfile index 1b84cb4b..3314fe94 100644 --- a/vagrant/Vagrantfile +++ b/vagrant/Vagrantfile @@ -23,7 +23,7 @@ nodes = YAML.load_file(pdf) # Inventory file creation File.open(File.dirname(__FILE__) + "/inventory/hosts.ini", "w") do |inventory_file| - inventory_file.puts("[all:vars]\nansible_connection=ssh\nansible_ssh_user=vagrant\n[all]") + inventory_file.puts("[all]") nodes.each do |node| inventory_file.puts("#{node['name']}\tansible_ssh_host=#{node['ip']} ansible_ssh_port=22") end @@ -119,6 +119,7 @@ Vagrant.configure("2") do |config| installer.vm.provision 'shell', privileged: false do |sh| sh.env = {'KRD_PLUGIN_ENABLED': 'true'} sh.inline = <<-SHELL + cp /vagrant/insecure_keys/key.pub /home/vagrant/.ssh/id_rsa.pub cp /vagrant/insecure_keys/key /home/vagrant/.ssh/id_rsa chown vagrant /home/vagrant/.ssh/id_rsa chmod 400 /home/vagrant/.ssh/id_rsa diff --git a/vagrant/insecure_keys/key.pub b/vagrant/insecure_keys/key.pub new file mode 100644 index 00000000..18a9c00f --- /dev/null +++ b/vagrant/insecure_keys/key.pub @@ -0,0 +1 @@ +ssh-rsa AAAAB3NzaC1yc2EAAAABIwAAAQEA6NF8iallvQVp22WDkTkyrtvp9eWW6A8YVr+kz4TjGYe7gHzIw+niNltGEFHzD8+v1I2YJ6oXevct1YeS0o9HZyN1Q9qgCgzUFtdOKLv6IedplqoPkcmF0aYet2PkEDo3MlTBckFXPITAMzF8dJSIFo9D8HfdOV0IAdx4O7PtixWKn5y2hMNG0zQPyUecp4pzC6kivAIhyfHilFR61RGL+GPXQ2MWZWFYbAGjyiYJnAmCP3NOTd0jMZEnDkbUvxhMmBYSdETk1rRgm+R4LOzFUGaHqHDLKLX+FIPKcF96hrucXzcWyLbIbEgE98OHlnVYCzRdK8jlqm8tehUc9c9WhQ== vagrant insecure public key diff --git a/vagrant/installer.sh b/vagrant/installer.sh index e251170f..271f44f5 100755 --- a/vagrant/installer.sh +++ b/vagrant/installer.sh @@ -131,7 +131,7 @@ function install_addons { sudo ansible-galaxy install $verbose -r $krd_folder/galaxy-requirements.yml --ignore-errors ansible-playbook $verbose -i $krd_inventory $krd_playbooks/configure-krd.yml | sudo tee $log_folder/setup-krd.log - for addon in ${KRD_ADDONS:-virtlet ovn-kubernetes multus}; do + for addon in ${KRD_ADDONS:-virtlet ovn4nfv}; do echo "Deploying $addon using configure-$addon.yml playbook.." ansible-playbook $verbose -i $krd_inventory $krd_playbooks/configure-${addon}.yml | sudo tee $log_folder/setup-${addon}.log if [[ "${testing_enabled}" == "true" ]]; then @@ -212,6 +212,7 @@ testing_enabled=${KRD_ENABLE_TESTS:-false} sudo mkdir -p $log_folder sudo mkdir -p /opt/csar +sudo chown -R $USER /opt/csar export CSAR_DIR=/opt/csar echo "export CSAR_DIR=${CSAR_DIR}" | sudo tee --append /etc/environment diff --git a/vagrant/playbooks/configure-ovn4nfv.yml b/vagrant/playbooks/configure-ovn4nfv.yml new file mode 100644 index 00000000..c864b8c3 --- /dev/null +++ b/vagrant/playbooks/configure-ovn4nfv.yml @@ -0,0 +1,98 @@ +--- +# SPDX-license-identifier: Apache-2.0 +############################################################################## +# Copyright (c) 2018 +# All rights reserved. This program and the accompanying materials +# are made available under the terms of the Apache License, Version 2.0 +# which accompanies this distribution, and is available at +# http://www.apache.org/licenses/LICENSE-2.0 +############################################################################## +- import_playbook: configure-ovn.yml +- import_playbook: configure-multus.yml + +- hosts: kube-master:kube-node + environment: + PATH: "{{ ansible_env.PATH }}:/usr/local/go/bin/" + roles: + - role: andrewrothstein.go + tasks: + - name: Load krd variables + include_vars: + file: krd-vars.yml + - name: clone ovn4nfv-k8s-plugin repo + git: + repo: "{{ ovn4nfv_url }}" + dest: "{{ ovn4nfv_dest }}" + version: "{{ ovn4nfv_version }}" + force: yes + when: ovn4nfv_source_type == "source" + - name: clean ovn4nfvk8s left over files + make: + chdir: "{{ ovn4nfv_dest }}" + target: clean + - name: build ovn4nfvk8s-cni + make: + chdir: "{{ ovn4nfv_dest }}" + target: ovn4nfvk8s-cni + become: yes + environment: + GOPATH: "{{ go_path }}" + - name: copy ovn4nfvk8s-cni to cni folder + command: "mv {{ ovn4nfv_dest }}/ovn4nfvk8s-cni /opt/cni/bin/ovn4nfvk8s-cni" + become: yes + - name: create ovn4k8s config file + become: yes + blockinfile: + path: /etc/openvswitch/ovn4nfv_k8s.conf + create: yes + block: | + [logging] + loglevel=5 + logfile=/var/log/openvswitch/ovn4k8s.log + + [cni] + conf-dir=/etc/cni/net.d + plugin=ovn4nfvk8s-cni + + [kubernetes] + kubeconfig=/etc/kubernetes/admin.conf + - name: create ovnkube logging directory + file: + path: /var/log/openvswitch + state: directory + +- hosts: kube-master + environment: + PATH: "{{ ansible_env.PATH }}:/usr/local/go/bin/" + become: yes + tasks: + - name: Load krd variables + include_vars: + file: krd-vars.yml + - name: build ovn4nfvk8s + make: + chdir: "{{ ovn4nfv_dest }}" + target: ovn4nfvk8s + environment: + GOPATH: "{{ go_path }}" + - name: copy ovn4nfvk8s to /usr/bin folder + command: "mv {{ ovn4nfv_dest }}/ovn4nfvk8s /usr/bin/ovn4nfvk8s" + - name: create ovn4nfvk8s systemd service + blockinfile: + path: /etc/systemd/system/ovn4nfvk8s.service + create: yes + block: | + [Unit] + Description=OVN4NFV Kubernetes Daemon + + [Service] + ExecStart=/usr/bin/ovn4nfvk8s \ + -k8s-kubeconfig=/etc/kubernetes/admin.conf + + [Install] + WantedBy=multi-user.target + - name: start ovn4nfvk8s systemd service + service: + name: ovn4nfvk8s + state: started + enabled: yes diff --git a/vagrant/playbooks/krd-vars.yml b/vagrant/playbooks/krd-vars.yml index 0269b9bb..15b7a1a4 100644 --- a/vagrant/playbooks/krd-vars.yml +++ b/vagrant/playbooks/krd-vars.yml @@ -51,6 +51,12 @@ istio_source_type: "tarball" istio_version: 1.0.3 istio_url: "https://github.com/istio/istio/releases/download/{{ istio_version }}/istio-{{ istio_version }}-linux.tar.gz" +go_path: "{{ base_dest }}/go" +ovn4nfv_dest: "{{ go_path }}/src/ovn4nfv-k8s-plugin" +ovn4nfv_source_type: "source" +ovn4nfv_version: 5026d1d89b05eac5e004279b742df6745a73d93a +ovn4nfv_url: "https://git.opnfv.org/ovn4nfv-k8s-plugin/" + go_version: '1.11' kubespray_version: 2.8.0 kubectl_version: 1.11.2 diff --git a/vagrant/tests/_common.sh b/vagrant/tests/_common.sh index e5134fd6..620c00af 100755 --- a/vagrant/tests/_common.sh +++ b/vagrant/tests/_common.sh @@ -21,9 +21,11 @@ virtlet_image=virtlet.cloud/fedora virtlet_deployment_name=virtlet-deployment plugin_deployment_name=plugin-deployment plugin_service_name=plugin-service +ovn4nfv_deployment_name=ovn4nfv-deployment onap_private_net=onap-private-net unprotected_private_net=unprotected-private-net protected_private_net=protected-private-net +ovn_multus_network_name=ovn-networkobj # vFirewall vars demo_artifacts_version=1.3.0 @@ -229,6 +231,8 @@ function populate_CSAR_vms_containers_vFW { cat << META > metadata.yaml resources: network: + - onap-ovn4nfvk8s-network.yaml + onapNetwork: - $unprotected_private_net.yaml - $protected_private_net.yaml - $onap_private_net.yaml @@ -255,52 +259,53 @@ spec: context: darkstat SERVICE - cat << NET > $unprotected_private_net.yaml + cat << MULTUS_NET > onap-ovn4nfvk8s-network.yaml apiVersion: "k8s.cni.cncf.io/v1" kind: NetworkAttachmentDefinition metadata: - name: $unprotected_private_net + name: $ovn_multus_network_name spec: config: '{ - "name": "unprotected", - "type": "bridge", - "ipam": { - "type": "host-local", - "subnet": "$protected_private_net_cidr" - } -}' + "cniVersion": "0.3.1", + "name": "ovn4nfv-k8s-plugin", + "type": "ovn4nfvk8s-cni" + }' +MULTUS_NET + + cat << NET > $unprotected_private_net.yaml +apiVersion: v1 +kind: onapNetwork +metadata: + name: $unprotected_private_net + cnitype : ovn4nfvk8s +spec: + name: $unprotected_private_net + subnet: $protected_private_net_cidr + gateway: 192.168.10.1/24 NET cat << NET > $protected_private_net.yaml -apiVersion: "k8s.cni.cncf.io/v1" -kind: NetworkAttachmentDefinition +apiVersion: v1 +kind: onapNetwork metadata: name: $protected_private_net + cnitype : ovn4nfvk8s spec: - config: '{ - "name": "protected", - "type": "bridge", - "ipam": { - "type": "host-local", - "subnet": "$protected_net_cidr" - } -}' + name: $protected_private_net + subnet: $protected_net_cidr + gateway: $protected_net_gw/24 NET cat << NET > $onap_private_net.yaml -apiVersion: "k8s.cni.cncf.io/v1" -kind: NetworkAttachmentDefinition +apiVersion: v1 +kind: onapNetwork metadata: name: $onap_private_net + cnitype : ovn4nfvk8s spec: - config: '{ - "name": "onap", - "type": "bridge", - "ipam": { - "type": "host-local", - "subnet": "$onap_private_net_cidr" - } -}' + name: $onap_private_net + subnet: $onap_private_net_cidr + gateway: 10.10.0.1/16 NET proxy="apt:" @@ -370,9 +375,10 @@ spec: VirtletSSHKeys: | $ssh_key VirtletRootVolumeSize: 5Gi - k8s.v1.cni.cncf.io/networks: '[ - { "name": "$unprotected_private_net", "interfaceRequest": "eth1" }, - { "name": "$onap_private_net", "interfaceRequest": "eth2" } + k8s.v1.cni.cncf.io/networks: '[{ "name": "$ovn_multus_network_name"}]' + ovnNetwork: '[ + { "name": "$unprotected_private_net", "ipAddress": "$vpg_private_ip_0", "interface": "eth1" , "defaultGateway": "false"}, + { "name": "$onap_private_net", "ipAddress": "$vpg_private_ip_1", "interface": "eth2" , "defaultGateway": "false"} ]' kubernetes.io/target-runtime: virtlet.cloud spec: @@ -437,10 +443,11 @@ spec: VirtletSSHKeys: | $ssh_key VirtletRootVolumeSize: 5Gi - k8s.v1.cni.cncf.io/networks: '[ - { "name": "$unprotected_private_net", "interfaceRequest": "eth1" }, - { "name": "$protected_private_net", "interfaceRequest": "eth2" }, - { "name": "$onap_private_net", "interfaceRequest": "eth3" } + k8s.v1.cni.cncf.io/networks: '[{ "name": "$ovn_multus_network_name"}]' + ovnNetwork: '[ + { "name": "$unprotected_private_net", "ipAddress": "$vfw_private_ip_0", "interface": "eth1" , "defaultGateway": "false"}, + { "name": "$protected_private_net", "ipAddress": "$vfw_private_ip_1", "interface": "eth2", "defaultGateway": "false" }, + { "name": "$onap_private_net", "ipAddress": "$vfw_private_ip_2", "interface": "eth3" , "defaultGateway": "false"} ]' kubernetes.io/target-runtime: virtlet.cloud spec: @@ -483,9 +490,10 @@ spec: app: vFirewall context: darkstat annotations: - k8s.v1.cni.cncf.io/networks: '[ - { "name": "$protected_private_net", "interfaceRequest": "eth1" }, - { "name": "$onap_private_net", "interfaceRequest": "eth2" } + k8s.v1.cni.cncf.io/networks: '[{ "name": "$ovn_multus_network_name"}]' + ovnNetwork: '[ + { "name": "$protected_private_net", "ipAddress": "$vsn_private_ip_0", "interface": "eth1", "defaultGateway": "false" }, + { "name": "$onap_private_net", "ipAddress": "$vsn_private_ip_1", "interface": "eth2" , "defaultGateway": "false"} ]' spec: containers: @@ -1001,3 +1009,88 @@ SERVICE popd } +# populate_CSAR_ovn4nfv() - Create content used for OVN4NFV functional test +function populate_CSAR_ovn4nfv { + local csar_id=$1 + + _checks_args $csar_id + pushd ${CSAR_DIR}/${csar_id} + + cat << META > metadata.yaml +resources: + onap_network: + - ovn-port-net.yaml + - ovn-priv-net.yaml + network: + - onap-ovn4nfvk8s-network.yaml + deployment: + - $ovn4nfv_deployment_name.yaml +META + + cat << MULTUS_NET > onap-ovn4nfvk8s-network.yaml +apiVersion: "k8s.cni.cncf.io/v1" +kind: NetworkAttachmentDefinition +metadata: + name: $ovn_multus_network_name +spec: + config: '{ + "cniVersion": "0.3.1", + "name": "ovn4nfv-k8s-plugin", + "type": "ovn4nfvk8s-cni" + }' +MULTUS_NET + + cat << NETWORK > ovn-port-net.yaml +apiVersion: v1 +kind: onapNetwork +metadata: + name: ovn-port-net + cnitype : ovn4nfvk8s +spec: + name: ovn-port-net + subnet: 172.16.33.0/24 + gateway: 172.16.33.1/24 +NETWORK + + cat << NETWORK > ovn-priv-net.yaml +apiVersion: v1 +kind: onapNetwork +metadata: + name: ovn-priv-net + cnitype : ovn4nfvk8s +spec: + name: ovn-priv-net + subnet: 172.16.44.0/24 + gateway: 172.16.44.1/24 +NETWORK + + cat << DEPLOYMENT > $ovn4nfv_deployment_name.yaml +apiVersion: apps/v1 +kind: Deployment +metadata: + name: $ovn4nfv_deployment_name + labels: + app: ovn4nfv +spec: + replicas: 1 + selector: + matchLabels: + app: ovn4nfv + template: + metadata: + labels: + app: ovn4nfv + annotations: + k8s.v1.cni.cncf.io/networks: '[{ "name": "$ovn_multus_network_name"}]' + ovnNetwork: '[{ "name": "ovn-port-net", "interface": "net0" , "defaultGateway": "false"}, + { "name": "ovn-priv-net", "interface": "net1" , "defaultGateway": "false"}]' + spec: + containers: + - name: $ovn4nfv_deployment_name + image: "busybox" + command: ["top"] + stdin: true + tty: true +DEPLOYMENT + popd +} diff --git a/vagrant/tests/_functions.sh b/vagrant/tests/_functions.sh index e3d88eb4..fe69b07b 100755 --- a/vagrant/tests/_functions.sh +++ b/vagrant/tests/_functions.sh @@ -12,6 +12,66 @@ set -o errexit set -o nounset set -o pipefail +function _get_ovn_central_address { + ansible_ifconfig=$(ansible ovn-central[0] -i $test_folder/../inventory/hosts.ini -m shell -a "ifconfig eth1 |grep \"inet addr\" |awk '{print \$2}' |awk -F: '{print \$2}'") + if [[ $ansible_ifconfig != *CHANGED* ]]; then + echo "Fail to get the OVN central IP address from eth1 nic" + exit + fi + echo "$(echo ${ansible_ifconfig#*>>} | tr '\n' ':')6641" +} + +# install_ovn_deps() - Install dependencies required for tests that require OVN +function install_ovn_deps { + if ! $(yq --version &>/dev/null); then + sudo -E pip install yq + fi + if ! $(ovn-nbctl --version &>/dev/null); then + source /etc/os-release || source /usr/lib/os-release + case ${ID,,} in + *suse) + ;; + ubuntu|debian) + sudo apt-get install -y apt-transport-https + echo "deb https://packages.wand.net.nz $(lsb_release -sc) main" | sudo tee /etc/apt/sources.list.d/wand.list + sudo curl https://packages.wand.net.nz/keyring.gpg -o /etc/apt/trusted.gpg.d/wand.gpg + sudo apt-get update + sudo apt install -y ovn-common + ;; + rhel|centos|fedora) + ;; + esac + fi +} + +# init_network() - This function creates the OVN resouces required by the test +function init_network { + local fname=$1 + local router_name="ovn4nfv-master" + + name=$(cat $fname | yq '.spec.name' | xargs) + subnet=$(cat $fname | yq '.spec.subnet' | xargs) + gateway=$(cat $fname | yq '.spec.gateway' | xargs) + ovn_central_address=$(_get_ovn_central_address) + + router_mac=$(printf '00:00:00:%02X:%02X:%02X' $((RANDOM%256)) $((RANDOM%256)) $((RANDOM%256))) + ovn-nbctl --may-exist --db tcp:$ovn_central_address ls-add $name -- set logical_switch $name other-config:subnet=$subnet external-ids:gateway_ip=$gateway + ovn-nbctl --may-exist --db tcp:$ovn_central_address lrp-add $router_name rtos-$name $router_mac $gateway + ovn-nbctl --may-exist --db tcp:$ovn_central_address lsp-add $name stor-$name -- set logical_switch_port stor-$name type=router options:router-port=rtos-$name addresses=\"$router_mac\" +} + +# cleanup_network() - This function removes the OVN resources created for the test +function cleanup_network { + local fname=$1 + + name=$(cat $fname | yq '.spec.name' | xargs) + ovn_central_address=$(_get_ovn_central_address) + + for cmd in "ls-del $name" "lrp-del rtos-$name" "lsp-del stor-$name"; do + ovn-nbctl --if-exist --db tcp:$ovn_central_address $cmd + done +} + function _checks_args { if [[ -z $1 ]]; then echo "Missing CSAR ID argument" diff --git a/vagrant/tests/integration_vcFW.sh b/vagrant/tests/integration_vcFW.sh index 93e75961..15cffcb8 100755 --- a/vagrant/tests/integration_vcFW.sh +++ b/vagrant/tests/integration_vcFW.sh @@ -18,13 +18,19 @@ source _functions.sh csar_id=aa443e7e-c8ba-11e8-8877-525400b164ff # Setup +install_ovn_deps if [[ ! -f $HOME/.ssh/id_rsa.pub ]]; then echo -e "\n\n\n" | ssh-keygen -t rsa -N "" fi populate_CSAR_vms_containers_vFW $csar_id pushd ${CSAR_DIR}/${csar_id} -for resource in $unprotected_private_net $protected_private_net $onap_private_net sink-service; do +for net in $unprotected_private_net $protected_private_net $onap_private_net; do + cleanup_network $net.yaml + echo "Create OVN Network $net network" + init_network $net.yaml +done +for resource in onap-ovn4nfvk8s-network sink-service; do kubectl apply -f $resource.yaml done setup $packetgen_deployment_name $firewall_deployment_name $sink_deployment_name @@ -43,4 +49,7 @@ done # Teardown #teardown $packetgen_deployment_name $firewall_deployment_name $sink_deployment_name +#for net in $unprotected_private_net $protected_private_net $onap_private_net; do +# cleanup_network $net.yaml +#done popd diff --git a/vagrant/tests/ovn4nfv.sh b/vagrant/tests/ovn4nfv.sh new file mode 100755 index 00000000..37fddfd8 --- /dev/null +++ b/vagrant/tests/ovn4nfv.sh @@ -0,0 +1,46 @@ +#!/bin/bash +############################################################################## +# Copyright (c) 2018 +# All rights reserved. This program and the accompanying materials +# are made available under the terms of the Apache License, Version 2.0 +# which accompanies this distribution, and is available at +# http://www.apache.org/licenses/LICENSE-2.0 +############################################################################## + +set -o errexit +set -o nounset +set -o pipefail + +source _common.sh +source _functions.sh + +csar_id=a1c5b53e-d7ab-11e8-85b7-525400e8c29a + +# Setup +install_ovn_deps +populate_CSAR_ovn4nfv $csar_id + +pushd ${CSAR_DIR}/${csar_id} +for net in ovn-priv-net ovn-port-net; do + cleanup_network $net.yaml + echo "Create OVN Network $net network" + init_network $net.yaml +done +kubectl apply -f onap-ovn4nfvk8s-network.yaml +setup $ovn4nfv_deployment_name + +# Test +deployment_pod=$(kubectl get pods | grep $ovn4nfv_deployment_name | awk '{print $1}') +echo "===== $deployment_pod details =====" +kubectl exec -it $deployment_pod -- ip a +multus_nic=$(kubectl exec -it $deployment_pod -- ifconfig | grep "net1") +if [ -z "$multus_nic" ]; then + echo "The $deployment_pod pod doesn't contain the net1 nic" + exit 1 +fi + +# Teardown +teardown $ovn4nfv_deployment_name +cleanup_network ovn-priv-net.yaml +cleanup_network ovn-port-net.yaml +popd -- cgit 1.2.3-korg