作者:Maxwell Li
日期:2016/12/20
未經作者允許,禁止轉載本文任何內容。如需轉載請留言。
本文從代碼層面簡單描述了擴容的實現(xiàn)過程。
在廊坊的時候就接到任務要對compass4nfv實現(xiàn)擴容功能,前前后后花了近兩周時間才完成。雖然任務比較艱巨,但是開發(fā)效率實在是有待提高。從初期的如何寫入host信息到中期的如何引導虛擬機安裝系統(tǒng)再到后期的引導ansible,自己一步一步摸索著走下去,學到了不少新知識,也對compass4nfv如何部署OpenStack也有了更加深入的了解。
注:本文所描述的OpenStack部署均為3+2模式,3個計算節(jié)點,2個控制節(jié)點,首次部署的節(jié)點為host1-5,新增計算節(jié)點為host6。
一、修改base.conf文件
加入了expansion變量,當expansion=false時,部署OpenStack;當expansion=true時,進行擴容,增加一個或多個計算節(jié)點。
export EXPANSION=${EXPANSION:-"false"}
二、修改launch.sh腳本
在launch.sh的main process中,進行擴容時,由于已經部署過OpenStack,只需要直接讀取machines信息即可。加入以下代碼
if [[ "$EXPANSION" == "false" ]]
then
...
else
machines=`get_host_macs`
if [[ -z $machines ]];then
log_error "get_host_macs failed"
exit 1
fi
log_info "deploy host macs: $machines"
fi
三、修改host_baremetal.sh/host_virtual.sh腳本
host_baremetal.sh腳本主要是為了從DHA文件中讀取到host的mac地址,而host_virtual.sh還要兼顧到拉起虛擬機、創(chuàng)建mac地址等工作(原代碼中默認虛擬部署的DHA文件中不寫入mac地址,虛擬機的mac地址由host_virtual.sh腳本中的get_host_macs()函數(shù)自動生成)。
考慮到在部署OpenStack時已經從DHA文件讀取或者自動生成5個mac地址,應該直接從work/deploy/switch_machines文件中讀取,而不是再次生成或者從DHA文件中再讀取一遍。不能夠重新生成比較好理解,如果重新生成幾個mac地址寫入到switch_machines中,將會導致和現(xiàn)有的host1-5mac地址不同。但是也不能再次從DHA文件中讀取,因為compass4nfv會部署DHA文件中的所有host,為了不影響host1-5的正常工作,必須重新寫一份DHA文件,而且此DHA文件中只能存在需要創(chuàng)建的新host。
示例文件:./deploy/conf/hardware_environment/expansion-sample/hardware_cluster_expansion.yml和./deploy/conf/vm_environment/virtual_cluster_expansion.yml。
host_baremetal.sh改動較小,貼上擴容前后的代碼:
擴容前:
function get_host_macs() {
machines=`echo $HOST_MACS | sed -e 's/,/'\',\''/g' -e 's/^/'\''/g' -e 's/$/'\''/g'`
echo $machines
}
擴容后:
function get_host_macs() {
if [[ "$EXPANSION" == "false" ]]; then
machines=`echo $HOST_MACS | sed -e 's/,/'\',\''/g' -e 's/^/'\''/g' -e 's/$/'\''/g'`
echo $machines > $WORK_DIR/switch_machines
else
machines_old=`cat $WORK_DIR/switch_machines`
machines_add=`echo $HOST_MACS | sed -e 's/,/'\',\''/g' -e 's/^/'\''/g' -e 's/$/'\''/g'`
echo $machines_add $machines_old > $WORK_DIR/switch_machines
machines=`echo $machines_add $machines_old|sed 's/ /,/g'`
fi
echo $machines
}
由以上代碼可以看出,在部署時(即$EXPANSION" == "false),先將DHA文件中讀取到的mac地址寫入switch_machines文件中。當需要擴容時,先從switch_machines文件中獲取到host1-5的mac地址,然后再從新的DHA文件中獲取到host6的mac地址,再一起寫入到switch_machines。
host_virtual.sh的改動稍微大一些,無非就是要多考慮DHA文件中沒有mac地址,要自動生成的情況。代碼如下:
擴容前:
function get_host_macs() {
local mac_generator=${COMPASS_DIR}/deploy/mac_generator.sh
local machines=
if [[ $REDEPLOY_HOST == "true" ]]; then
mac_array=`cat $WORK_DIR/switch_machines`
else
chmod +x $mac_generator
mac_array=`$mac_generator $VIRT_NUMBER`
echo $mac_array > $WORK_DIR/switch_machines
fi
machines=`echo $mac_array|sed 's/ /,/g'`
echo $machines
}
擴容后:
function get_host_macs() {
local mac_generator=${COMPASS_DIR}/deploy/mac_generator.sh
local machines=
if [[ $REDEPLOY_HOST == "true" ]]; then
mac_array=`cat $WORK_DIR/switch_machines`
machines=`echo $mac_array|sed 's/ /,/g'`
else
if [[ -z $HOST_MACS ]]; then
if [[ "$EXPANSION" == "false" ]]; then
chmod +x $mac_generator
mac_array=`$mac_generator $VIRT_NUMBER`
echo $mac_array > $WORK_DIR/switch_machines
machines=`echo $mac_array|sed 's/ /,/g'`
else
machines_old=`cat $WORK_DIR/switch_machines`
chmod +x $mac_generator
machines_add=`$mac_generator $VIRT_NUMBER`
echo $machines_add $machines_old > $WORK_DIR/switch_machines
machines=`echo $machines_add $machines_old|sed 's/ /,/g'`
fi
else
if [[ "$EXPANSION" == "false" ]]; then
machines=`echo $HOST_MACS | sed -e 's/,/'\',\''/g' -e 's/^/'\''/g' -e 's/$/'\''/g'`
else
machines_old=`cat $WORK_DIR/switch_machines`
machines_add=`echo $HOST_MACS | sed -e 's/,/'\',\''/g' -e 's/^/'\''/g' -e 's/$/'\''/g'`
echo $machines_add $machines_old > $WORK_DIR/switch_machines
machines=`echo $machines_add $machines_old|sed 's/ /,/g'`
fi
fi
fi
echo $machines
}
先考慮DHA文件中是否存在mac地址,如果存在,則和host_baremetal.sh的處理方式相同;如果不存在,則創(chuàng)建mac地址,并寫入到switch_machines中。
四、修改client.py腳本
client.py腳本應該算是改動最大的腳本之一,但是和之前的腳本如出一轍,增加一個對expansion的判斷。
首先來看deploy函數(shù)。擴容前僅有if CONF.expansion == "false"部分,擴容后增加了else,代碼如下:
def deploy():
if CONF.expansion == "false":
client = CompassClient()
machines = client.get_machines()
LOG.info('machines are %s', machines)
client.add_subnets()
adapter_id, os_id, flavor_id = client.get_adapter()
cluster_id = client.add_cluster(adapter_id, os_id, flavor_id)
client.add_cluster_hosts(cluster_id, machines)
client.set_host_networking()
client.set_cluster_os_config(cluster_id)
if flavor_id:
client.set_cluster_package_config(cluster_id)
client.set_all_hosts_roles(cluster_id)
client.deploy_clusters(cluster_id)
LOG.info("compass OS installtion is begin")
threading.Thread(target=print_ansible_log).start()
client.get_installing_progress(cluster_id)
client.check_dashboard_links(cluster_id)
else:
client = CompassClient()
machines = client.get_machines()
LOG.info('machines are %s', machines)
client.add_subnets()
status, response = client.client.list_clusters()
cluster_id = 1
for cluster in response:
if cluster['name'] == CONF.cluster_name:
cluster_id = cluster['id']
client.add_cluster_hosts(cluster_id, machines)
client.set_host_networking()
client.set_cluster_os_config(cluster_id)
client.set_cluster_package_config(cluster_id)
client.set_all_hosts_roles(cluster_id)
client.deploy_clusters(cluster_id)
threading.Thread(target=print_ansible_log).start()
client.get_installing_progress(cluster_id)
部署和擴容的大部分步驟相似,在擴容中刪去了對cluster_id的獲取,直接置為1,僅考慮單租戶的情況。
然后再來看看else部分中對函數(shù)內部的修改。
def add_cluster_hosts(self, cluster_id, machines):
由于通過get_machines獲取到的machines=[1,2,3,4,5,6],而add_cluster_hosts函數(shù)中獲取到的hostnames=[host6],為了使machines與hostnames對應,需要將machines中前五位刪去。故在add_cluster_hosts中加入:machines = machines[-len(hostnames):]。最開始沒有對machines進行處理,通過zip(machines, hostnames)后得到[1,"host6"],而machine_id=1已經被host1占用,導致無法加入host6。
def add_subnets(self):
在部署時,需要通過add_subnet()函數(shù)來獲取subnet,但是在部署時將沿用部署時采用的subnet,代碼如下:
if CONF.expansion == "false":
status, resp = self.client.add_subnet(subnet)
LOG.info('add subnet %s status %s response %s',
subnet, status, resp)
if not self.is_ok(status):
raise RuntimeError('failed to add subnet %s' % subnet)
subnet_mapping[resp['subnet']] = resp['id']
else:
for subnet_in_db in subnets_in_db:
if subnet == subnet_in_db['subnet']:
subnet_mapping[subnet] = subnet_in_db['id']
五、修改ansible腳本
至此,能夠成功寫入host6信息,并且安裝host6的操作系統(tǒng)。但是在安裝系統(tǒng)后,發(fā)現(xiàn)host6中ansible并沒有跑起來。進入到compass虛擬機中,將/var/ansible/run/openstack_mitaka-opnfv2/group_vars/all和/var/ansible/run/openstack_mitaka-opnfv2-expansion/group_vars /all進行對比,結果如下:
...
@@ -38,8 +38,8 @@
internal_ip: "{{ ip_settings[inventory_hostname]['mgmt']['ip'] }}"
internal_nic: mgmt
-vrouter_id_internal: 62
-vrouter_id_public: 62
+vrouter_id_internal: 102
+vrouter_id_public: 102
identity_host: "{{ internal_ip }}"
controllers_host: "{{ internal_ip }}"
@@ -50,8 +50,14 @@
dashboard_host: "{{ internal_ip }}"
haproxy_hosts:
+ host1: 172.16.1.1
+ host2: 172.16.1.2
+ host3: 172.16.1.3
...
在openstack_mitaka-opnfv2-expansion中的all文件中haproxy_hosts下沒有任何內容,手動從openstack_mitaka-opnfv2中的all文件中拷入后,才能夠正確安裝compute節(jié)點。由此考慮,在./deploy/adapters/ansible/openstack_mitaka/roles/nova-compute/templates/目錄下加入nova.conf,此文件從./deploy/adapters/ansible/openstack_mitaka/templates/目錄下拷貝過來,并略作修改。修改后對比如下:
--- ./nova.conf
+++ ../roles/nova-compute/templates/nova.conf
@@ -1,10 +1,6 @@
-{% set memcached_servers = [] %}
-{% for host in haproxy_hosts.values() %}
-{% set _ = memcached_servers.append('%s:11211'% host) %}
-{% endfor %}
-{% set memcached_servers = memcached_servers|join(',') %}
-
[DEFAULT]
+block_device_allocate_retries=5
+block_device_allocate_retries_interval=300
dhcpbridge_flagfile=/etc/nova/nova.conf
dhcpbridge=/usr/bin/nova-dhcpbridge
logdir=/var/log/nova
@@ -53,8 +49,6 @@
notification_driver = nova.openstack.common.notifier.rpc_notifier
notification_driver = ceilometer.compute.nova_notifier
-memcached_servers = {{ memcached_servers }}
-
[database]
# The SQLAlchemy connection string used to connect to the database
connection = mysql://nova:{{ NOVA_DBPASS }}@{{ db_host }}/nova
@@ -74,7 +68,6 @@
admin_tenant_name = service
admin_user = nova
admin_password = {{ NOVA_PASS }}
-memcached_servers = {{ memcached_servers }}
[glance]
host = {{ internal_vip.ip }}
并且修改./deploy/adapters/ansible/openstack_mitaka/roles/nova-compute/tasks/main.yml文件,修改如下:
--- a/deploy/adapters/ansible/openstack_mitaka/roles/nova-compute/tasks/main.yml
+++ b/deploy/adapters/ansible/openstack_mitaka/roles/nova-compute/tasks/main.yml
@@ -31,7 +31,7 @@
when: ansible_os_family == "Debian"
- name: update nova-compute conf
- template: src=templates/{{ item }} dest=/etc/nova/{{ item }}
+ template: src={{ item }} dest=/etc/nova/{{ item }}
with_items:
- nova.conf
notify:
以上,擴容功能的開發(fā)基本結束。關于compass4nfv部署OpenStack的過程,本人也有很多地方沒有了解透測,歡迎各位留言交流。
完整的代碼對比可參照以下網(wǎng)址:
https://gerrit.opnfv.org/gerrit/#/c/20859/
https://gerrit.opnfv.org/gerrit/#/c/20869/
另外,關于擴容功能的使用,可參考以下說明文檔:
http://artifacts.opnfv.org/compass4nfv/review/20995/installationprocedure/expansion.html