OpenStack Nova安装配置实战:从依赖排查到服务启动

📅 2026/7/9 23:21:24 👁️ 阅读次数 📝 编程学习
OpenStack Nova安装配置实战:从依赖排查到服务启动

1. Nova不是“另一个VSCode插件”,而是OpenStack的计算服务核心

很多人第一次看到“Nova安装及配置”这个标题,下意识会联想到VSCode里那个叫Codex或Claude Code的AI编程插件——毕竟搜索热词里“codex安装”“claude code安装”“vscode配置python”高居不下。但这里说的Nova,和代码编辑器、AI助手、本地开发环境完全无关。它属于另一个技术宇宙:云基础设施层

Nova是OpenStack项目中负责虚拟机全生命周期管理的服务模块,全称是OpenStack Compute Service。你可以把它理解成云平台的“CPU调度中枢”:用户点一下“创建实例”,背后是Nova接收请求、调用底层Hypervisor(如KVM)、分配CPU/内存/磁盘、挂载网络、注入密钥、启动虚拟机——整套动作由Nova协调完成。它不直接操作硬件,但所有计算资源的申请、调度、释放都必须经过它的API网关。

为什么现在还有人要亲手安装配置Nova?因为两类人绕不开它:一类是高校云计算课程的实训学生,课程设计明确要求在Ubuntu 22.04或CentOS 7虚拟机上从源码或包管理器部署完整OpenStack最小集群;另一类是中小企业的IT运维工程师,需要在私有化环境中快速验证云能力,又不愿采购商业云管平台。他们面对的不是“点下一步”的图形向导,而是几十个配置文件、上百行命令、服务间环环相扣的依赖链。

我带过三届云计算方向的实训班,发现一个高频误区:学生常把Nova当成一个独立可运行的二进制程序,像安装Python或MySQL那样执行apt install nova-api就以为完事了。结果服务起不来,日志里满屏ConnectionRefusedError: [Errno 111] Connection refused,却不知道这错误根本不是Nova自己的问题,而是它依赖的RabbitMQ没通、MySQL库没建、Keystone认证端点没注册导致的连锁反应。Nova从来不是单点,它是齿轮组里最显眼的那个齿轮,但咬合的每一个齿都来自其他服务。

所以这篇内容不讲“如何三分钟装好Nova”,而是带你亲手拧紧每一颗螺丝:从底层数据库选型依据、消息队列的连接池参数怎么调、Keystone服务注册的字段含义,到nova.conf[DEFAULT]段37个关键参数中哪些绝对不能改、哪些改了必崩、哪些改了能提效30%。所有操作基于真实实验室环境复现——Ubuntu 22.04 + OpenStack Yoga版本,全程无Docker封装,不跳过任何报错排查步骤。如果你正对着终端里红色的ERROR发呆,这篇就是为你写的。

2. 环境准备不是“装几个包”,而是构建可信的基础设施信任链

实训项目里最容易被跳过的环节,恰恰是后续所有故障的根源:环境初始化。很多学生直接sudo apt update && sudo apt install -y python3-pip,然后兴冲冲去装nova,结果卡在pip install pbr报SSL证书错误,或者mysql_secure_installation时输错root密码导致后续所有数据库操作失败。这不是手速问题,而是对“信任链”的认知缺失。

OpenStack服务间通信建立在三层信任基础上:操作系统级信任(用户权限、SELinux/AppArmor策略)、网络级信任(防火墙规则、端口开放、主机名解析)、服务级信任(TLS证书、数据库密码、消息队列凭证)。漏掉任何一层,Nova就像没有地基的楼。

2.1 操作系统级:Ubuntu 22.04的隐藏陷阱

Ubuntu 22.04默认启用systemd-resolved作为DNS解析器,其监听在127.0.0.53:53,而OpenStack服务(尤其是neutron)的某些组件会因glibc版本差异与该服务冲突,导致getaddrinfo()调用超时。这不是Nova的bug,但会让nova-manage db sync卡住10分钟无响应。

解决方案不是关掉systemd-resolved(会影响系统其他服务),而是强制所有OpenStack服务使用传统/etc/resolv.conf

sudo ln -sf /run/systemd/resolve/stub-resolv.conf /etc/resolv.conf sudo systemctl restart systemd-resolved

同时检查/etc/hosts是否包含本机完整FQDN映射:

# 必须存在这一行,且hostname输出与之匹配 127.0.0.1 localhost 192.168.100.10 controller.controller.local controller # 这里的controller必须和hostname命令输出一致

