华为eNSP模拟器STP生成树协议实战:从根桥选举到MSTP负载分担配置详解
1. 为什么要在模拟器里折腾生成树协议很多人第一次接触交换机配置都是从划分VLAN开始的。把不同端口塞进不同VLAN广播域隔离开网络看起来就通了。但只要你在拓扑里多接一根网线形成一个物理环路整个网络瞬间就会像堵死的十字路口——广播帧在环路里无限打转CPU被瞬间拉满指示灯疯狂闪烁这就是广播风暴。而生成树协议STP就是解决这个问题的核心机制它通过逻辑上阻塞冗余链路把带环的物理拓扑修剪成一棵无环的树。我之所以推荐在华为eNSP模拟器里练STP原因很实在真机上你不敢随便插网线制造环路一旦风暴起来可能影响整个办公网而在模拟器里你可以随便造环、随便拔线观察根桥选举、端口状态迁移、拓扑收敛的全过程成本为零风险为零。这篇文章就是写给那些已经会配VLAN、但对STP一知半解的网络初学者以及想系统梳理华为交换机STP配置要点的运维人员。我会从协议原理讲到eNSP实操把根桥选举、端口角色、边缘端口、BPDU保护这些关键点全部拆开揉碎让你看完就能自己搭拓扑复现。需要先说明的是STP不是一个配了就行的协议它的很多参数需要根据网络规模去调优。默认参数在小网络里能用但一旦接入设备多了、链路复杂了收敛慢、次优路径、边缘端口震荡这些问题就会冒出来。所以这篇文章不只是教你敲命令更重要的是让你理解每条命令背后的意图。2. 生成树协议的核心原理拆解2.1 STP到底在解决什么问题要理解STP先得理解二层网络的死穴。以太网帧本身没有TTL字段不像IP包那样每经过一个路由器就减一减到零就丢弃。二层帧一旦进入环路就会永远循环下去。更麻烦的是交换机对未知单播、广播、组播帧的处理方式是泛洪——从除入端口外的所有端口发出去。环路存在时一个广播帧会被反复泛洪数量呈指数级增长几秒钟就能把链路带宽和交换机CPU吃干净。STP的思路很巧妙既然物理上不能删掉冗余链路冗余是为了可靠性那就在逻辑上把某些端口堵住让数据帧只能沿一条无环路径转发。当主链路故障时再把这个被堵住的端口放开恢复连通性。这个堵住不是物理断开而是端口进入阻塞状态不转发数据帧但仍然接收并处理BPDU桥协议数据单元。华为交换机默认运行的STP模式是MSTP多生成树协议它兼容STP和RSTP并且支持基于实例的负载分担。这一点很关键很多新手以为配的是普通STP其实设备跑的是MSTP行为上有差异。2.2 根桥选举谁说了算STP收敛的第一步是选出一台根桥Root Bridge整个树的拓扑都以它为参考点。选举规则只有一条桥ID最小者胜。桥ID由两部分组成——优先级2字节加MAC地址6字节。优先级默认32768取值范围0到61440步长4096。如果优先级相同就比较MAC地址MAC小的当选。这里有个实操中很容易踩的坑华为交换机的优先级字段实际是16位但只有高4位参与比较低12位是扩展系统ID用于MSTP的实例编号。所以你敲命令时看到的是4096的倍数比如4096、8192、12288。配置根桥的标准做法是[SW1] stp root primary这条命令会把优先级自动设为0。对应的还有stp root secondary优先级设为4096。用这两条命令比手动敲stp priority 0更省事也更不容易出错。我个人的经验是核心层交换机一定要手动指定为根桥不要让它们靠默认优先级去随机选举。因为默认优先级都一样最后比MAC地址而MAC地址是出厂烧录的你根本控制不了谁大谁小。一旦根桥选错了位置流量路径就会绕远延迟增加链路利用率也不均衡。2.3 端口角色与状态迁移选完根桥每台非根交换机都要选出一个根端口Root Port也就是到根桥路径开销最小的那个端口。路径开销跟带宽有关华为默认采用IEEE 802.1t标准千兆链路开销是20000百兆是200000。每条链路上还要选出一个指定端口Designated Port负责向该网段转发BPDU。剩下的端口就是阻塞端口Alternate Port处于Discarding状态。端口状态迁移是STP收敛慢的根源。传统STP有五个状态Disabled、Blocking、Listening、Learning、Forwarding。从Blocking到Forwarding要经过Listening15秒和Learning15秒加上Max Age20秒最坏情况要50秒才能收敛。RSTP把这个过程压缩到了秒级引入了边缘端口、替代端口等概念。MSTP则在此基础上支持多实例。在eNSP里观察状态迁移特别直观。你可以用display stp brief看每个端口的角色和状态用display stp interface GigabitEthernet 0/0/1看详细计时器。我建议在拓扑收敛过程中反复敲这两条命令亲眼看着端口从Discarding变成Forwarding比看十遍书都管用。3. eNSP环境搭建与基础拓扑设计3.1 模拟器环境准备eNSP的安装本身没什么难度但有几个点必须注意。第一它依赖WinPcap、Wireshark和VirtualBox三个组件安装顺序建议先装WinPcap再装Wireshark最后装VirtualBox否则可能出现设备启动失败。第二eNSP对VirtualBox版本比较挑太新的版本反而容易出问题我实测5.2.x系列比较稳。第三启动设备前先确认VirtualBox的虚拟网卡没有冲突如果之前装过其他虚拟化软件建议先清理网络适配器。设备型号选择上练STP用S5700系列就够了它支持MSTP、RSTP命令行也跟真机一致。路由器用AR2220PC用普通的PC设备即可。这里提醒一句eNSP里的PC功能比较弱只能配IP和ping做不了复杂的抓包分析真要抓BPDU还是得靠Wireshark配合镜像端口。3.2 一个能复现所有STP现象的拓扑我设计的拓扑是这样的三台S5700交换机SW1、SW2、SW3两两互联形成一个三角形环路。SW1作为核心SW2和SW3作为接入。每台交换机下挂一台PCPC1接SW1PC2接SW2PC3接SW3。所有互联口配置为Trunk允许所有VLAN通过。IP规划上PC1用192.168.1.1/24PC2用192.168.1.2/24PC3用192.168.1.3/24都在同一个网段方便测试连通性。这个三角形拓扑的好处是它能同时展示根桥选举、根端口选择、阻塞端口产生这三个核心现象。当你把SW1设为根桥后SW2和SW3之间必然有一个端口被阻塞。然后你拔掉SW1到SW2的线观察阻塞端口如何变成转发状态就能直观理解STP的冗余切换。连线的时候有个细节eNSP里交换机的端口编号是从GigabitEthernet 0/0/1开始的别跟真机的槽位编号搞混。我习惯把互联口统一用0/0/1到0/0/4接入PC的口用0/0/10以后这样配置时不容易看花眼。3.3 基础配置与VLAN规划在配STP之前先把基础打通。三台交换机都创建VLAN 10和VLAN 20互联口配成Trunk接入PC的口划到对应VLAN。SW1的PC1划到VLAN 10SW2的PC2划到VLAN 10SW3的PC3划到VLAN 20。这样设计是为了后面演示MSTP的多实例负载分担——VLAN 10走一棵树VLAN 20走另一棵树。基础配置命令如下[SW1] vlan batch 10 20 [SW1] interface GigabitEthernet 0/0/1 [SW1-GigabitEthernet0/0/1] port link-type trunk [SW1-GigabitEthernet0/0/1] port trunk allow-pass vlan 10 20 [SW1] interface GigabitEthernet 0/0/10 [SW1-GigabitEthernet0/0/10] port link-type access [SW1-GigabitEthernet0/0/10] port default vlan 10SW2和SW3照此配置注意互联口的编号要对应实际连线。配完后用display vlan确认VLAN和端口归属用display port vlan确认Trunk口的PVID和允许列表。这一步别偷懒我见过太多人STP配了半天没效果最后发现是Trunk口没放行VLAN。4. STP配置实操全流程4.1 开启STP并指定根桥华为交换机默认全局STP是开启的但为了保险还是手动确认一下[SW1] stp enable [SW1] stp mode mstpstp mode有三个选项stp、rstp、mstp。默认是mstp但如果你之前改过记得改回来。MSTP模式下所有VLAN默认映射到实例0IST也就是所有VLAN共用一棵树。要实现负载分担需要配置MST域。指定根桥[SW1] stp root primary [SW2] stp root secondarySW1成为主根SW2成为备份根。SW3不指定让它参与选举但不当根。配完后用display stp查看你会看到SW1的CIST Root/ERPC都是0说明它就是根桥。这里有个细节值得说stp root primary本质上就是把优先级设为0stp root secondary设为4096。如果你手动敲stp priority 0效果一样但用root命令更语义化也方便后期维护时一眼看出设计意图。4.2 观察端口角色与状态配置完成后在SW2上敲[SW2] display stp brief输出会列出每个端口的MSTID、Role、State、Cost。你会看到连向SW1的端口是ROOT根端口连向SW3的端口是ALTE替代端口Discarding状态连向PC的端口是DESI指定端口Forwarding。SW3上类似连向SW1的是根端口连向SW2的是替代端口。这个结果验证了STP的核心逻辑SW2和SW3之间必然有一个端口被阻塞因为如果两个都转发SW1-SW2-SW3就形成了环路。至于阻塞哪一个取决于到根桥的路径开销。如果两条路径开销相同就比较发送者的桥ID和端口ID。我建议你在这个状态下用PC1去ping PC2和PC3应该都能通。然后拔掉SW1到SW2的线再ping一次观察丢几个包后恢复。这个丢包过程就是STP重新收敛的时间传统STP可能要几十秒MSTP会快很多。4.3 配置边缘端口加速接入接入PC的端口如果也参与STP计算每次插拔网线都要等30秒才能转发用户体验极差。解决办法是配成边缘端口[SW1] interface GigabitEthernet 0/0/10 [SW1-GigabitEthernet0/0/10] stp edged-port enable边缘端口的特点是一插上就进入Forwarding不参与生成树计算也不发送BPDU。但这里有个风险——如果边缘端口误接到另一台交换机就可能引入环路。所以华为提供了BPDU保护功能[SW1] stp bpdu-protection开启后如果边缘端口收到BPDU交换机会自动把这个端口关闭Error-Down并记录日志。这相当于给边缘端口加了一道保险。我在实际项目里所有接终端的端口都会同时配edged-port和bpdu-protection这是标准操作。4.4 MSTP多实例负载分担配置前面所有VLAN都跑在实例0上SW2和SW3之间那条被阻塞的链路完全浪费了。MSTP的价值就在于可以让不同VLAN走不同的树实现负载分担。配置思路是创建两个实例实例1映射VLAN 10实例2映射VLAN 20。然后让SW1在实例1里当根SW2在实例2里当根。这样VLAN 10的流量走SW1-SW2路径VLAN 20的流量走SW2-SW3路径两条链路都用上了。配置命令[SW1] stp region-configuration [SW1-mst-region] region-name RG1 [SW1-mst-region] instance 1 vlan 10 [SW1-mst-region] instance 2 vlan 20 [SW1-mst-region] active region-configuration三台交换机的域配置必须完全一致包括域名、实例映射、修订级别。配完后用display stp region-configuration确认。然后在实例1里指定SW1为根实例2里指定SW2为根[SW1] stp instance 1 root primary [SW2] stp instance 2 root primary配完后在SW2上display stp brief你会看到同一个物理端口在不同实例里的角色可能不同——在实例1里是替代端口在实例2里可能是指定端口。这就是MSTP的精髓物理拓扑不变逻辑拓扑按实例分化。5. 常见问题与排查技巧实录5.1 根桥选举不符合预期这是最常见的问题。现象是你明明把SW1设成了root primary但display stp显示根桥是另一台。原因通常有三个一是域配置不一致三台交换机不在同一个MST域里各自选各自的根二是优先级没生效可能被其他配置覆盖三是物理连接有问题根桥的BPDU传不过来。排查步骤先display stp region-configuration对比三台交换机的域配置确保域名、修订级别、实例映射完全一致。再display stp看CIST Root是不是SW1的桥ID。如果域配置不一致改完后必须active region-configuration激活否则不生效。5.2 端口一直处于Discarding状态如果某个端口长时间不转发先看它的角色。如果是ALTE那是正常的说明它是被阻塞的冗余端口。如果是ROOT或DESI却还在Discarding那就有问题。常见原因是链路两端STP模式不匹配比如一端是STP一端是RSTP协商会出现异常。解决办法是统一stp mode。还有一种情况是端口被BPDU保护关闭了。用display stp interface看端口状态如果是Error-Down说明它收到了BPDU。这时候要么关掉bpdu-protection要么把对端设备挪走。5.3 拓扑收敛慢ping丢包多传统STP收敛慢是协议本身决定的但你可以通过几个手段优化。第一把stp mode改成rstp或mstp收敛时间从几十秒降到秒级。第二配置边缘端口让终端接入立即转发。第三调整计时器比如把Forward Delay从15秒改成更小但这需要全网一致且不能太小以免误判。我实测下来MSTP加边缘端口拔线切换的丢包通常在3到5个ping包以内对于大多数办公网络完全够用。如果要求更高那就得上堆叠或者链路聚合了那是另一个话题。5.4 常见问题速查表问题现象可能原因排查命令解决办法根桥不是指定的设备域配置不一致或优先级未生效display stp region-configuration统一域配置并激活端口长期Discarding角色为ALTE属正常否则模式不匹配display stp interface统一STP模式边缘端口收BPDU被关闭BPDU保护触发display stp interface检查接线或关闭保护收敛慢丢包多运行传统STPdisplay stp切换MSTP并配边缘端口VLAN间负载不均衡未配MSTP多实例display stp brief配置实例映射和根桥提示每次改完STP配置养成用display stp brief和display stp interface复查的习惯。STP的问题往往不是配错而是配了没生效复查能省下大量排查时间。6. 实操心得与进阶建议6.1 我踩过的几个坑第一个坑是域配置的修订级别。MSTP的域配置里有一个revision level默认是0。如果你只改了域名和实例映射没改修订级别而其他交换机改了那它们就不在同一个域里。这个参数很隐蔽display stp region-configuration里能看到但新手经常忽略。第二个坑是Trunk口的native VLAN。如果两端native VLAN不一致BPDU可能被打了标签或者被丢弃导致STP计算异常。华为默认native VLAN是1建议保持默认或者两端显式配成一致。第三个坑是在eNSP里改配置后没保存。模拟器不像真机重启后配置全丢。练的时候无所谓但如果你想把拓扑保存下来以后复习记得在每台设备上save并且保存整个eNSP项目文件。6.2 从模拟器到真机的差异eNSP毕竟不是真机有几个差异要心里有数。第一模拟器的收敛速度比真机快因为不存在物理链路的信号延迟和硬件转发延迟所以你在模拟器里看到的秒级收敛真机上可能要多等一两秒。第二模拟器对BPDU的抓包支持有限真机上可以用镜像端口配合抓包工具分析BPDU字段模拟器里比较难。第三真机的STP默认可能不是MSTP不同厂商、不同型号默认模式不一样上线前一定要确认。6.3 后续可以扩展的方向练完基础STP可以继续深入几个方向。一是RSTP的快速收敛机制研究Proposal/Agreement握手机制理解为什么RSTP能秒级收敛。二是MSTP与VRRP联动实现网关冗余和负载分担这是园区网的标准架构。三是STP安全特性包括根保护root protection、环路保护loop protection、TC-BPDU攻击防护这些在生产网里都是必配的。我个人觉得STP这个协议最值得花时间的地方不是配置命令而是故障场景下的行为分析。比如根桥宕机后备份根多久接管阻塞端口多久变转发TC拓扑变更通知如何泛洪。这些行为在模拟器里都能复现多拔几次线、多看几次日志比背命令有用得多。最后分享一个小技巧在eNSP里做STP实验时把Wireshark挂在互联链路上过滤stp协议你能看到BPDU的完整字段——根桥ID、路径开销、端口ID、计时器。对照着协议原理看这些字段很多之前想不通的问题会豁然开朗。这个习惯我从学STP的第一天保持到现在每次遇到奇怪的收敛问题抓个包基本就能定位。

