弹霄博科

小谈谈一亩三分地



RouterOS v7 路由过滤器学习笔记


发布日期: 2026/03/08
作者: 小谈谈
分类: RouterOS
标签: RouterOS, BGP, 路由, 网络工程
阅读时间: 12 分钟
字数: 3185 字


RouterOS v7 中 routing filter(路由过滤器) 的工作方式、语法结构、匹配属性、可执行动作、社区匹配、AS-PATH 正则、RPKI 与选择规则与 RouterOS v6 中存在较大的差异,本文整理通过 ChatGPT 5.4 Thinking 模型对这部分内容进行了整理。[1][2]

注意:该内容由人工智能(ChatGPT 5.4 Thinking 模型)进行生成。


RouterOS v7 的路由过滤器已经从 v6 那种偏“参数式”的风格,演进成一套更接近策略脚本语言的模型。其基本形式为:

```
if ( [matchers] ) { [actions] } else { [actions] }
```

过滤器规则不再只是简单的“匹配一个条件然后设置一个值”,而是支持布尔表达式、属性修改、跳转子链、返回父链、追加或删除 communities 等完整流程控制。[2]

对实际使用来说,最重要的理解是:

  • 先匹配,再执行动作
  • 并不是所有属性都能修改,有些属性只能用于匹配;
  • 过滤链默认动作为 reject,没有显式 accept 的路由最终会被拒绝;
  • 社区、扩展社区、大社区在 v7 中都有统一的匹配与修改机制;
  • AS-PATH 正则在 v7 中语义已经变化,不能直接照搬 v6/Cisco 写法。[1][2]
  • v6 到 v7 的核心变化

    协议配置结构变化

    在 BGP 方面,ROS v7 不再沿用 ROS v6 的 instance / peer 模型,而是重构为 connectiontemplatesession 三部分。官方说明,这样做是为了将“连接相关参数”和“BGP 协议本身参数”明确分离,使配置结构更清晰。[1]

    同时,v7 中很多原本分散的路由策略控制,也被统一到新的 /routing filter 框架里。BGP 会通过 input.filter-chainoutput.filter-chain 等方式将策略链挂接到会话输入与输出过程上。[1]

    routing filter 的职责增强

    在 OSPF 示例中,官方明确说明虽然 redistribution knob 在后续版本中回来了,但如果需要进一步控制哪些路由能被引入、以及修改 metric/type 等属性,仍然要使用 routing filter。[1]

    这意味着在 ROS v7 中,协议负责挂载过滤器,过滤器负责做细粒度策略决策。[1]

    v7 过滤器的执行模型

    规则是脚本字符串

    官方示例展示,v7 的过滤器规则是通过 rule="..." 的形式编写在字符串中的,例如:

    ```
    /routing filter rule
    add chain=myChain \
    rule="if (dst in 192.168.1.0/24 && dst-len>24) {set distance +1; accept} else {set distance -1; accept}"
    ```

    也就是说,规则本身是一段脚本,内部包含:

    链默认拒绝

    官方在 v6→v7 迁移文档中明确强调:routing filter chain 的默认动作是 reject。[1]

    这点非常关键。实际效果是:如果一条路由走完整条链都没有遇到 accept,那么即使没有显式写 reject,它最终也不会被接受。[1][2]

    accept / reject / jump / return

    官方文档列出的主要控制动作包括:

    它们分别用于: 因此,复杂策略推荐拆成“主链 + 子链”的结构,而不是写成一条很长的 if 语句。[2]

    属性分类:只读与可读写

    官方明确将路由过滤属性分为两类:[2]

    只读属性

    只能用于匹配,不允许修改。常见如:

    这些属性适合出现在 if (...) 里作为判断条件。[2]

    可读写属性

    既能匹配,也能通过 setappendunset 等动作修改。常见如:

    这类属性通常用于 BGP 策略控制、出口打社区、调整本地优先级、修改下一跳等场景。[2]

    常用匹配语法

    基本判断

    官方示例表明,v7 支持布尔表达式与比较操作,例如:

    ```
    if ( protocol connected ) { accept }
    if ( bgp-med < 30 ) { accept }
    if ( ospf-dn ) { reject }
    ```

    这说明:

    前缀匹配与 in

    在前缀过滤中,dst in 192.168.1.0/24 表示当前路由前缀是否属于该网络范围。[2]

    这对于常见的“允许某个聚合块及其子前缀输出”非常有用,例如:

    ```
    if (dst in 2a05:dfc1:7100::/40 && dst-len <= 48) { accept; }
    ```

    address-list 的坑

    官方特别提醒:如果使用 dst in listname,而该 listname 是 address-list,那么其匹配逻辑源于 host-address 设计,可能会把 /32 也纳入命中范围。官方建议必要时同时加入 dst-len 约束,例如:

    ```
    if (dst in list_name && dst-len < 32) { ... }
    ```

    这对于做白名单输出控制或黑名单过滤时尤其重要。[2]

    常用动作语法

    set / unset

    set 用于设置可写属性,例如:

    ```
    set bgp-local-pref 200;
    set distance +1;
    ```

    官方也支持在原值基础上增减,例如 +1-1,甚至从其他数值属性读取值参与计算。[2]

    unset 用于清空属性,官方文档中提到可用于如 pref-srcbgp-medbgp-out-medbgp-local-pref 等属性。[2]

    append

    append 用于向可追加属性中增加内容,典型场景就是 communities:

    ```
    append bgp-communities 65000:100;
    append bgp-large-communities 64999:1100:6939;
    ```

    这也是 large community 正确的使用方法之一。[2]

    delete / filter

    官方说明:

    这些动作可以应用于:

    BGP 场景最重要的几个属性

    bgp-local-pref

    用于 iBGP 内部优先级控制,是最常见的入口策略属性之一。例如按上游 ASN 给某个入口更高本地优先级:

    ```
    if (bgp-input-remote-as == 6939) {
    set bgp-local-pref 200;
    accept;
    }
    ```

    该用法基于官方列出的 bgp-input-remote-as(只读)和 bgp-local-pref(可写)属性。[2]

    bgp-path-prepend

    官方说明,bgp-path-prepend 用于在 BGP output 时为本地 ASN 执行 prepend。也就是说,这是“我方向外发时,额外重复自己的 ASN 次数”的控制方式。[2]

    bgp-path-peer-prepend

    这个属性和上一个很容易混淆。官方说明它主要关联从对端收到的 prepend 信息,可以用于 input 中匹配“对方 prepend 过多”的路由,也可在某些场景下覆盖收到的 peer prepend 值。[2]

    因此:

    gw / gw-ll

    官方说明,gwgw-ll 用于修改网关/下一跳,但在 BGP output 中并不是任何场景都能自由修改。尤其在 output 阶段,是否允许修改 next-hop,取决于会话属性、是否是 route reflector、是否启用了 nexthop-choice=propagate、是否为非 eBGP 且无 force-self 等上下文条件。[2]

    因此,语法能写不等于一定能生效,这一点需要在实际出站策略中重点验证。[2]

    Communities / Large Communities 的匹配与处理

    社区匹配操作符

    官方列出了多种社区匹配方式,包括:[2]

    在工程实践中常见理解如下:

    使用社区列表

    官方支持预定义:

    这些列表可以被用于: 对复杂网络策略来说,推荐把经常复用的上游控制社区、blackhole 社区、large communities 定义为 list,再在规则里调用,而不是每条规则都手写常量。[2]

    大社区的正确写法

    在 ROS v7 中,大社区属于 bgp-large-communities 这个属性。要给路由加 large community,应写成:

    ```
    if (dst == 2a05:dfc1:710e::/48) {
    append bgp-large-communities 64999:1100:6939;
    accept;
    }
    ```

    而不能把 64999:1100:6939 直接裸写成“动作”。因为官方动作体系中并不存在“把一个 large community 常量直接当 action 执行”的语法,必须通过 setappend 作用到 bgp-large-communities 属性上。[2]

    删除和清洗 communities

    官方单独说明了 delete 对不同社区类型的支持范围:[2]

    普通 communities

    可删除:

    扩展 communities

    可删除:

    Large communities

    可删除:

    这在出口策略中非常有用,例如:

    AS-PATH 正则:v7 与 v6 不兼容

    这是迁移时非常关键的一点。官方明确警告:不能把 ROS v6 或 Cisco 的 AS-PATH 正则直接复制到 ROS v7 中使用,因为 v7 的 AS-PATH 正则语义已经改变。[2]

    官方举例说明:

    官方还指出: 官方还提供了 /routing/filter/test-as-path-regexp 工具用于测试正则表达式。[2]

    RPKI 与 select-rule

    RPKI

    官方在可执行动作中列出了 rpki-verify rpkigroupname,说明在过滤链中可以直接启用指定 RPKI 组进行验证。[2]

    这意味着 RPKI 校验可以直接融入输入过滤链逻辑中,与 accept/reject、社区处理、标签标记等策略联动。[2]

    select-rule

    官方还介绍了 /routing/filter/select-rule,它并不是普通的 input/output filter,而是用于从候选路由集中挑选出符合条件的项。官方示例中甚至可以通过单独的 chain 去表达“只选 active 路由”的逻辑。[2]

    这一机制对于高级选路与输出控制场景有较强扩展性,但日常 BGP 邻居入站/出站策略中用得相对少一些。[2]

    filter wizard 辅助生成过滤规则

    官方文档提到,从 v7.20 开始提供 /routing/filter/filter-wizard,用于帮助用户生成过滤规则。这从侧面说明 v7 的过滤器虽然功能更强,但语法和心智负担也明显高于 v6。[2]

    因此在生产环境中,推荐:

    面向 BGP 实战的推荐写法

    按 AFI 分流

    官方支持 afi 作为匹配属性,可识别 ipv4ipv6l2vpnvpnv4vpnv6 等地址族。[2]

    因此,在双栈 BGP 策略中,建议先在主链按 AFI 分流,再分别跳转到 IPv4 / IPv6 子链中处理:

    ```
    /routing/filter/rule
    add chain=bgp_in rule="if (afi ipv4) { jump v4_in; } else { jump v6_in; }"
    ```

    先匹配,再修改,再 accept

    推荐统一采用下列风格:

    ```
    if (条件) {
    set/append/delete ...;
    accept;
    }
    ```

    这样最符合 v7 的执行模型,也最不容易出现“语法看起来像对,实际上动作块不成立”的问题。[2]

    next-hop 改写前先确认条件

    由于官方明确说明 gw / gw-ll 的生效受 output 上下文约束,因此在设计 set gw ...set gw-ll ... 时,需要同时检查:

    实战示例

    按 IPv6 前缀打 large community

    ```
    /routing/filter/rule
    add chain=bgp_out rule="if (dst == 2a05:dfc1:710e::/48) { append bgp-large-communities 64999:1100:6939; accept; }"
    ```

    说明:对指定 IPv6 前缀增加 large community,再接受输出。[2]

    限制对端过度 prepend

    ```
    /routing/filter/rule
    add chain=bgp_in rule="if (bgp-path-peer-prepend > 4) { reject; }"
    ```

    说明:对方 prepend 过多时直接拒绝,适用于清理异常路径。[2]

    按来源 ASN 提高本地优先级

    ```
    /routing/filter/rule
    add chain=bgp_in rule="if (bgp-input-remote-as == 6939) { set bgp-local-pref 200; accept; }"
    add chain=bgp_in rule="accept"
    ```

    说明:来自 AS6939 的路由提高 local-pref,其余默认接受。[2]

    限制可发布的前缀块与掩码长度

    ```
    /routing/filter/rule
    add chain=bgp_out rule="if (dst in 2a05:dfc1:7100::/40 && dst-len <= 48) { accept; }"
    add chain=bgp_out rule="reject"
    ```

    说明:只允许指定聚合块内、且不超过 /48 的前缀输出。[2]

    清洗不应对外发布的社区

    ```
    /routing/filter/rule
    add chain=bgp_out rule="delete bgp-communities wk,other; accept;"
    ```

    说明:将普通 communities 中的 well-known 或 other 类项清洗后再输出。是否这样删,需要按实际策略决定。[2]

    最容易踩的坑

    忘写 accept

    因为链默认是 reject,所以少写一个 accept 就可能导致整个策略链“看起来正常,实际上全丢”。[1][2]

    把 large community 当动作写

    正确写法是:

    ```
    append bgp-large-communities 64999:1100:6939;
    ```

    而不是裸写 64999:1100:6939。后者不符合 v7 的动作语法。[2]

    直接照抄 v6/Cisco 的 AS-PATH 正则

    官方明确不建议这么做,因为语义已变,可能造成严重误匹配。[2]

    误以为 set gw 必然生效

    官方已说明 BGP output 的 next-hop 改写受会话上下文限制,因此必须结合具体 BGP 角色与会话属性判断。[2]

    address-list 误匹配 host route

    使用 dst in list_name 时,应根据需要补充 dst-len 限定,避免匹配到不希望处理的 /32。[2]

    结论

    RouterOS v7 的 routing filter 已经不再只是一个“附加条件的小工具”,而是一套覆盖匹配、修改、流程控制、社区处理、RPKI 验证、路由选择的完整策略语言框架。[2]

    对于生产环境,推荐采用以下实践:

  • 主链负责分流,子链负责细分策略;
  • 所有出口、入口策略都显式写 accept / reject
  • 将 communities、large communities 做成 list 复用;
  • 对 next-hop、prepend、local-pref 等属性的修改,严格区分 input 与 output 语义;
  • 所有 AS-PATH 正则先用官方测试工具验证,再上线;
  • 迁移 v6 配置时,不要机械照抄旧语法,要按 v7 逻辑重新审视。[1][2]

  • 参考来源

    [1] MikroTik. Moving from ROSv6 to v7 with examples. RouterOS Documentation. Last updated Feb 19, 2026. Available at: https://help.mikrotik.com/docs/spaces/ROS/pages/30474256/Moving+from+ROSv6+to+v7+with+examples

    [2] MikroTik. Route Selection and Filters. RouterOS Documentation. Last updated Feb 09, 2026. Available at: https://help.mikrotik.com/docs/spaces/ROS/pages/74678285/Route+Selection+and+Filters