devtest_undercloud¶
Add extra elements for Undercloud UI
if [ "$USE_UNDERCLOUD_UI" -ne 0 ] ; then UNDERCLOUD_DIB_EXTRA_ARGS="$UNDERCLOUD_DIB_EXTRA_ARGS ceilometer-collector \ ceilometer-api ceilometer-agent-central ceilometer-agent-notification \ ceilometer-undercloud-config horizon nova-ironic" fi
Specifiy a client-side timeout in minutes for creating or updating the undercloud Heat stack.
UNDERCLOUD_STACK_TIMEOUT=${UNDERCLOUD_STACK_TIMEOUT:-60}
Create your undercloud image. This is the image that the seed nova will deploy to become the baremetal undercloud. $UNDERCLOUD_DIB_EXTRA_ARGS is meant to be used to pass additional arguments to disk-image-create.
NODE_ARCH=$(os-apply-config -m $TE_DATAFILE --key arch --type raw) $TRIPLEO_ROOT/diskimage-builder/bin/disk-image-create $NODE_DIST \ -a $NODE_ARCH -o $TRIPLEO_ROOT/undercloud \ ntp baremetal boot-stack os-collect-config dhcp-all-interfaces \ neutron-dhcp-agent $DIB_COMMON_ELEMENTS $UNDERCLOUD_DIB_EXTRA_ARGS 2>&1 | \ tee $TRIPLEO_ROOT/dib-undercloud.log
If you wanted to build the image and run it elsewhere, you can stop at this point and head onto the overcloud image building.
Load the undercloud image into Glance:
UNDERCLOUD_ID=$(load-image -d $TRIPLEO_ROOT/undercloud.qcow2)
Set the public interface of the undercloud network node:
NeutronPublicInterface=${NeutronPublicInterface:-'nic1'}
Set the NTP server for the undercloud::
UNDERCLOUD_NTP_SERVER=${UNDERCLOUD_NTP_SERVER:-''}
Create secrets for the cloud. The secrets will be written to a file ($TRIPLEO_ROOT/tripleo-undercloud-passwords by default) that you need to source into your shell environment.
Note
You can also make or change these later and update the heat stack definition to inject them - as long as you also update the keystone recorded password.
Note
There will be a window between updating keystone and instances where they will disagree and service will be down. Instead consider adding a new service account and changing everything across to it, then deleting the old account after the cluster is updated.
setup-undercloud-passwords $TRIPLEO_ROOT/tripleo-undercloud-passwords source $TRIPLEO_ROOT/tripleo-undercloud-passwords
Export UNDERCLOUD_CEILOMETER_SNMPD_PASSWORD to your environment so it can be applied to the SNMPd of all Overcloud nodes.
NEW_JSON=$(jq ‘.undercloud.ceilometer_snmpd_password=”’${UNDERCLOUD_CEILOMETER_SNMPD_PASSWORD}’”’ $TE_DATAFILE) echo $NEW_JSON > $TE_DATAFILE
Pull out needed variables from the test environment definition.
POWER_MANAGER=$(os-apply-config -m $TE_DATAFILE --key power_manager --type raw) POWER_KEY=$(os-apply-config -m $TE_DATAFILE --key ssh-key --type raw) POWER_HOST=$(os-apply-config -m $TE_DATAFILE --key host-ip --type raw) POWER_USER=$(os-apply-config -m $TE_DATAFILE --key ssh-user --type raw)
Wait for the BM cloud to register BM nodes with the scheduler:
wait_for -w 60 --delay 1 -- wait_for_hypervisor_stats
We need an environment file to store the parameters we’re going to give heat.:
HEAT_ENV=${HEAT_ENV:-"${TRIPLEO_ROOT}/undercloud-env.json"}
Read the heat env in for updating.:
if [ -e "${HEAT_ENV}" ]; then ENV_JSON=$(cat "${HEAT_ENV}") else ENV_JSON='{"parameters":{}}' fi
Detect if we are deploying with a VLAN for API endpoints / floating IPs. This is done by looking for a ‘public’ network in Neutron, and if found we pull out the VLAN id and pass that into Heat, as well as using a VLAN enabled Heat template.
if (neutron net-list | grep -q public); then VLAN_ID=$(neutron net-show public | awk '/provider:segmentation_id/ { print $4 }') else VLAN_ID= fi
Nova-baremetal and Ironic require different Heat templates and different options.
if [ -n "$VLAN_ID" ]; then HEAT_UNDERCLOUD_TEMPLATE="undercloud-vm-ironic-vlan.yaml" ENV_JSON=$(jq .parameters.NeutronPublicInterfaceTag=\"${VLAN_ID}\" <<< $ENV_JSON) # This should be in the heat template, but see # https://bugs.launchpad.net/heat/+bug/1336656 # note that this will break if there are more than one subnet, as if # more reason to fix the bug is needed :). PUBLIC_SUBNET_ID=$(neutron net-show public | awk '/subnets/ { print $4 }') VLAN_GW=$(neutron subnet-show $PUBLIC_SUBNET_ID | awk '/gateway_ip/ { print $4}') BM_VLAN_CIDR=$(neutron subnet-show $PUBLIC_SUBNET_ID | awk '/cidr/ { print $4}') ENV_JSON=$(jq .parameters.NeutronPublicInterfaceDefaultRoute=\"${VLAN_GW}\" <<< $ENV_JSON) else HEAT_UNDERCLOUD_TEMPLATE="undercloud-vm-ironic.yaml" fi ENV_JSON=$(jq .parameters.IronicPassword=\"${UNDERCLOUD_IRONIC_PASSWORD}\" <<< $ENV_JSON) REGISTER_SERVICE_OPTS="--ironic-password $UNDERCLOUD_IRONIC_PASSWORD" STACKNAME_UNDERCLOUD=${STACKNAME_UNDERCLOUD:-'undercloud'}
Choose whether to deploy or update. Use stack-update to update:: HEAT_OP=stack-create
if heat stack-show $STACKNAME_UNDERCLOUD > /dev/null; then HEAT_OP=stack-update if (heat stack-show $STACKNAME_UNDERCLOUD | grep -q FAILED); then echo "Updating a failed stack. this is a new ability and may cause problems." >&2 fi else HEAT_OP=stack-create fi
Set parameters we need to deploy a baremetal undercloud:
ENV_JSON=$(jq '.parameters = { "MysqlInnodbBufferPoolSize": 100 } + .parameters + { "AdminPassword": "'"${UNDERCLOUD_ADMIN_PASSWORD}"'", "AdminToken": "'"${UNDERCLOUD_ADMIN_TOKEN}"'", "SnmpdReadonlyUserPassword": "'"${UNDERCLOUD_CEILOMETER_SNMPD_PASSWORD}"'", "GlancePassword": "'"${UNDERCLOUD_GLANCE_PASSWORD}"'", "HeatPassword": "'"${UNDERCLOUD_HEAT_PASSWORD}"'", "NovaPassword": "'"${UNDERCLOUD_NOVA_PASSWORD}"'", "NeutronPassword": "'"${UNDERCLOUD_NEUTRON_PASSWORD}"'", "NeutronPublicInterface": "'"${NeutronPublicInterface}"'", "undercloudImage": "'"${UNDERCLOUD_ID}"'", "BaremetalArch": "'"${NODE_ARCH}"'", "PowerSSHPrivateKey": "'"${POWER_KEY}"'", "NtpServer": "'"${UNDERCLOUD_NTP_SERVER}"'", "Flavor": "'"${FLAVOR}"'" }' <<< $ENV_JSON) #Add Ceilometer to env only if USE_UNDERCLOUD_UI is specified if [ "$USE_UNDERCLOUD_UI" -ne 0 ] ; then ENV_JSON=$(jq '.parameters = .parameters + { "CeilometerPassword": "'"${UNDERCLOUD_CEILOMETER_PASSWORD}"'" }' <<< $ENV_JSON) fi
Save the finished environment file.:
jq . > "${HEAT_ENV}" <<< $ENV_JSON chmod 0600 "${HEAT_ENV}"
Add Keystone certs/key into the environment file.:
generate-keystone-pki --heatenv $HEAT_ENV
Deploy an undercloud.
make -C $TRIPLEO_ROOT/tripleo-heat-templates $HEAT_UNDERCLOUD_TEMPLATE heat $HEAT_OP -e $HEAT_ENV \ -t 360 \ -f $TRIPLEO_ROOT/tripleo-heat-templates/$HEAT_UNDERCLOUD_TEMPLATE \ $STACKNAME_UNDERCLOUD
You can watch the console via
virsh
/virt-manager
to observe the PXE boot/deploy process. After the deploy is complete, it will reboot into the image.Get the undercloud IP from
nova list
# Make time out 60 mins as like the Heat stack-create default timeout. wait_for_stack_ready -w $(($UNDERCLOUD_STACK_TIMEOUT * 60 )) 10 undercloud UNDERCLOUD_CTL_IP=$(nova list | grep ctlplane | sed -e "s/.*=\\([0-9.]*\\).*/\1/")
If we’re deploying with a public VLAN we must use it, not the control plane network (which we may not even have access to) to ping and configure thing.
if [ -n "$VLAN_ID" ]; then UNDERCLOUD_IP=$(heat output-show undercloud PublicIP|sed 's/^"\(.*\)"$/\1/') else UNDERCLOUD_IP=$UNDERCLOUD_CTL_IP fi
We don’t (yet) preserve ssh keys on rebuilds.
ssh-keygen -R $UNDERCLOUD_IP ssh-keygen -R $UNDERCLOUD_CTL_IP
Exclude the undercloud from proxies:
export no_proxy=$no_proxy,$UNDERCLOUD_IP
Export the undercloud endpoint and credentials to your test environment.
UNDERCLOUD_ENDPOINT="http://$UNDERCLOUD_IP:5000/v2.0" NEW_JSON=$(jq '.undercloud.password="'${UNDERCLOUD_ADMIN_PASSWORD}'" | .undercloud.endpoint="'${UNDERCLOUD_ENDPOINT}'" | .undercloud.endpointhost="'${UNDERCLOUD_IP}'"' $TE_DATAFILE) echo $NEW_JSON > $TE_DATAFILE
Source the undercloud configuration:
source $TRIPLEO_ROOT/tripleo-incubator/undercloudrc
Perform setup of your undercloud.
init-keystone -o $UNDERCLOUD_CTL_IP -t $UNDERCLOUD_ADMIN_TOKEN \ -e admin@example.com -p $UNDERCLOUD_ADMIN_PASSWORD \ --public $UNDERCLOUD_IP --no-pki-setup # Creating these roles to be used by tenants using swift openstack role create swiftoperator openstack role create ResellerAdmin # Create service endpoints and optionally include Ceilometer for UI support ENDPOINT_LIST="--glance-password $UNDERCLOUD_GLANCE_PASSWORD --heat-password $UNDERCLOUD_HEAT_PASSWORD --neutron-password $UNDERCLOUD_NEUTRON_PASSWORD --nova-password $UNDERCLOUD_NOVA_PASSWORD --tuskar-password $UNDERCLOUD_TUSKAR_PASSWORD" if [ "$USE_UNDERCLOUD_UI" -ne 0 ] ; then ENDPOINT_LIST="$ENDPOINT_LIST --ceilometer-password $UNDERCLOUD_CEILOMETER_PASSWORD" fi setup-endpoints $UNDERCLOUD_CTL_IP $ENDPOINT_LIST $REGISTER_SERVICE_OPTS \ --public $UNDERCLOUD_IP openstack role create heat_stack_user user-config BM_NETWORK_CIDR=$(os-apply-config -m $TE_DATAFILE --key baremetal-network.cidr --type raw --key-default '192.0.2.0/24') if [ -n "$VLAN_ID" ]; then # No ctl plane gateway - public net gateway is needed. # XXX (lifeless) - Neutron still configures one, first position in the subnet. BM_NETWORK_GATEWAY= else # Use a control plane gateway. BM_NETWORK_GATEWAY=$(os-apply-config -m $TE_DATAFILE --key baremetal-network.gateway-ip --type raw --key-default '192.0.2.1') fi BM_NETWORK_UNDERCLOUD_RANGE_START=$(os-apply-config -m $TE_DATAFILE --key baremetal-network.undercloud.range-start --type raw --key-default '192.0.2.21') BM_NETWORK_UNDERCLOUD_RANGE_END=$(os-apply-config -m $TE_DATAFILE --key baremetal-network.undercloud.range-end --type raw --key-default '192.0.2.40') UNDERCLOUD_NAMESERVER=$(os-apply-config -m $TE_DATAFILE --key undercloud.nameserver --type netaddress --key-default "${UNDERCLOUD_NAMESERVER:-}") NETWORK_JSON=$(mktemp) jq "." <<EOF > $NETWORK_JSON { "physical": { "gateway": "$BM_NETWORK_GATEWAY", "metadata_server": "$UNDERCLOUD_CTL_IP", "cidr": "$BM_NETWORK_CIDR", "allocation_start": "$BM_NETWORK_UNDERCLOUD_RANGE_START", "allocation_end": "$BM_NETWORK_UNDERCLOUD_RANGE_END", "name": "ctlplane", "nameserver": "$UNDERCLOUD_NAMESERVER" } } EOF setup-neutron -n $NETWORK_JSON rm $NETWORK_JSON if [ -n "$VLAN_ID" ]; then BM_VLAN_START=$(jq -r '.["baremetal-network"].undercloud.public_vlan.start' $TE_DATAFILE) BM_VLAN_END=$(jq -r '.["baremetal-network"].undercloud.public_vlan.finish' $TE_DATAFILE) PUBLIC_NETWORK_JSON=$(mktemp) jq "." <<EOF > $PUBLIC_NETWORK_JSON { "physical": { "gateway": "$VLAN_GW", "metadata_server": "$UNDERCLOUD_CTL_IP", "cidr": "$BM_VLAN_CIDR", "allocation_start": "$BM_VLAN_START", "allocation_end": "$BM_VLAN_END", "name": "public", "nameserver": "$UNDERCLOUD_NAMESERVER", "segmentation_id": "$VLAN_ID", "physical_network": "ctlplane", "enable_dhcp": false } } EOF setup-neutron -n $PUBLIC_NETWORK_JSON fi
Nova quota runs up with the defaults quota so overide the default to allow unlimited cores, instances and ram.
nova quota-update --cores -1 --instances -1 --ram -1 $(openstack project show admin | awk '$2=="id" {print $4}')
Register two baremetal nodes with your undercloud.
setup-baremetal --service-host undercloud --nodes <(jq '.nodes - [.nodes[0]]' $TE_DATAFILE)