相关新闻

递归下降分析器的本质:LL(1)预测表的硬编码实现

递归下降分析器的本质:LL(1)预测表的硬编码实现

简介:本资源是面向计算机专业本科生与编译原理初学者的实验教学材料,聚焦自上而下的语法分析核心实践——递归下降分析器的设计与实现。内容涵盖LL(1)文法改造(含左递归消除)、FIRST/FOLLOW集手工推导与验证、词法分析器扩展&…

2026/10/17 21:46:49 阅读更多 →
MySQL备份方案详解:mysqldump+binlog全量增量恢复实战

MySQL备份方案详解:mysqldump+binlog全量增量恢复实战

做数据库运维的人,没有谁没被“备份”这两个字教育过。每次看到有人在群里问“数据还能不能找回来”,我第一反应都是:先看看你们 binlog 开没开。mysqldump 加 binlog 这套组合,是绝大多数 MySQL 实例都能用到的基本备份方案——全…

2026/10/17 21:46:49 阅读更多 →
多核缓存一致性基石:写策略、MESI协议与伪共享实战

多核缓存一致性基石:写策略、MESI协议与伪共享实战

上一篇把Cache的基本组织、读命中与缺失的路径都梳理了一遍,这篇继续往下走,聊写路径和一致性协议MESI。很多初学者在这里会明显感觉到难度上了一个台阶:读路径再复杂,核心问题无非是“数据在不在Cache里、从哪一层取”&#xff1…