提示:执行hostname -f必须返回controller.controller.local,否则Keystone注册服务时会因主机名不匹配拒绝请求。这是我在第7次实训中才定位到的坑——前6次都以为是数据库权限问题。

2.2 网络级:防火墙规则的精确外科手术

学生常犯的错误是直接ufw disable一了百了。但生产环境严禁如此。Nova需要开放的端口远不止文档写的8774(API端口):

端口协议服务关键性误关后果
3306TCPMySQL★★★★★nova-manage db sync直接失败,报pymysql.err.OperationalError: (2003, "Can't connect to MySQL server")
5672TCPRabbitMQ★★★★★所有服务启动后立即崩溃,日志显示AMQP connection failed
35357/5000TCPKeystone★★★★☆Nova无法获取token,API请求全部返回401 Unauthorized
9292TCPGlance★★★☆☆创建实例时镜像下载失败,报Image not found
8774TCPNova API★★★★★外部无法调用API,但内部服务仍可运行

正确做法是逐条添加:

sudo ufw allow proto tcp from 192.168.100.0/24 to any port 3306 sudo ufw allow proto tcp from 192.168.100.0/24 to any port 5672 sudo ufw allow proto tcp from 192.168.100.0/24 to any port 35357 sudo ufw allow 8774 sudo ufw status verbose # 务必验证规则已生效

2.3 服务级:数据库与消息队列的“强一致性”初始化

Nova依赖MySQL存储实例元数据、配额、宿主机状态等。但很多教程只写CREATE DATABASE nova_api;,忽略三个致命细节:

  1. 字符集必须为utf8mb4:OpenStack Yoga版本开始强制要求,否则插入中文镜像名或长UUID时会截断;
  2. 用户权限必须细化到库级别GRANT ALL PRIVILEGES ON nova_api.* TO 'nova'@'localhost'中的localhost必须与实际连接IP匹配,若Nova服务运行在192.168.100.10,则需'nova'@'192.168.100.10'
  3. 密码强度策略:MySQL 8.0+默认启用validate_password插件,nova密码若含连续数字(如nova123)会被拒绝。

实操命令(以MySQL 8.0为例):

-- 临时关闭密码策略(仅实训环境) SET GLOBAL validate_password.policy=LOW; SET GLOBAL validate_password.length=4; -- 创建库并指定字符集 CREATE DATABASE nova_api CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci; CREATE DATABASE nova CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci; CREATE DATABASE nova_cell0 CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci; -- 创建用户(注意@后的IP必须与Nova服务所在主机IP一致) CREATE USER 'nova'@'192.168.100.10' IDENTIFIED BY 'NOVA_DBPASS'; GRANT ALL PRIVILEGES ON nova_api.* TO 'nova'@'192.168.100.10'; GRANT ALL PRIVILEGES ON nova.* TO 'nova'@'192.168.100.10'; GRANT ALL PRIVILEGES ON nova_cell0.* TO 'nova'@'192.168.100.10'; FLUSH PRIVILEGES;

RabbitMQ同理,不能只建vhost,必须绑定用户权限:

# 创建vhost sudo rabbitmqctl add_vhost /openstack # 创建用户 sudo rabbitmqctl add_user openstack RABBIT_PASS # 设置权限(读/写/配置) sudo rabbitmqctl set_permissions -p /openstack openstack ".*" ".*" ".*"

注意:RABBIT_PASS必须与后续nova.confrabbit_password值完全一致,且不能含特殊字符/@,否则URL解析失败。我曾因密码设为openstack@2024导致nova-scheduler反复重启,日志只显示AMQP connection failed,排查3小时才发现是@被解析为URL分隔符。

3. Keystone服务注册:Nova的“身份证申领流程”

Nova不是独立存在的服务,它必须先在Keystone(OpenStack的身份认证服务)中注册自己,才能获得合法“身份”。这步常被简化为一句“运行openstack service create --name nova ...”,但背后的字段逻辑决定整个云平台能否运转。

Keystone中每个服务实体包含三个核心对象:Service(服务类型)、Endpoint(访问端点)、User(服务账户)。Nova需要注册两个Service:compute(计算服务)和placement(资源提供者服务),后者在Yoga版本后成为硬性依赖。

3.1 Service注册:类型与名称的语义陷阱

执行以下命令注册Compute服务:

openstack service create --name nova --description "OpenStack Compute" compute

注意--name nova不是随意命名,它将成为后续Endpoint URL的路径前缀。例如API端点URL为http://controller:8774/v2.1,其中v2.1前的路径由Keystone动态拼接,而nova就是拼接依据。如果误写为--name openstack-nova,则所有客户端SDK(如python-openstackclient)将无法识别服务,报错No service with a type, name or alias of 'nova'

