From 960613e5c6c58a8b13d1ca450ed81ee400bb49c7 Mon Sep 17 00:00:00 2001 From: Pete Birley Date: Thu, 15 Jun 2017 21:51:53 -0500 Subject: [PATCH] Boot VM's and basic functional test in Zuul Checks This PS adds basic vm booting and functional testing to the single node Zuul gates. Multinode testing will be once we have ceph running in zuul. Change-Id: Ifcbdcaa4a30dee4088e369d4410dd737ef6f12cd --- tools/gate/basic_launch.sh | 13 +- tools/gate/funcs/common.sh | 31 +++++ tools/gate/funcs/helm.sh | 8 +- tools/gate/funcs/openstack.sh | 56 +++++++++ tools/gate/openstack_aio_launch.sh | 140 ++++++++++++++++++++++ tools/gate/setup_gate.sh | 4 + tools/kubeadm-aio/kubeadm-aio-launcher.sh | 1 + 7 files changed, 249 insertions(+), 4 deletions(-) create mode 100644 tools/gate/funcs/common.sh create mode 100755 tools/gate/funcs/openstack.sh create mode 100644 tools/gate/openstack_aio_launch.sh diff --git a/tools/gate/basic_launch.sh b/tools/gate/basic_launch.sh index 20251b6379..eb3bb32a00 100755 --- a/tools/gate/basic_launch.sh +++ b/tools/gate/basic_launch.sh @@ -26,25 +26,32 @@ if [ "x$HOST_OS" == "xfedora" ]; then sudo modprobe openvswitch sudo modprobe gre sudo modprobe vxlan + sudo modprobe ip6_tables fi helm install --namespace=openstack local/mariadb --name=mariadb helm install --namespace=openstack local/memcached --name=memcached helm install --namespace=openstack local/etcd --name=etcd-rabbitmq helm install --namespace=openstack local/rabbitmq --name=rabbitmq +kube_wait_for_pods openstack 420 helm install --namespace=openstack local/keystone --name=keystone helm install --namespace=openstack local/glance --name=glance \ --values=${WORK_DIR}/tools/overrides/mvp/glance.yaml +kube_wait_for_pods openstack 420 helm install --namespace=openstack local/nova --name=nova \ --values=${WORK_DIR}/tools/overrides/mvp/nova.yaml \ --set=conf.nova.libvirt.nova.conf.virt_type=qemu helm install --namespace=openstack local/neutron --name=neutron \ --values=${WORK_DIR}/tools/overrides/mvp/neutron.yaml +kube_wait_for_pods openstack 420 helm install --namespace=openstack local/cinder --name=cinder helm install --namespace=openstack local/heat --name=heat helm install --namespace=openstack local/horizon --name=horizon +kube_wait_for_pods openstack 420 -kube_wait_for_pods openstack 1200 +if [ "x$INTEGRATION" == "xaio" ]; then + bash ${WORK_DIR}/tools/gate/openstack_aio_launch.sh +fi -helm_test_deployment keystone -helm_test_deployment glance +helm_test_deployment keystone 600 +helm_test_deployment glance 600 diff --git a/tools/gate/funcs/common.sh b/tools/gate/funcs/common.sh new file mode 100644 index 0000000000..90176491e8 --- /dev/null +++ b/tools/gate/funcs/common.sh @@ -0,0 +1,31 @@ +#!/bin/bash +# +# 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. +set -e + +function base_install { + if [ "x$HOST_OS" == "xubuntu" ]; then + sudo apt-get update -y + sudo apt-get install -y --no-install-recommends -qq \ + iproute2 \ + iptables + elif [ "x$HOST_OS" == "xcentos" ]; then + sudo yum install -y \ + iproute \ + iptables + elif [ "x$HOST_OS" == "xfedora" ]; then + sudo dnf install -y \ + iproute \ + iptables + fi +} diff --git a/tools/gate/funcs/helm.sh b/tools/gate/funcs/helm.sh index 7da90e9385..937df8168e 100755 --- a/tools/gate/funcs/helm.sh +++ b/tools/gate/funcs/helm.sh @@ -79,7 +79,13 @@ function helm_build { function helm_test_deployment { DEPLOYMENT=$1 - helm test ${DEPLOYMENT} + if [ x$2 == "x" ]; then + TIMEOUT=300 + else + TIMEOUT=$2 + fi + + helm test --timeout ${TIMEOUT} ${DEPLOYMENT} mkdir -p ${LOGS_DIR}/rally kubectl logs -n openstack ${DEPLOYMENT}-rally-test > ${LOGS_DIR}/rally/${DEPLOYMENT} kubectl delete -n openstack pod ${DEPLOYMENT}-rally-test diff --git a/tools/gate/funcs/openstack.sh b/tools/gate/funcs/openstack.sh new file mode 100755 index 0000000000..a7dc0e9414 --- /dev/null +++ b/tools/gate/funcs/openstack.sh @@ -0,0 +1,56 @@ +#!/bin/bash +# +# 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. +set -e + +function wait_for_ping { + # Default wait timeout is 180 seconds + set +x + PING_CMD="ping -q -c 1 -W 1" + end=$(date +%s) + if [ x$2 != "x" ]; then + end=$((end + $2)) + else + end=$((end + 180)) + fi + while true; do + $PING_CMD $1 > /dev/null && \ + break || true + sleep 1 + now=$(date +%s) + [ $now -gt $end ] && echo "Could not ping $1 in time" && exit -1 + done + set -x + $PING_CMD $1 +} + +function openstack_wait_for_vm { + # Default wait timeout is 180 seconds + set +x + end=$(date +%s) + if [ x$2 != "x" ]; then + end=$((end + $2)) + else + end=$((end + 180)) + fi + while true; do + STATUS=$($OPENSTACK server show $1 -f value -c status) + [ $STATUS == "ACTIVE" ] && \ + break || true + sleep 1 + now=$(date +%s) + [ $now -gt $end ] && echo VM failed to start. && \ + $OPENSTACK server show $1 && exit -1 + done + set -x +} diff --git a/tools/gate/openstack_aio_launch.sh b/tools/gate/openstack_aio_launch.sh new file mode 100644 index 0000000000..a946dc86f5 --- /dev/null +++ b/tools/gate/openstack_aio_launch.sh @@ -0,0 +1,140 @@ +#!/bin/bash +# +# 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. +set -xe + +: ${KS_USER:="admin"} +: ${KS_PROJECT:="admin"} +: ${KS_PASSWORD:="password"} +: ${KS_USER_DOMAIN:="default"} +: ${KS_PROJECT_DOMAIN:="default"} +: ${KS_URL:="http://keystone-api.openstack:5000/v3"} + +: ${OSH_BR_EX_ADDR:="172.24.4.1/24"} +: ${OSH_EXT_SUBNET:="172.24.4.0/24"} +: ${OSH_EXT_DNS:="8.8.8.8"} +: ${OSH_EXT_NET_NAME:="public"} +: ${OSH_EXT_SUBNET_NAME:="public-subnet"} +: ${OSH_ROUTER:="router1"} +: ${OSH_PRIVATE_NET_NAME:="private"} +: ${OSH_PRIVATE_SUBNET:="10.0.0.0/24"} +: ${OSH_PRIVATE_SUBNET_NAME:="private-subnet"} +: ${OSH_PRIVATE_SUBNET_POOL:="10.0.0.0/8"} +: ${OSH_PRIVATE_SUBNET_POOL_NAME:="shared-default-subnetpool"} +: ${OSH_PRIVATE_SUBNET_POOL_DEF_PREFIX:="24"} +: ${OSH_VM_NAME:="osh-smoketest"} +: ${OSH_VM_KEY:="osh-smoketest-key"} + +# Source some functions that will help us +source ${WORK_DIR}/tools/gate/funcs/openstack.sh + +# Setup openstack clients +KEYSTONE_CREDS="--os-username ${KS_USER} \ + --os-project-name ${KS_PROJECT} \ + --os-auth-url ${KS_URL} \ + --os-project-domain-name ${KS_PROJECT_DOMAIN} \ + --os-user-domain-name ${KS_USER_DOMAIN} \ + --os-password ${KS_PASSWORD}" +NEUTRON_POD=$(kubectl get -n openstack pods -l app=neutron-server --no-headers -o name | head -1 | awk -F '/' '{ print $NF }') +NEUTRON="kubectl exec -n openstack ${NEUTRON_POD} -- neutron ${KEYSTONE_CREDS}" +OPENSTACK_POD=$(kubectl get -n openstack pods -l app=keystone-api --no-headers -o name | head -1 | awk -F '/' '{ print $NF }') +OPENSTACK="kubectl exec -n openstack ${OPENSTACK_POD} -- openstack ${KEYSTONE_CREDS} --os-identity-api-version 3 --os-image-api-version 2" +NOVA_POD=$(kubectl get -n openstack pods -l app=nova-api-osapi --no-headers -o name | head -1 | awk -F '/' '{ print $NF }') +NOVA="kubectl exec -n openstack ${NOVA_POD} -- nova ${KEYSTONE_CREDS}" + +# Turn on ip forwarding if its not already +if [ $(cat /proc/sys/net/ipv4/ip_forward) -eq 0 ]; then + sudo bash -c "echo 1 > /proc/sys/net/ipv4/ip_forward" +fi + +# Assign IP address to br-ex +sudo ip addr add ${OSH_BR_EX_ADDR} dev br-ex +sudo ip link set br-ex up + +# Disable In-Band rules on br-ex bridge to ease debugging +OVS_VSWITCHD_POD=$(kubectl get -n openstack pods -l app=ovs-vswitchd --no-headers -o name | head -1 | awk -F '/' '{ print $NF }') +kubectl exec -n openstack ${OVS_VSWITCHD_POD} -- ovs-vsctl set Bridge br-ex other_config:disable-in-band=true + +# Setup masquerading on default route dev to public subnet +DEFAULT_GW_DEV=$(sudo ip -4 route list 0/0 | cut -d ' ' -f 5) +sudo iptables -t nat -A POSTROUTING -o ${DEFAULT_GW_DEV} -s ${OSH_EXT_SUBNET} -j MASQUERADE + +# Create default networks +$NEUTRON net-create ${OSH_PRIVATE_NET_NAME} +$NEUTRON subnet-create \ + --name ${OSH_PRIVATE_SUBNET_NAME} \ + --ip-version 4 \ + --dns-nameserver ${OSH_EXT_DNS} \ + $($NEUTRON net-show private -f value -c id) \ + ${OSH_PRIVATE_SUBNET} +$NEUTRON router-create ${OSH_ROUTER} +$NEUTRON subnetpool-create \ + ${OSH_PRIVATE_SUBNET_POOL_NAME} \ + --default-prefixlen ${OSH_PRIVATE_SUBNET_POOL_DEF_PREFIX} \ + --pool-prefix ${OSH_PRIVATE_SUBNET_POOL} \ + --shared \ + --is-default=True +$NEUTRON net-create ${OSH_EXT_NET_NAME} -- --is-default \ + --router:external \ + --provider:network_type=flat \ + --provider:physical_network=public +$NEUTRON router-interface-add $($NEUTRON router-show ${OSH_ROUTER} -f value -c id) $($NEUTRON subnet-show private-subnet -f value -c id) +$NEUTRON subnet-create \ + --name ${OSH_EXT_SUBNET_NAME} \ + --ip-version 4 \ + $($NEUTRON net-show ${OSH_EXT_NET_NAME} -f value -c id) ${OSH_EXT_SUBNET} -- --enable_dhcp=False +$NEUTRON router-gateway-set $($NEUTRON router-show ${OSH_ROUTER} -f value -c id) $($NEUTRON net-show ${OSH_EXT_NET_NAME} -f value -c id) + +ROUTER_PUBLIC_IP=$($NEUTRON router-show ${OSH_ROUTER} -f value -c external_gateway_info | jq -r '.external_fixed_ips[].ip_address') +wait_for_ping ${ROUTER_PUBLIC_IP} + +# Setup SSH Keypair in Nova +KEYPAIR_LOC="$(mktemp).pem" +$OPENSTACK keypair create ${OSH_VM_KEY} > ${KEYPAIR_LOC} +chmod 600 ${KEYPAIR_LOC} + +# Boot a vm and wait for it to become active +FLAVOR=$($OPENSTACK flavor show "m1.tiny" -f value -c id) +IMAGE=$($OPENSTACK image list -f csv | awk -F ',' '{ print $2 "," $1 }' | grep "^\"Cirros" | head -1 | awk -F ',' '{ print $2 }' | tr -d '"') +NETWORK=$($NEUTRON net-show private -f value -c id) +$NOVA boot \ + --nic net-id=${NETWORK} \ + --flavor=${FLAVOR} \ + --image=${IMAGE} \ + --key-name=${OSH_VM_KEY} \ + --security-groups="default" \ + ${OSH_VM_NAME} +openstack_wait_for_vm ${OSH_VM_NAME} + +# Assign a floating IP to the VM +FLOATING_IP=$($OPENSTACK floating ip create ${OSH_EXT_NET_NAME} -f value -c floating_ip_address) +$OPENSTACK server add floating ip ${OSH_VM_NAME} ${FLOATING_IP} + +# Loosen up security group to allow access to the VM +PROJECT=$($OPENSTACK project show admin -f value -c id) +SECURITY_GROUP=$($OPENSTACK security group list -f csv | grep ${PROJECT} | grep "default" | awk -F "," '{ print $1 }' | tr -d '"') +$OPENSTACK security group rule create ${SECURITY_GROUP} --protocol icmp --src-ip 0.0.0.0/0 +$OPENSTACK security group rule create ${SECURITY_GROUP} --protocol tcp --dst-port 22:22 --src-ip 0.0.0.0/0 + +# Ping our VM +wait_for_ping ${FLOATING_IP} + +# SSH into the VM and check it can reach the outside world +ssh-keyscan "$FLOATING_IP" >> ~/.ssh/known_hosts +ssh -i ${KEYPAIR_LOC} cirros@${FLOATING_IP} ping -q -c 1 -W 2 ${OSH_BR_EX_ADDR%/*} + +# SSH into the VM and check it can reach the metadata server +ssh -i ${KEYPAIR_LOC} cirros@${FLOATING_IP} curl -sSL 169.254.169.254 + +# Bonus round - display a Unicorn +ssh -i ${KEYPAIR_LOC} cirros@${FLOATING_IP} curl http://artscene.textfiles.com/asciiart/unicorn || true diff --git a/tools/gate/setup_gate.sh b/tools/gate/setup_gate.sh index 5712cf956d..e31dd17a9e 100755 --- a/tools/gate/setup_gate.sh +++ b/tools/gate/setup_gate.sh @@ -21,6 +21,7 @@ export KUBEADM_IMAGE=openstackhelm/kubeadm-aio:${KUBE_VERSION} export WORK_DIR=$(pwd) source /etc/os-release export HOST_OS=${ID} +source ${WORK_DIR}/tools/gate/funcs/common.sh source ${WORK_DIR}/tools/gate/funcs/network.sh source ${WORK_DIR}/tools/gate/funcs/helm.sh @@ -33,6 +34,9 @@ function dump_logs () { } trap 'dump_logs "$?"' ERR +# Install base requirements +base_install + # Moving the ws-linter here to avoid it blocking all the jobs just for ws if [ "x$INTEGRATION_TYPE" == "xlinter" ]; then bash ${WORK_DIR}/tools/gate/whitespace.sh diff --git a/tools/kubeadm-aio/kubeadm-aio-launcher.sh b/tools/kubeadm-aio/kubeadm-aio-launcher.sh index 2f42fb768c..d9bab230e9 100755 --- a/tools/kubeadm-aio/kubeadm-aio-launcher.sh +++ b/tools/kubeadm-aio/kubeadm-aio-launcher.sh @@ -31,6 +31,7 @@ sudo rm -rfv \ /var/etcd \ /var/lib/kubelet/* \ /run/openvswitch \ + /var/lib/nova \ ${HOME}/.kubeadm-aio/admin.conf \ /var/lib/nfs-provisioner || true