2026/10/17 21:46:49 阅读更多 →

最新新闻

加载结果数据的工程化指南:从异步分页到弱网优化

加载结果数据的工程化指南:从异步分页到弱网优化

1. 从一句“加载结果数据”说起的真实场景如果你在代码仓库里翻到一个只有“加载结果数据”六个字的提交记录,第一反应大概率是困惑。这也太模糊了。可真正做过数据处理或者后台管理系统的人都会心一笑——这六个字背后,往往藏着一整套“从数据源取数&am…

2026/10/17 23:29:26 阅读更多 →
Unity URP Bloom后处理全解析:从原理到手写RenderFeature

Unity URP Bloom后处理全解析:从原理到手写RenderFeature

做渲染效果的时候,Bloom(泛光)大概是最容易快速提升画面质感的一项。低强度模式下,它能让霓虹灯、屏幕反光、金属高光边缘柔化出一圈渐变光晕;高强度模式下,又能把普通灯具变成那种梦幻的“发光体”。在 Un…

2026/10/17 23:29:26 阅读更多 →
Cocos2d-x LuaJIT二进制库链接避坑指南

Cocos2d-x LuaJIT二进制库链接避坑指南

简介:本资源是专为Cocos2d-x iOS平台开发者提供的libluajit.a兼容性修复库,聚焦解决cocos2d-x在iPhone 5S及更高型号设备上因LuaJIT架构不匹配导致的lua_open()调用崩溃问题。适用于中高级移动游戏开发工程师,尤其在使用旧版cocos2d-x集成Lua…