Placement服务同理:

openstack service create --name placement --description "Placement API" placement

这里--name placement必须小写,且与Nova配置文件中[placement]段的os_region_name值严格一致,否则Nova启动时会因无法连接Placement服务而退出。

3.2 Endpoint注册:public/internal/admin三端点的本质区别

Keystone要求为每个Service注册三种Endpoint:

  • public:供外部用户(如Horizon界面、curl命令)调用;
  • internal:供OpenStack内部服务(如Neutron调用Nova获取实例网络信息)调用;
  • admin:供管理员操作(如nova-manage命令)调用。

三者URL结构相同,但域名/IP不同:

# public端点(假设外部用户通过controller.openstack域访问) openstack endpoint create --region RegionOne compute public http://controller.openstack:8774/v2.1 # internal端点(内部服务走内网IP) openstack endpoint create --region RegionOne compute internal http://192.168.100.10:8774/v2.1 # admin端点(管理员工具直连) openstack endpoint create --region RegionOne compute admin http://192.168.100.10:8774/v2.1

关键点在于:controller.openstack必须能在外部DNS解析,而192.168.100.10必须是控制器节点的真实内网IP。若填错,比如internal端点用了localhost,则Neutron服务将无法与Nova通信,创建实例时网络配置永远卡在building状态。

3.3 User与Role绑定:最小权限原则的落地

Nova服务自身需要一个Keystone用户来代表自己进行API调用(如向Placement上报资源用量)。创建用户后,必须赋予service角色:

openstack user create --domain default --password NOVA_PASS nova openstack role add --project service --user nova service

这里--project service指定了用户所属项目,而service角色是Keystone预置的特殊角色,专用于服务间调用。若误用admin角色,虽能运行但违反安全规范;若忘记role add,则Nova服务启动后立即报错:

ERROR nova.service: Failed to discover available identity versions when contacting http://controller:35357/v3. Attempting to parse version catalog from URL. ... keystoneauth1.exceptions.auth_plugins.MissingAuthPlugin: No auth plugin configured

这是因为Nova尝试用nova用户凭据连接Keystone,但该用户未被授权任何角色,Keystone拒绝返回token。

4. nova.conf核心参数解剖:37个选项里哪些是“命门”

/etc/nova/nova.conf是Nova的“大脑”,共37个配置段(Yoga版本),但90%的故障集中在5个段落的12个参数。盲目修改会导致服务无法启动、实例无法调度、资源上报失败等深层问题。下面逐个拆解这些“命门参数”。

4.1 [DEFAULT]段:全局行为的隐形开关

此段控制Nova整体行为,看似通用,实则处处是坑:

  • transport_url = rabbit://openstack:RABBIT_PASS@controller:5672/openstack
    致命点RABBIT_PASS必须与RabbitMQ创建用户时密码完全一致;controller必须能被DNS解析(ping controller需通);末尾/openstack必须与RabbitMQ vhost名称一致。漏掉斜杠或大小写错误,服务启动即崩溃。

  • my_ip = 192.168.100.10
    易错点:这不是本机任意IP,而是Nova服务监听的IP。若服务器有多个网卡(如eth0=192.168.100.10, eth1=10.0.0.10),必须设为提供API服务的网卡IP。设错则nova-api监听在错误接口,外部curl超时。

  • use_neutron = true
    依赖点:必须为true,否则Nova使用已废弃的nova-network,无法与现代Neutron集成。设为false会导致创建实例时网络配置失败,日志出现NetworkManager is not configured

  • firewall_driver = nova.virt.firewall.NoopFirewallDriver
    安全权衡:实训环境为简化可设为Noop(禁用防火墙),但生产环境必须用IptablesFirewallDriver。若在生产环境误设,所有实例将暴露在公网。

4.2 [api_database]与[database]段:双库架构的协同逻辑

Nova采用双数据库设计:

  • api_database:存储API层面的轻量数据(如配额、聚合、服务状态);
  • database:存储核心实例数据(如instance_uuid、host、power_state)。

两者连接字符串格式相同,但库名不同:

[api_database] connection = mysql+pymysql://nova:NOVA_DBPASS@controller/nova_api [database] connection = mysql+pymysql://nova:NOVA_DBPASS@controller/nova

关键校验:执行nova-manage api_db syncnova-manage db sync必须成功,且顺序不能颠倒。若先执行db sync,会因nova_api库不存在报错;若api_db sync失败,nova-conductor服务无法启动。

