summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorPeter Bandzi <pbandzi@cisco.com>2015-07-21 16:31:40 +0200
committerPeter Bandzi <pbandzi@cisco.com>2015-07-22 10:00:04 +0200
commit2beb18fbd56e7474e6da103634ce1feb697a4965 (patch)
treec45cf7109ab6be7ff281676f565e4b506720e0d0
parent85b729b515037043e21bbbcf3128045af1979c5e (diff)
Script for reconfiguring UCS network
Script will reconfigure POD-2 network for foreman or fuel Networ is specified in yaml file. Template must be created on UCS. JIRA: OCTO-109 Change-Id: I375a387c7607eb5dea126812569d8e19fda0c5c0 Signed-off-by: Peter Bandzi <pbandzi@cisco.com>
-rwxr-xr-xutils/lab-reconfiguration/create_venv.sh35
-rw-r--r--utils/lab-reconfiguration/foreman.yaml14
-rw-r--r--utils/lab-reconfiguration/fuel.yaml8
-rwxr-xr-xutils/lab-reconfiguration/reconfigUcsNet.py180
-rw-r--r--utils/lab-reconfiguration/requirements.pip2
5 files changed, 239 insertions, 0 deletions
diff --git a/utils/lab-reconfiguration/create_venv.sh b/utils/lab-reconfiguration/create_venv.sh
new file mode 100755
index 000000000..19d9b49c4
--- /dev/null
+++ b/utils/lab-reconfiguration/create_venv.sh
@@ -0,0 +1,35 @@
+#!/bin/bash -e
+
+# Script checks that venv exists. If it doesn't it will be created
+# It requires python2.7 and virtualenv packages installed
+
+BASEDIR=`dirname $0`
+
+function venv_install() {
+ if command -v virtualenv-2.7; then
+ virtualenv-2.7 $1
+ elif command -v virtualenv2; then
+ virtualenv2 $1
+ elif command -v virtualenv; then
+ virtualenv $1
+ else
+ echo Cannot find virtualenv command.
+ return 1
+ fi
+}
+
+# exit when something goes wrong during venv install
+set -e
+if [ ! -d "$BASEDIR/venv" ]; then
+ venv_install $BASEDIR/venv
+ echo "Virtualenv created."
+fi
+
+if [ ! -f "$BASEDIR/venv/updated" -o $BASEDIR/requirements.pip -nt $BASEDIR/venv/updated ]; then
+ source $BASEDIR/venv/bin/activate
+ pip install -r $BASEDIR/requirements.pip
+ touch $BASEDIR/venv/updated
+ echo "Requirements installed."
+ deactivate
+fi
+set +e
diff --git a/utils/lab-reconfiguration/foreman.yaml b/utils/lab-reconfiguration/foreman.yaml
new file mode 100644
index 000000000..ad91ba911
--- /dev/null
+++ b/utils/lab-reconfiguration/foreman.yaml
@@ -0,0 +1,14 @@
+# Vnic configuration for foreman deploy
+
+eth0:
+ order: 1
+ template: foreman-control
+eth1:
+ order: 2
+ template: foreman-private
+eth2:
+ order: 3
+ template: foreman-public
+eth3:
+ order: 4
+ template: foreman-storage
diff --git a/utils/lab-reconfiguration/fuel.yaml b/utils/lab-reconfiguration/fuel.yaml
new file mode 100644
index 000000000..3f31939e9
--- /dev/null
+++ b/utils/lab-reconfiguration/fuel.yaml
@@ -0,0 +1,8 @@
+# Vnic configuration for fuel deploy
+
+eth0:
+ order: 1
+ template: fuel-public
+eth1:
+ order: 2
+ template: fuel-tagged
diff --git a/utils/lab-reconfiguration/reconfigUcsNet.py b/utils/lab-reconfiguration/reconfigUcsNet.py
new file mode 100755
index 000000000..8adace00b
--- /dev/null
+++ b/utils/lab-reconfiguration/reconfigUcsNet.py
@@ -0,0 +1,180 @@
+#!/usr/bin/python
+#
+# 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 script reconfigure UCSM vnics for varios OPNFV deployers
+# Usage: reconfigUcsNet.py [options]
+#
+# Options:
+# -h, --help show this help message and exit
+# -i IP, --ip=IP [Mandatory] UCSM IP Address
+# -u USERNAME, --username=USERNAME
+# [Mandatory] Account Username for UCSM Login
+# -p PASSWORD, --password=PASSWORD
+# [Mandatory] Account Password for UCSM Login
+# -f FILE, --file=FILE
+# [Optional] Yaml file with network config you want to set for POD
+# If not present only current network config will be printed
+#
+
+import getpass
+import optparse
+import platform
+import yaml
+from UcsSdk import *
+from collections import defaultdict
+
+
+def getpassword(prompt):
+ if platform.system() == "Linux":
+ return getpass.unix_getpass(prompt=prompt)
+ elif platform.system() == "Windows" or platform.system() == "Microsoft":
+ return getpass.win_getpass(prompt=prompt)
+ else:
+ return getpass.getpass(prompt=prompt)
+
+
+def get_servers(handle=None):
+ """
+ Return list of servers
+ """
+ orgObj = handle.GetManagedObject(None, OrgOrg.ClassId(), {OrgOrg.DN : "org-root"})[0]
+ servers = handle.GetManagedObject(orgObj, LsServer.ClassId())
+ for server in servers:
+ if server.Type == 'instance' and "POD-2" in server.Dn:
+ yield server
+
+def get_vnics(handle=None, server=None):
+ """
+ Return list of vnics for given server
+ """
+ vnics = handle.ConfigResolveChildren(VnicEther.ClassId(), server.Dn, None, YesOrNo.TRUE)
+ return vnics.OutConfigs.GetChild()
+
+
+def get_network_config(handle=None):
+ """
+ Print current network config
+ """
+ print "\nCURRENT NETWORK CONFIG:"
+ for server in get_servers(handle):
+ print ' {}'.format(server.Name)
+ for vnic in get_vnics(handle, server):
+ print ' {}'.format(vnic.Name)
+ print ' {}'.format(vnic.Addr)
+ vnicIfs = handle.ConfigResolveChildren(VnicEtherIf.ClassId(), vnic.Dn, None, YesOrNo.TRUE)
+ for vnicIf in vnicIfs.OutConfigs.GetChild():
+ print ' Vlan: {}'.format(vnicIf.Vnet)
+
+
+def add_interface(handle=None, lsServerDn=None, vnicEther=None, templName=None, order=None):
+ """
+ Add interface to server specified by server.DN name
+ """
+ print " Adding interface: {}, template: {}, server.Dn: {}".format(vnicEther, templName, lsServerDn)
+ obj = handle.GetManagedObject(None, LsServer.ClassId(), {LsServer.DN:lsServerDn})
+ vnicEtherDn = lsServerDn + "/ether-" + vnicEther
+ params = {
+ VnicEther.STATS_POLICY_NAME: "default",
+ VnicEther.NAME: vnicEther,
+ VnicEther.DN: vnicEtherDn,
+ VnicEther.SWITCH_ID: "A-B",
+ VnicEther.ORDER: order,
+ "adminHostPort": "ANY",
+ VnicEther.ADMIN_VCON: "any",
+ VnicEther.NW_TEMPL_NAME: templName,
+ VnicEther.MTU: "1500"}
+ handle.AddManagedObject(obj, VnicEther.ClassId(), params, True)
+
+
+def remove_interface(handle=None, vnicEtherDn=None):
+ """
+ Remove interface specified by Distinguished Name (vnicEtherDn)
+ """
+ print " Removing interface: {}".format(vnicEtherDn)
+ obj = handle.GetManagedObject(None, VnicEther.ClassId(), {VnicEther.DN:vnicEtherDn})
+ handle.RemoveManagedObject(obj)
+
+
+def read_yaml_file(yamlFile):
+ """
+ Read vnic config from yaml file
+ """
+ # TODO: add check if vnic templates specified in file exist on UCS
+ with open(yamlFile, 'r') as stream:
+ return yaml.load(stream)
+
+
+def set_network(handle=None, yamlFile=None):
+ """
+ Configure VLANs on POD according specified network
+ """
+ # add interfaces and bind them with vNIC templates
+ # TODO: make sure MAC address for admin is still same
+ print "\nRECONFIGURING VNICs..."
+ network = read_yaml_file(yamlFile)
+ for server in get_servers(handle):
+ for iface, data in network.iteritems():
+ add_interface(handle, server.Dn, iface, data['template'], data['order'])
+ # Remove other interfaces which have not assigned required vnic template
+ vnics = get_vnics(handle, server)
+ for vnic in vnics:
+ if not any(data['template'] in vnic.OperNwTemplName for iface, data in network.iteritems()):
+ remove_interface(handle, vnic.Dn)
+ print " {} removed, template: {}".format(vnic.Name, vnic.OperNwTemplName)
+
+
+if __name__ == "__main__":
+ # Latest urllib2 validate certs by default
+ # The process wide "revert to the old behaviour" hook is to monkeypatch the ssl module
+ # https://bugs.python.org/issue22417
+ import ssl
+ if hasattr(ssl, '_create_unverified_context'):
+ ssl._create_default_https_context = ssl._create_unverified_context
+ try:
+ handle = UcsHandle()
+ parser = optparse.OptionParser()
+ parser.add_option('-i', '--ip',dest="ip",
+ help="[Mandatory] UCSM IP Address")
+ parser.add_option('-u', '--username',dest="userName",
+ help="[Mandatory] Account Username for UCSM Login")
+ parser.add_option('-p', '--password',dest="password",
+ help="[Mandatory] Account Password for UCSM Login")
+ parser.add_option('-f', '--file',dest="yamlFile",
+ help="[Optional] Yaml file contains network config you want to set on UCS POD1")
+ (options, args) = parser.parse_args()
+
+ if not options.ip:
+ parser.print_help()
+ parser.error("Provide UCSM IP Address")
+ if not options.userName:
+ parser.print_help()
+ parser.error("Provide UCSM UserName")
+ if not options.password:
+ options.password=getpassword("UCSM Password:")
+
+ handle.Login(options.ip, options.userName, options.password)
+
+ if (options.yamlFile != None):
+ print options.yamlFile
+ set_network(handle, options.yamlFile)
+ get_network_config(handle)
+
+ handle.Logout()
+
+ except Exception, err:
+ handle.Logout()
+ print "Exception:", str(err)
+ import traceback, sys
+ print '-'*60
+ traceback.print_exc(file=sys.stdout)
+ print '-'*60
diff --git a/utils/lab-reconfiguration/requirements.pip b/utils/lab-reconfiguration/requirements.pip
new file mode 100644
index 000000000..8cd1db0ba
--- /dev/null
+++ b/utils/lab-reconfiguration/requirements.pip
@@ -0,0 +1,2 @@
+UcsSdk==0.8.2.2
+PyYAML