2026/10/17 23:29:26 阅读更多 →
大数据技术原理与应用测试题考点全解析与三轮复习法

大数据技术原理与应用测试题考点全解析与三轮复习法

简介:这套《大数据技术原理应用》测试题以docx文档形式整理,面向高校大数据专业学生、课程备考者及自学爱好者,用于系统检验大数据基础理论、关键技术与应用框架的掌握程度。文档共58页,包内仅1个文件,整体大小76KB&am…

2026/10/17 23:29:26 阅读更多 →
mmdetection模型解析:从配置文件到检测框的完整拆解

mmdetection模型解析:从配置文件到检测框的完整拆解

1. 从配置文件到检测框:mmdetection模型解析到底在解析什么刚接触mmdetection的人,十有八九会被它那套配置文件体系绕晕。打开一个configs/目录下的py文件,里面嵌套着model、data、schedule、runtime好几层字典,每个字典里又套着b…

2026/10/17 23:29:26 阅读更多 →
Oracle基金交易平台实战:七张表设计+PL/SQL全流程开发

Oracle基金交易平台实战:七张表设计+PL/SQL全流程开发

简介:面向Oracle数据库学习者的项目实战文档,聚焦基金交易平台的数据库设计,适合正在准备项目实训或课程设计的开发人员。文档以招商银行某分行的开放式基金交易系统为业务背景,先梳理基金管理、客户账户管理、交易审核等核心功能…