4.3 [placement]段:资源调度的神经中枢

Yoga版本后,Placement服务成为Nova调度决策的核心。此段配置错误将导致实例永远处于scheduling状态:

[placement] os_auth_url = http://controller:5000/v3 os_username = placement os_password = PLACEMENT_PASS os_project_name = service os_user_domain_name = Default os_project_domain_name = Default os_identity_api_version = 3 region_name = RegionOne

血泪教训os_password必须与Keystone中placement用户的密码一致;region_name必须与Endpoint注册时的--region值完全相同(大小写敏感);os_auth_url末尾必须带/v3,少一个字符就返回404 Not Found

4.4 [glance]段:镜像服务的“信任状”

Nova从Glance拉取镜像,但不直接连Glance数据库,而是通过API。因此需配置认证信息:

[glance] api_servers = http://controller:9292 auth_type = password username = glance password = GLANCE_PASS project_name = service user_domain_name = Default project_domain_name = Default

隐蔽风险api_servers必须是Glance的API地址,而非数据库地址;若Glance启用了TLS,此处需改为https://controller:9292并配置cafile参数,否则连接被拒绝。

4.5 [libvirt]段:虚拟化引擎的性能命脉

此段直接影响实例启动速度和稳定性:

[libvirt] virt_type = qemu cpu_mode = none disk_cachemodes = "file=directsync,block=directsync"
  • virt_type = qemu:实训环境用纯软件模拟,生产环境应为kvm(需CPU支持VT-x/AMD-V);
  • cpu_mode = none:禁用CPU特性透传,避免跨物理机迁移失败;
  • disk_cachemodesdirectsync模式确保数据写入磁盘后再返回,牺牲性能换数据安全。若设为unsafe,实例崩溃时磁盘镜像可能损坏。

实测对比:同一台服务器,directsync下启动CentOS实例耗时23秒,unsafe模式下仅8秒,但三次压力测试后出现一次镜像文件系统损坏。实训环境建议宁慢勿错。

5. 服务启动与故障排查:从日志红字到定位根因的完整链路

当执行sudo systemctl start nova-api后看到Active: active (running),不代表一切正常。Nova由7个核心服务组成,必须全部就绪才能创建实例。以下是标准启动顺序与排错路径:

5.1 启动顺序:服务间的强依赖关系

Nova服务有严格启动依赖链,必须按序启动:

  1. nova-api:提供REST API入口;
  2. nova-scheduler:接收API请求,选择合适计算节点;
  3. nova-conductor:作为数据库代理,避免计算节点直连DB;
  4. nova-novncproxy:提供VNC控制台访问(可选,但实训必备);
  5. nova-compute:运行在计算节点,真正启动KVM虚拟机(实训中常与controller合一)。

若跳过nova-conductor直接启nova-compute,后者会因无法连接数据库而崩溃。启动命令必须带--no-block参数避免卡死:

sudo systemctl enable --now nova-api nova-scheduler nova-conductor nova-novncproxy sudo systemctl start nova-compute # 此服务需单独启动,因依赖libvirt

5.2 日志分析:读懂红字背后的三层含义

Nova日志位于/var/log/nova/,每个服务有独立日志文件。遇到错误,先看nova-api.lognova-scheduler.log,它们最先暴露问题。

典型错误模式与根因定位

