OpenStack跨集群实例迁移后Floating IP及网络连通性异常排查
问题描述
我有一个由两个网络组成的OpenStack资源池,每个网络包含5个节点,其中4个固定在集群内,第5个节点可在集群间迁移。我编写了自动化迁移脚本,但执行后遇到以下问题:
- 迁移节点的Floating IP在实例属性中可见,但无法正常工作,无法通过SSH连接节点(已配置正确安全组);
- 同一集群内其他实例无法ping通该迁移节点(本应具备L2连接);
- 删除迁移实例并创建新实例后,原使用的Floating IP无法再次分配(未显示为可用状态)。
我推测服务器端Neutron未正确应用新实例网络配置,但我没有OpenStack基础设施服务器的访问权限,无法重启Neutron。以下是我使用的迁移脚本:
#!/bin/bash set -euo pipefail if [[ $# -ne 3 ]]; then echo "Usage: $0 <instance_name> <source_network> <destination_network>" exit 1 fi INSTANCE_NAME="$1" SOURCE_NET="$2" DEST_NET="$3" CLOUD="openstack" echo "Obtaining instance's id" INSTANCE_ID=$(openstack --os-cloud "$CLOUD" server show "$INSTANCE_NAME" -f value -c id) echo "Obtaining floating IP..." FLOATING_IP=$(openstack --os-cloud "$CLOUD" server show "$INSTANCE_NAME" -f json | jq -r '.addresses | to_entries[] | select(.key=="'"$SOURCE_NET"'") | .value' | grep -oP '\d+\.\d+\.\d+\.\d{1,3}' | tail -n1) echo "Floating IP: $FLOATING_IP" PORT_ID=$(openstack --os-cloud "$CLOUD" port list --server "$INSTANCE_ID" --network "$SOURCE_NET" -f value -c ID) echo "Old Port ID: $PORT_ID" FIP_ID=$(openstack --os-cloud "$CLOUD" floating ip list --floating-ip-address "$FLOATING_IP" -f value -c ID) echo "Disasociating floating IP" openstack --os-cloud "$CLOUD" floating ip unset "$FIP_ID" echo "Removing old port from instance" openstack --os-cloud "$CLOUD" server remove port "$INSTANCE_NAME" "$PORT_ID" openstack --os-cloud "$CLOUD" port delete "$PORT_ID" echo "Creating new port in $DEST_NET..." NEW_PORT_NAME="${INSTANCE_NAME}-${DEST_NET}-port" NEW_PORT_ID=$(openstack --os-cloud "$CLOUD" port create --network "$DEST_NET" "$NEW_PORT_NAME" -f value -c id) echo "New port created: $NEW_PORT_ID" echo "Associating new port to $INSTANCE_NAME" openstack --os-cloud "$CLOUD" server add port "$INSTANCE_NAME" "$NEW_PORT_ID" echo "Reassigning floating IP to port" openstack --os-cloud "$CLOUD" floating ip set --port "$NEW_PORT_ID" "$FIP_ID" openstack --os-cloud "$CLOUD" server add security group "$INSTANCE_NAME" kubernetes
解决方案
针对上述问题,可通过优化脚本逻辑和添加必要操作来解决,无需重启Neutron:
1. 强制实例硬重启刷新网络配置
实例添加新端口后不会自动重新加载网络栈,硬重启能让实例重新获取新端口的IP、路由等参数,解决L2连通性和FIP失效问题。在脚本末尾添加:
echo "Hard rebooting instance to apply new network config" openstack --os-cloud "$CLOUD" server reboot --hard "$INSTANCE_NAME"
2. 优化FIP解绑与端口清理流程
Neutron状态同步存在延迟,直接删除端口可能导致FIP残留关联状态。修改脚本中解绑FIP到删除端口的步骤:
echo "Disasociating floating IP" openstack --os-cloud "$CLOUD" floating ip unset "$FIP_ID" # 等待FIP完全解绑 echo "Waiting for floating IP to be disassociated..." until openstack --os-cloud "$CLOUD" floating ip show "$FIP_ID" -f value -c port_id | grep -q "^$"; do sleep 2 done echo "Removing old port from instance" openstack --os-cloud "$CLOUD" server remove port "$INSTANCE_NAME" "$PORT_ID" openstack --os-cloud "$CLOUD" port delete "$PORT_ID"
若删除实例后FIP仍显示占用,手动执行openstack floating ip unset <FIP_ID>强制解绑。
3. 复制原端口关键属性到新端口
原脚本创建新端口时未继承原端口的安全组、IP分配方式等属性,导致网络配置不匹配。修改端口创建命令:
# 获取原端口的安全组列表 OLD_SECURITY_GROUPS=$(openstack --os-cloud "$CLOUD" port show "$PORT_ID" -f value -c security_groups | tr -d '[]' | sed 's/,/ /g') echo "Creating new port in $DEST_NET..." NEW_PORT_NAME="${INSTANCE_NAME}-${DEST_NET}-port" # 创建新端口时复制安全组,若原端口用静态IP需添加--fixed-ip指定 NEW_PORT_ID=$(openstack --os-cloud "$CLOUD" port create \ --network "$DEST_NET" \ --security-group $OLD_SECURITY_GROUPS \ "$NEW_PORT_NAME" -f value -c id) echo "New port created: $NEW_PORT_ID"
如果原端口使用静态IP,需添加--fixed-ip subnet=<目标子网ID>,ip-address=<原静态IP>参数(确保目标子网有该IP可用)。
4. 添加FIP绑定后的状态验证
在绑定FIP后添加验证步骤,确保状态正常:
echo "Reassigning floating IP to port" openstack --os-cloud "$CLOUD" floating ip set --port "$NEW_PORT_ID" "$FIP_ID" # 验证FIP绑定状态 echo "Verifying floating IP association..." FIP_PORT=$(openstack --os-cloud "$CLOUD" floating ip show "$FIP_ID" -f value -c port_id) if [[ "$FIP_PORT" != "$NEW_PORT_ID" ]]; then echo "Error: Floating IP not properly associated with new port" exit 1 fi
内容的提问来源于stack exchange,提问作者Juan Cameros
相关产品推荐
相关产品推荐