2026/10/17 23:28:25 阅读更多 →

日新闻

DeepSeek选型与部署:V3/R1、Ollama、API全攻略

DeepSeek选型与部署:V3/R1、Ollama、API全攻略

简介:《DeepSeek使用方法.pdf》是一份面向DeepSeek入门及进阶用户的完整使用指南,重点围绕V3与R1两款模型的能力差异与适用场景展开,帮助读者根据任务类型与成本选择合适的模型。资源共1个PDF文件,压缩包大小约311KB,篇…

2026/10/17 0:00:25 阅读更多 →
200+Deepseek润色指令拆解:从底层原理到场景落地的完整指南

200+Deepseek润色指令拆解:从底层原理到场景落地的完整指南

简介:这是一份聚焦DeepSeek提示词优化的《200Deepseek润色指令》PDF文档,共收录两百余条可直接套用的润色指令,涵盖语法修正、风格统一、逻辑梳理、表达精炼等维度,并针对商务写作、学术论文、广告文案等场景给出差异化建议。文档…

2026/10/17 0:00:25 阅读更多 →
OpenCV轮廓法物体计数系统:轻量、可控、可落地的工业级实现

OpenCV轮廓法物体计数系统:轻量、可控、可落地的工业级实现

简介:本资源是一份基于OpenCV的本科课程设计完整报告,面向计算机视觉初学者、图像处理学习者及高校通信/信息类专业学生,解决物体智能计数与检测结果结构化记录的实际问题。项目覆盖图像预处理、轮廓检测、边界框绘制、轨迹栏交互式参数调节、…