日志红字片段表面现象实际层级排查路径
ConnectionRefusedError: [Errno 111] Connection refused服务无法连接某地址网络层telnet controller 3306→ 若不通,查防火墙/MySQL服务状态;telnet controller 5672→ 查RabbitMQ状态
keystoneauth1.exceptions.auth_plugins.MissingAuthPlugin认证失败Keystone层openstack token issue --os-auth-url http://controller:5000/v3 --os-project-name admin --os-username admin --os-password ADMIN_PASS→ 若失败,查Keystone服务状态及用户密码
No module named 'oslo_db'Python模块缺失环境层`pip3 list
Failed to bind port网络端口占用系统层sudo ss -tuln | grep :8774→ 若被占用,sudo lsof -i :8774查进程并kill

5.3 实例创建全流程跟踪:从curl到KVM的12个关键节点

当执行openstack server create --image cirros --flavor m1.tiny --network provider --security-group default test-instance后,可通过以下命令跟踪全流程:

  1. API层tail -f /var/log/nova/nova-api.log \| grep "test-instance"
    查看是否收到请求,记录request_id(如req-abc123

  2. Scheduler层tail -f /var/log/nova/nova-scheduler.log \| grep "req-abc123"
    查看是否选出主机,若无输出,说明Scheduler未收到请求或过滤失败

  3. Conductor层tail -f /var/log/nova/nova-conductor.log \| grep "req-abc123"
    查看是否生成实例记录,若报DBDeadlock,说明数据库锁冲突

  4. Compute层tail -f /var/log/nova/nova-compute.log \| grep "req-abc123"
    查看是否调用libvirt,若出现libvirtError: internal error: process exited while connecting to monitor,说明KVM未启用或CPU不支持

  5. Libvirt层sudo virsh list --all
    若列表中无instance-00000001,说明KVM未启动;执行sudo systemctl status libvirtd确认服务状态

  6. 实例层sudo virsh console instance-00000001
    进入虚拟机控制台,观察启动日志,确认是否卡在DHCP获取IP阶段(此时需查Neutron配置)

我在实训中总结出“三分钟定位法”:当实例卡在scheduling状态,立即执行三步:①nova service-list查所有服务状态;②nova-status upgrade check查数据库同步状态;③openstack endpoint list \| grep compute查Endpoint是否注册。80%的问题在这三步内暴露。

6. 验证与压测:让Nova真正“扛住”你的第一个实例

安装配置完成不等于可用。必须通过四层验证:功能验证、性能验证、边界验证、灾备验证

6.1 功能验证:从API到控制台的端到端贯通

执行以下命令链,任一环节失败即说明配置未闭环:

# 1. 列出可用镜像(验证Glance集成) openstack image list # 2. 列出可用规格(验证Flavor定义) openstack flavor list # 3. 创建实例(触发全链路) openstack server create --image cirros --flavor m1.tiny --network provider --security-group default test-01 # 4. 查看实例状态(等待变为ACTIVE) openstack server list --name test-01 # 5. 获取VNC链接(验证novncproxy) openstack console url show test-01 # 6. 通过浏览器打开VNC链接,登录cirros(默认账号:cirros,密码:cubswin:))

若第4步长时间显示BUILD,执行nova show test-01查看fault字段;若为空,说明问题在调度层;若有内容,复制message字段搜索OpenStack官方文档。

6.2 性能验证:量化Nova的调度吞吐能力

实训环境常忽略性能基线。用nova boot命令批量创建10个实例,记录时间:

for i in {1..10}; do openstack server create --image cirros --flavor m1.tiny --network provider --security-group default test-$i & done wait

正常情况(Ubuntu 22.04 + 8核16G)应在90秒内全部进入ACTIVE状态。若超时,检查:

  • nova-scheduler.logFilterScheduler_schedule方法耗时;
  • top命令查看nova-scheduler进程CPU占用率,若持续>90%,需调大[DEFAULT] scheduler_max_attempts参数;
  • mysqladmin processlist查数据库慢查询,优化nova.instances表索引。

6.3 边界验证:测试配置的鲁棒性

故意制造异常场景,检验系统容错能力:

  • 网络中断测试sudo systemctl stop rabbitmq-server,观察Nova服务是否自动重连(需[DEFAULT] rabbit_retry_interval> 0);
  • 数据库故障测试sudo systemctl stop mysql,再执行openstack server list,应返回503 Service Unavailable而非崩溃;
  • 资源超限测试:创建超过quota限制的实例,验证是否返回403 Forbidden及准确错误信息。

6.4 灾备验证:配置备份与快速恢复

Nova配置的生命线是/etc/nova/nova.conf和数据库。每日备份脚本示例:

#!/bin/bash # backup_nova.sh DATE=$(date +%Y%m%d) sudo cp /etc/nova/nova.conf /backup/nova.conf.$DATE mysqldump -h controller -u nova -pNOVA_DBPASS nova > /backup/nova_db.$DATE.sql mysqldump -h controller -u nova -pNOVA_DBPASS nova_api > /backup/nova_api_db.$DATE.sql # 保留最近7天 find /backup -name "nova.conf.*" -mtime +7 -delete

恢复时先还原数据库,再覆盖配置文件,最后重启服务。切记:nova-manage db sync必须在数据库还原后执行,否则表结构不匹配。

最后分享一个硬核技巧:当nova-compute服务反复崩溃,且日志显示libvirtError: cannot connect to '/var/run/libvirt/libvirt-sock',不要急着重装libvirt。执行sudo usermod -a -G libvirtd nova将nova用户加入libvirtd组,再sudo systemctl restart libvirtd即可。这是Ubuntu 22.04的默认权限策略导致的,官方文档从未提及,却是实训中最常见的“玄学故障”。