1. 项目背景与整体设计思路拆解1.1 这个插件到底解决什么问题先把这个标题拆开看。OpenStack 是目前企业私有云和运营商云里用得最广的一套开源云平台Agile Controller 是华为推出的一套园区网络与数据中心网络控制器产品而 DCN 插件则是 Agile Controller 面向数据中心网络场景提供的一个对接组件。把这三者串起来本质上要干的事情是让 OpenStack 云平台在创建虚拟机、挂载网络、迁移虚机的时候能够自动把网络策略下发到 Agile Controller 上由控制器去驱动底层物理交换机完成 VLAN、VXLAN、ACL 等配置而不是靠运维人员手工去交换机上敲命令。这个场景在传统数据中心里非常典型。以前的做法是云管平台建一个虚机运维收到工单登录交换机配 VLAN配端口配路由一套下来半小时起步还容易配错。DCN 插件要做的就是把这条链路自动化让云平台的网络动作和物理网络的动作保持一致。它解决的核心问题是云网联动——云侧的虚拟网络和物理网络之间的映射关系自动同步。适合看这篇内容的人大概有三类一是正在做 OpenStack 与华为网络设备对接的云平台运维工程师二是负责数据中心网络自动化改造的网络工程师三是做私有云集成项目、需要把控制器插件装到 OpenStack 里的实施人员。如果你只是刚接触 OpenStack连 Neutron 的基本概念都还没搞明白建议先把 Neutron 的 ML2 架构、agent 机制、provider network 这些基础过一遍再来看不然会有点吃力。1.2 为什么选择插件方式而不是手工对接这里要先说清楚一个设计层面的取舍。OpenStack 对接外部网络控制器业界大致有三条路一是走 Neutron 的 ML2 driver 机制把控制器当成一个特殊的 mechanism driver二是走 Neutron 的 service plugin 机制把控制器当成一个独立的服务插件三是干脆绕过 Neutron自己在上层写脚本调控制器的北向 API。DCN 插件走的是第一条路也就是 ML2 mechanism driver 的方式。为什么这么选因为 ML2 是 Neutron 里专门为多种网络技术共存设计的框架它把网络类型VLAN、VXLAN、GRE 等和实现机制Linux bridge、OVS、外部控制器解耦了。你把 DCN 插件注册成一个 mechanism driverNeutron 在创建网络、端口、子网的时候就会回调这个 driver 的接口插件再把信息翻译成 Agile Controller 能听懂的 REST 请求发过去。这样做的好处是不需要改动 Neutron 核心代码升级 OpenStack 版本时插件跟着升级就行坏处是插件和 Neutron 版本强绑定Neutron 的 driver 接口一变插件就得跟着改。我个人的经验是如果你的环境里物理网络设备品牌比较单一而且控制器本身提供了比较完整的北向接口走 ML2 driver 是最省事的。如果设备品牌很杂今天华为明天思科后天锐捷那可能要考虑用 Neutron 的 tap 机制或者自己写中间层做适配不然插件会写得很痛苦。1.3 整体架构与数据流向把架构画在脑子里大概是这么一条链路OpenStack 控制节点上的 Neutron Server 加载了 DCN 插件的 mechanism driver。用户在 Horizon 或者命令行创建一个网络Neutron 的 API 层收到请求经过 ML2 的 type driver 确定网络类型假设是 VLAN然后依次调用注册的 mechanism driver。DCN 插件被调用后把网络名称、VLAN ID、网段、网关这些信息组装成 JSON通过 HTTPS 发给 Agile Controller 的北向接口。控制器收到后在自己的数据库里记录这条网络并把它映射到某台物理交换机上的某个 VLAN然后通过南向协议比如 NETCONF、SNMP 或者设备私有协议把配置推到交换机。虚机创建的时候Neutron 分配端口DCN 插件把端口对应的 MAC、IP、所在网络、所在物理端口信息再发给控制器控制器据此在交换机上配置端口 VLAN 和 ACL。虚机迁移的时候插件要通知控制器更新端口位置控制器再更新交换机配置。整个链路里插件是翻译官控制器是大脑交换机是手脚。这里有个关键点插件的可靠性直接决定了云平台网络操作的成败。如果控制器挂了或者网络不通Neutron 创建网络就会卡住甚至失败。所以生产环境里控制器一般要做集群插件侧要配超时和重试还要有降级策略——比如控制器不可达时允许网络创建成功但标记为待同步等控制器恢复后再补下发。2. 安装前的环境准备与依赖梳理2.1 版本匹配是第一步也是最容易翻车的地方我见过太多人装插件失败最后发现是版本对不上。OpenStack 的版本节奏是每半年一个大版本Neutron 的 ML2 driver 接口在不同版本之间会有细微变化。Agile Controller 的 DCN 插件也是跟着 OpenStack 版本走的比如某个插件版本明确只支持 Queens 到 Train你硬装到 Ussuri 上大概率会报 import error 或者接口方法找不到。所以安装前第一件事是确认三样东西的版本OpenStack 版本看/etc/os-release或者neutron --version、Agile Controller 版本登录控制器 Web 界面看关于页面、DCN 插件版本看插件包里的 README 或者 version 文件。三者要在一个兼容矩阵里。如果拿不到官方兼容矩阵一个土办法是看插件包里的setup.cfg或者requirements.txt里面通常会写它依赖的 Neutron 版本范围。另外要注意 Python 版本。OpenStack 从 Train 开始主推 Python 3之前很多是 Python 2.7。插件如果是 Python 2 写的在 Python 3 环境里装会各种编码报错。这个坑很隐蔽因为安装过程可能不报错但运行起来处理中文字符或者特殊字符时就崩了。2.2 网络连通性与证书准备插件要和 Agile Controller 通信走的是 HTTPS。这意味着两件事网络要通证书要信。网络方面Neutron Server 所在的控制节点要能访问控制器的北向接口 IP 和端口。一般控制器北向是 443 或者自定义端口。先用curl -k https://控制器IP:端口试一下能返回东西说明网络通。如果中间有防火墙要放行。注意不要只测 pingping 通不代表 443 通。证书方面如果控制器用的是自签名证书插件默认会校验失败。有两种处理方式一是把控制器的 CA 证书导入到控制节点的信任库/etc/pki/ca-trust/source/anchors/然后update-ca-trust二是在插件配置里关掉证书校验。生产环境强烈建议用第一种第二种等于把 HTTPS 当 HTTP 用中间人攻击风险很大。我吃过亏有一次测试环境图省事关了校验结果后来上生产忘了改被安全扫描扫出来返工很麻烦。2.3 依赖包与系统参数检查插件本身通常是一个 Python 包依赖一些库比如requests、keystoneauth1、neutron-lib等。安装前先确认这些依赖的版本和 OpenStack 环境里已有的是否冲突。最稳妥的做法是在一个干净的虚拟环境里先pip install试一遍看有没有版本冲突。系统参数方面有几个要检查文件描述符限制Neutron 并发高的时候会开很多连接ulimit -n建议调到 65535。SELinux如果开着可能会阻止插件写某些目录或者发网络请求。测试阶段可以先设成 permissive生产环境再根据审计日志加策略。时间同步控制节点和控制器的时间要同步否则 HTTPS 证书校验或者 token 校验会失败。用 chrony 或者 ntp 都行偏差控制在几秒内。提示装之前先给 Neutron 的配置文件和数据库做个备份。插件安装会改 Neutron 的配置文件万一改错了还能回滚。数据库备份主要是防插件初始化时写坏表结构。3. 插件安装与核心配置实操3.1 安装插件包与注册 mechanism driver假设你已经拿到了插件包通常是个 tar.gz 或者 whl 文件。解压后进入目录用 pip 安装# 建议在 Neutron 的虚拟环境里装如果是系统包管理安装的 OpenStack直接用 root pip install ./dcn_plugin-xxx.tar.gz装完后要验证一下pip show dcn-plugin # 看 Location 和 Version 是否符合预期接下来是注册 mechanism driver。编辑 Neutron 的主配置文件一般在/etc/neutron/neutron.conf或者/etc/neutron/plugins/ml2/ml2_conf.ini取决于你的 OpenStack 发行版。找到[ml2]段在mechanism_drivers里加上插件的 driver 名称。这个名称不能瞎写要看插件文档通常是类似dcn或者agile_dcn这样的字符串。[ml2] mechanism_drivers openvswitch,l2population,dcn这里有个顺序问题。mechanism driver 是按列表顺序依次调用的。如果你的环境里同时用了 OVS 和 DCN一般把 DCN 放在后面让它做补充性的物理网络下发。但具体顺序要看插件文档有的插件要求放在特定位置放错了会导致网络创建时 driver 之间互相干扰。改完配置要重启 Neutron Serversystemctl restart neutron-server重启后看日志journalctl -u neutron-server -n 200 | grep -i dcn如果看到 driver 加载成功的日志说明注册没问题。如果报Stevedore相关的错误通常是包没装好或者 entry point 没注册上检查setup.cfg里的entry_points段。3.2 配置控制器连接参数插件自己的配置文件一般在/etc/neutron/plugins/ml2/dcn_plugin.ini或者类似路径。核心配置项大概有这些[dcn] controller_ip 192.168.1.100 controller_port 443 username openstack password 加密后的密码 protocol https verify_ssl true ca_cert /etc/neutron/dcn/ca.pem sync_interval 300 request_timeout 30 retry_times 3逐项说一下。controller_ip和controller_port是控制器北向接口地址。username和password是控制器上给 OpenStack 用的账号这个账号要有创建网络、修改端口、查询拓扑的权限。密码如果支持加密尽量用加密后的别明文写在配置文件里不然ps或者配置文件泄露就麻烦了。verify_ssl和ca_cert是证书校验相关。sync_interval是插件和控制器做全量同步的周期单位秒。这个值别设太小否则控制器压力大也别太大否则两边数据不一致的时间窗口太长。300 秒是个比较折中的值。request_timeout和retry_times是请求超时和重试次数网络抖动的时候有用。配置完先别急着重启用插件自带的工具测一下连通性。有的插件提供dcn-check之类的命令没有的话就自己写个 Python 脚本调一下控制器的登录接口import requests url https://192.168.1.100:443/rest/plat/smapp/v1/sessions data {userName: openstack, password: xxx} r requests.post(url, jsondata, verify/etc/neutron/dcn/ca.pem) print(r.status_code, r.text)返回 200 并且带 token 就说明认证通了。3.3 数据库同步与初始化插件一般需要在 Neutron 数据库里建自己的表用来记录网络和控制器侧对象的映射关系。安装包里通常有个dcn-db-manage之类的命令dcn-db-manage --config-file /etc/neutron/neutron.conf upgrade head这一步会创建表、插入初始数据。执行前确认数据库连接配置正确执行后检查表是否建好use neutron; show tables like dcn%;如果表建好了说明初始化成功。如果报错常见原因是数据库用户权限不够或者 Neutron 的数据库迁移版本和插件期望的不一致。后者比较麻烦可能需要先升级 Neutron 数据库到插件要求的版本。注意数据库迁移命令只能执行一次重复执行可能会报表已存在或者数据冲突。如果执行到一半失败了要先看失败在哪一步手动清理掉已建的表再重来别直接再跑一遍。4. 联调验证与常见问题排查4.1 从创建网络到交换机配置的端到端验证装完配置完最关键的是验证整条链路通不通。我的做法是分四步走每步都确认后再进行下一步。第一步在 OpenStack 里创建一个测试网络openstack network create test-dcn-net --provider-network-type vlan --provider-physical-network physnet1 --provider-segmentation-id 100创建完看 Neutron 日志里有没有插件调用控制器的记录。如果有说明插件被触发了。第二步登录 Agile Controller 的 Web 界面看有没有一条对应的网络记录VLAN ID 是不是 100。如果有说明插件到控制器的下发成功了。第三步登录对应的物理交换机看 VLAN 100 有没有被创建对应的端口有没有放通。如果有说明控制器到交换机的下发也成功了。第四步在这个网络里创建一台虚机看虚机能不能通网关能不能访问同网络的其他虚机。这一步验证的是数据面前面三步验证的是控制面。这四步里任何一步断了都要停下来排查别急着往下走。我见过有人第一步没确认就往下做最后虚机不通回头查发现是插件根本没触发白白浪费半天。4.2 常见问题速查表现象可能原因排查方法解决方式Neutron 启动失败日志报 driver 加载错误插件包没装好或 entry point 未注册pip show看包python -c import dcn看能否导入重装插件包检查 setup.cfg创建网络卡住最后超时失败控制器不可达或认证失败手动 curl 控制器接口看插件日志检查网络、证书、账号密码网络创建成功但控制器侧没有记录插件配置未生效或 driver 顺序不对看 Neutron 日志里 driver 调用顺序调整 mechanism_drivers 顺序重启控制器侧有记录但交换机没配置控制器到交换机南向不通登录控制器看设备管理状态检查控制器和设备之间的连接虚机不通网关数据面 VLAN 或端口配置问题在交换机上看端口 VLAN在虚机里抓包检查 provider network 映射插件日志报 SSL 证书错误证书未信任或过期openssl s_client -connect看证书导入 CA 证书或更新证书同步周期到了但数据不一致同步任务失败或部分失败看插件同步日志对比两边数据手动触发同步检查失败原因4.3 几个我踩过的坑和独家技巧第一个坑是中文网络名。有的插件在处理网络名称时没做编码转换中文名会导致发给控制器的 JSON 解析失败。解决办法是网络名统一用英文加数字别用中文。如果业务方非要中文那就在插件侧做一层转码但改插件代码有风险升级会覆盖。第二个坑是并发创建网络。Neutron 是并发处理请求的如果同时创建多个网络插件可能并发调控制器接口控制器如果没做幂等或者锁会出现数据错乱。我的做法是在插件配置里限制并发数或者让业务方错峰创建。这个在批量部署场景下特别容易出问题。第三个坑是控制器重启后的数据同步。控制器重启后内存里的状态可能丢了但数据库里还有。这时候插件如果不知道继续按老状态下发就会不一致。解决办法是插件要能感知控制器重启重启后主动做一次全量同步。有的插件版本没这个机制需要自己写个定时任务定期对比两边数据。第四个技巧是日志级别。插件默认日志级别可能是 INFO排查问题时不够。可以在插件配置里把日志级别调到 DEBUG但别长期开着DEBUG 日志量很大会把磁盘写满。排查完记得调回去。第五个技巧是灰度验证。生产环境装插件别一次性在所有控制节点上装。先在一个节点上装创建一个测试网络验证没问题再推其他节点。因为 Neutron 是多节点部署一个节点有问题可能影响整个集群的网络操作。5. 性能调优与生产环境注意事项5.1 插件性能调优的几个关键参数插件在生产环境跑性能主要受三个因素影响请求控制器的频率、单次请求的数据量、并发数。请求频率方面除了前面说的sync_interval还要注意 Neutron 本身的事件触发频率。比如批量创建 100 个端口插件就会发 100 次请求。如果控制器处理慢请求就会堆积。可以在插件侧加一个队列把请求攒一批再发但这样会增加延迟。取舍看业务对实时性的要求。数据量方面每次请求尽量只带必要字段别把整个网络的所有信息都发过去。有的插件实现得比较粗暴每次全量发网络多了之后请求体巨大传输和处理都慢。如果插件支持增量下发一定要用增量。并发数方面插件一般有个线程池或者连接池配置。线程池太小请求排队太大控制器扛不住。一般从 10 开始试观察控制器 CPU 和响应时间慢慢调。我一般会压测一下用脚本模拟 100 个并发创建网络看插件和控制器能不能在可接受时间内处理完。5.2 高可用与容灾考虑生产环境里Agile Controller 一般要做集群至少两台主备或者负载均衡。插件配置里要能配多个控制器地址一个挂了自动切另一个。有的插件支持有的不支持不支持的话就要在插件前面加个负载均衡器插件只连 VIP。Neutron Server 本身也是多节点每个节点都装了插件。这时候要注意多个插件实例同时往控制器发请求控制器要能处理并发。另外如果某个 Neutron 节点挂了它之前下发的网络状态还在控制器里新节点接管后要能同步这些状态。这个在插件设计时就要考虑一般靠定期全量同步来兜底。容灾方面最坏的情况是控制器全挂了。这时候云平台的网络操作会失败。要有降级方案比如允许网络创建成功但标记为未同步等控制器恢复后补下发。这个需要改 Neutron 的代码或者插件的逻辑实现起来有点复杂但生产环境值得做。5.3 监控与日常运维插件上线后要监控几个指标插件到控制器的请求成功率、请求延迟、同步任务的执行情况、控制器侧的网络对象数量是否和 Neutron 侧一致。请求成功率低于 99% 就要告警说明链路有问题。延迟突然升高可能是控制器负载高或者网络抖动。同步任务失败说明两边数据可能不一致要人工介入。数量不一致说明有网络创建了但没同步过去或者删除了但控制器侧没删。日常运维方面建议每周做一次全量数据对比用脚本拉两边数据比对发现不一致及时处理。另外插件和 OpenStack 升级时要先确认新版本插件兼容再升级。升级顺序一般是先升控制器再升插件最后升 OpenStack反过来容易出问题。提示插件相关的日志建议单独收集别和 Neutron 主日志混在一起。可以用 rsyslog 或者 filebeat 把插件日志打到独立的索引里排查问题时方便过滤。6. 版本升级与后续扩展思路6.1 插件升级的稳妥流程插件升级不是简单换个包重启就完事。因为插件和 Neutron 数据库、控制器数据都有耦合升级过程中要保证数据一致性。我的流程是这样的先在测试环境验证新版本插件兼容当前 OpenStack 和控制器版本验证通过后在生产环境选一个业务低峰期。升级前备份 Neutron 数据库和插件配置文件。然后停止一个控制节点的 Neutron Server升级该节点的插件启动观察日志和功能。没问题后再逐个升级其他节点。全部升级完后执行数据库迁移命令如果有。最后做一次全量同步确保两边数据一致。升级过程中如果发现新版本有问题要能快速回滚。所以升级前要把旧版本的插件包和配置文件留好回滚就是换回旧包、恢复配置、重启。6.2 后续可以扩展的方向插件装好只是第一步后面还有很多可以做的事。比如把插件的操作日志接入到云平台的审计系统这样谁在什么时候创建了什么网络、下发到哪台交换机都有记录可查。再比如把控制器的拓扑信息拉回 OpenStack在 Horizon 上展示物理网络拓扑让云平台用户能看到自己的网络在物理上是怎么走的。还可以做智能运维比如插件检测到某台交换机端口流量异常自动触发告警或者限流。这个需要插件和控制器、监控系统联动实现起来复杂但价值很高。另外如果环境里有多套 OpenStack 或者多个数据中心可以考虑插件支持多控制器、多站点把网络策略统一管理。这个对大型企业或者运营商比较有用。6.3 一些个人体会装这个插件技术本身不算特别难难的是对 OpenStack 网络模型和物理网络的理解要到位。很多人装不上或者装上了不通不是插件的问题是对 Neutron 的 provider network、tenant network、ML2 这些概念没吃透。所以我的建议是装插件之前先把 Neutron 的网络创建流程在脑子里过一遍知道每个阶段发生了什么插件在哪个阶段介入这样排查问题的时候就有方向。另外文档要看但别全信文档。文档写的都是理想情况实际环境里各种版本、各种配置、各种历史遗留问题。遇到问题多查日志多动手验证别光看文档猜。我这些年排查网络问题最有效的方法就是抓包加看日志比任何文档都管用。最后生产环境变更一定要谨慎。插件安装涉及云平台网络一旦出问题影响面很大。能灰度就灰度能回滚就准备好回滚方案别嫌麻烦。我见过太多因为变更不规范导致的故障事后复盘都是当时觉得没问题就没备份。这个教训希望你别重复。