2026/10/17 0:00:25 阅读更多 →

周新闻

流感时间序列预测实战:ARIMA/LSTM全流程拆解与避坑指南

流感时间序列预测实战:ARIMA/LSTM全流程拆解与避坑指南

简介:基于 ARIMA、LSTM、Transformer 等模型的流感时间序列预测 Python 源码,面向计算机相关专业课程设计与期末大作业学生,以及项目实战学习者。内容覆盖预处理、平稳性检验、定阶、残差分析、多模型对比预测的完整时序建模流程,…

2026/10/16 21:35:51 阅读更多 →
影刀RPA新手教程:键盘模拟输入实战——输入文本与模拟按键的区别

影刀RPA新手教程:键盘模拟输入实战——输入文本与模拟按键的区别

影刀RPA新手教程:键盘模拟输入实战——输入文本与模拟按键的区别 做影刀RPA自动化,十个新手有八个栽在"往输入框里填东西"这件事上:要么填不进去,要么填了一半,要么直接把原来内容追加在后面。这背后的根因&…

2026/10/17 1:44:59 阅读更多 →
影刀RPA新手教程:阅文起点小说数据采集实战——书籍信息与章节内容

影刀RPA新手教程:阅文起点小说数据采集实战——书籍信息与章节内容

影刀RPA新手教程:阅文起点小说数据采集实战——书籍信息与章节内容 1. 认识影刀:什么场景该用RPA采小说数据 起点中文网的页面结构相对稳定——分类榜单、书籍详情、章节内容三块独立页面,跳转链路清晰。这种场景非常适合影刀自动化&#x…

2026/10/16 15:04:24 阅读更多 →

月新闻

我发现了一个新思路:用 Remotion + Claude Code 像写代码一样自动化生成短视频

我发现了一个新思路:用 Remotion + Claude Code 像写代码一样自动化生成短视频

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

2026/10/16 21:54:38 阅读更多 →
Windows下 Codex 中 Chrome 和 Computer Use 插件不可用问题排查及解决参考方式:TaoToken 统一 Key 配置与验证

Windows下 Codex 中 Chrome 和 Computer Use 插件不可用问题排查及解决参考方式:TaoToken 统一 Key 配置与验证

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

2026/10/17 17:22:31 阅读更多 →
黑夜航拍船只数据集训练YOLOV5模型全流程解析

黑夜航拍船只数据集训练YOLOV5模型全流程解析

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

2026/10/16 14:23:36 阅读更多 →