obmp-docker/docs/router-integration.md
Sam 65fd88a0a2 blueprints: fix cross-references, flag next-hop-self caveat, sync XRd timers
Review findings from verifying the router-blueprints drop against the
deployed stack:

- router-blueprints/README.md linked docs/router-config-guide.md, which
  does not exist -- the guide is docs/router-integration.md
- router-integration.md still advised --router-port 5000 for lab routers;
  1790 is the standard now, the note points at re-applying via
  cml/proxmox_bmp_config.py instead
- verify sections referenced Grafana paths that don't exist in the
  provisioned UI: 'Base-1001 -> Peers Table' -> Inventory / Peer Detail,
  and folder 'OBMP-Learning' -> OBMP-Reference
- role-route-reflector.cfg: loud caveat block on next-hop-self -- it only
  rewrites eBGP-learned/local routes (what this lab wants); reflected
  iBGP routes need 'ibgp policy out enforce-modifications', so on a pure
  RR the line is a silent no-op
- cml/xrd-node-definition.yaml BMP timers synced to the blueprint values
  (initial-delay 60, refresh 60/30, drop flapping-delay) per the
  keep-hand-config-and-automation-in-sync rule

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-07-20 16:49:40 -07:00

11 KiB

Router Integration Guide

The stack side of an OpenBMP deployment is covered by deploy.sh and setup.sh — see DEPLOYMENT-TYPES.md for the three scopes (full-stack, remote, central-store). This document covers the other side: what to configure on the routers you want to feed into it.

The stack supports four ingest paths. This guide is the tour of all four and the order to bring them up in. For the BMP path specifically — the mandatory one — the detailed reference lives in router-bmp-config.md (address selection on WSL vs native Linux, port choice, RR-scope activation, verification). Read this file to understand the shape, then follow router-bmp-config.md when you actually configure BMP.

Two artifacts per path:

  1. Hand-config reference — copy-paste IOS-XR fragments under router-blueprints/iosxr/.
  2. Automation — for fleets, drive the same config with ncclient (NETCONF) or SSH-CLI. Reference implementations for a specific lab live under cml/ and exabgp/; those are examples of the automation shape, not required.

The two are meant to stay in sync — if you change one, mirror the other, or the drift will surface as either a broken fleet run or a fragment that no longer matches how you actually deploy.


The four ingest paths (and what each costs you if you skip it)

Path What lights up if you configure it What you lose if you don't Mandatory?
BMP session Everything BGP: peers, RIB, churn, dashboards The stack sees nothing. Grafana panels are empty. Yes
BGP-LS export LinkState folder: ls_nodes/links, LS Topology LinkState dashboards are empty; Maps folder degraded. Only for topology
gNMI streaming Telemetry-3001 folder: interface counters etc Container-level Stack Resources still works, but per-router interface telemetry is missing. Only for interface
NETCONF Programmatic config + polling automation You can still do everything by hand on the router CLI, but there's no automation path. Only for automation

Bring these up incrementally — BMP first, then layer on the others as you use the dashboards that consume them.


Prerequisite: NETCONF over SSH

Nearly every automation entry point in this repo connects with ncclient over port 830 using the IOS-XR NETCONF device dialect. Turn it on first even if you plan to configure the rest by hand — you'll want it for the poller and any programmatic per-router queries.

Fragment: router-blueprints/iosxr/00-netconf.cfg

Credentials to align with .env:

  • IOSXR_NETCONF_USER / IOSXR_NETCONF_PASS — the account the automation logs in as. Whatever you pick, create it on the router with matching credentials and enough privilege to edit-config.
  • IOSXR_NETCONF_ADMIN_USER / IOSXR_NETCONF_ADMIN_PASS — separate admin-tier override for routers whose config draws from a privileged account.

Verify from the stack host:

ssh -p 830 <NETCONF_USER>@<ROUTER_MGMT_IP> -s netconf
# Expect an <hello> capability exchange, not a login shell.

Path 1: BMP session (mandatory) → see router-bmp-config.md

The BMP collector is what the whole stack is built around. Every router you want visibility into opens a TCP session to it and streams its Adj-RIB-In.

Full reference: router-bmp-config.md — read it before configuring. Covers:

  • Which address the router targets (ROUTER_FACING_IP from .env, not HOST_IP on WSL deployments — the WSL VM's NAT address is unreachable from real routers; see PORTABILITY-FINDINGS.md finding 4).
  • Which port (ROUTER_FACING_PORT — 1790, the IANA BMP port, standardized 2026-07; the legacy 5000 is retired. Routers still configured for 5000 must be re-applied — cml/proxmox_bmp_config.py pushes the current .env values).
  • The BMP bmp server 1 block, flat formal form.
  • Activation via neighbor-group BMP-MONITORED.
  • RR-scope-only activation for load reduction — the single biggest ingest-load lever in an RR topology.

Fragment (matches the block in router-bmp-config.md): router-blueprints/iosxr/01-bmp-basic.cfg — substitutions and the RR-scope note are inline in the fragment header.

Deployment-type note: on a remote collector deployment, routers targeting that remote node use its own ROUTER_FACING_IP, not the central-store's — the split-ingest topology (see DEPLOYMENT-TYPES.md) has each remote terminating BMP locally and forwarding parsed data over Kafka to the central store.


Path 2: BGP-LS export

Adds IGP topology visibility. The router distributes its local IS-IS database into BGP as the link-state address family, and the RRs propagate it. The collector's BMP session picks it up and the stack lands it in ls_nodes / ls_links / ls_prefixes tables, which feed the OBMP-LinkState folder and the LS Topology Map under OBMP-Maps.

Fragment: router-blueprints/iosxr/02-bgp-ls.cfg

Three parts, applied in order:

  1. IS-IS distribute link-state — tell the IGP to hand its LSDB to BGP.
  2. BGP address-family link-state link-state — enable the AF globally.
  3. Per-neighbor LS activation — activate LS toward the two RRs (on a client router) or between RRs (on a reflector). Only peers with the LS AF activated will exchange topology.

Substitutions:

  • <ISIS_INSTANCE> — the IS-IS instance tag on this router.
  • <LOCAL_ASN>, <RR_LOOPBACK_1>, <RR_LOOPBACK_2> — as documented in router-blueprints/README.md.

Verify:

On the router:

show isis database detail
show bgp link-state link-state summary

On the stack:

docker exec -i obmp-psql psql -U openbmp -d openbmp \
  -c "SELECT protocol, count(*) FROM ls_nodes GROUP BY protocol;"

Grafana → OBMP-LinkStateLS Topology should render an actual graph.

If you run OSPF instead of IS-IS, replace the router isis <ISIS_INSTANCE> block with router ospf <PROCESS_ID> + distribute link-state; the BGP side is identical.


Path 3: gNMI streaming telemetry

Feeds the Telemetry-3001 dashboards: interface counters, interface state, and anything else you subscribe to. This is dial-in gNMI — the stack's obmp-telegraf container opens a gRPC connection to each router on port 57400 and asks it to stream OpenConfig paths on an interval.

Fragment: router-blueprints/iosxr/03-gnmi.cfg

Router-side setup is small:

  • Enable the gRPC server on 57400. Use no-tls only on a trusted management network; provision a server cert otherwise.
  • Have a user Telegraf can authenticate as — a read-only account is fine. Values live in .env as GNMI_USERNAME and GNMI_PASSWORD; create the matching user on the router.

Subscription paths are configured on the stack side, not the router — see telegraf/telegraf.conf for the exact paths. The two currently active subscriptions are:

Path Interval What it feeds
openconfig-interfaces:/interfaces/interface/state/counters 10s Interface Utilization, Errors
openconfig-interfaces:/interfaces/interface/state 30s Interface Utilization (oper state)

To add more sensors, edit telegraf.conf and rebuild the telegraf container — no router-side change needed as long as the OpenConfig path is model-supported on your platform.

Reachability note: not every IOS-XR platform / release has gRPC dial-in enabled on every VRF or every interface by default. If a router authenticates fine over NETCONF but the Telegraf log shows a connection refused on 57400, verify show grpc status locally and that management ACLs don't drop 57400.

Verify:

On the router:

show grpc status
show running-config grpc

On the stack:

docker logs obmp-telegraf 2>&1 | grep -i "connected"

Grafana → OBMP-TelemetryInterface Utilization should show per-if lines within a couple minutes.


Route-reflector-only overlay

If the router is an iBGP route reflector, also apply the RR overlay after the base fragments.

Fragment: router-blueprints/iosxr/role-route-reflector.cfg

Adds an RR-CLIENT neighbor-group with route-reflector-client under both ipv4-unicast and link-state link-state, plus a bgp cluster-id. Every client peer just needs use neighbor-group RR-CLIENT.

The RR overlay is also where the RR-scope-only BMP activation belongs in practice — the RR-CLIENT group already has bmp-activate server 1 in the fragment, so every client session added to the RR is auto-monitored, while the client-router side has BMP off. See the router-bmp-config.md discussion of activation scope for why this matters.


Multi-router bring-up checklist

For a fresh AS with two RRs and N clients, apply in this order:

  1. All routers: 00-netconf.cfg (enables everything else).
  2. RRs: 01-bmp-basic.cfg + role-route-reflector.cfg (which handles both RR-client wiring and BMP activation on reflected sessions).
  3. Clients: 01-bmp-basic.cfg server block only — do NOT bmp-activate your iBGP session to the RR; the RR is already monitoring the same table pre-policy. This is the load-reduction pattern from router-bmp-config.md.
  4. Routers you want in topology: 02-bgp-ls.cfg (usually all).
  5. Routers you want streaming telemetry: 03-gnmi.cfg.
  6. Verify each layer on the stack side before adding the next — don't configure all four on all routers in one shot; you lose the ability to correlate a failure to a specific ingest path.

Extending to another vendor

The four ingest paths are all standards (RFC 7854 for BMP, RFC 7752 for BGP-LS, gNMI 0.10.0+ for telemetry, RFC 6241 for NETCONF). The fragments under router-blueprints/iosxr/ are IOS-XR syntax; the behavior the stack expects is vendor-neutral:

  • BMP: TCP session from router to ROUTER_FACING_IP:ROUTER_FACING_PORT, Adj-RIB-In scope (pre-policy inbound), no monitoring type restrictions.
  • BGP-LS: standard NLRI encoding, exported over any iBGP session.
  • gNMI: OpenConfig models on the paths listed above; JSON_IETF encoding.
  • NETCONF: edit-config over SSH port 830 with vendor-native YANG models — a different vendor obviously uses different modules and scripts.

If you deploy against Junos, EOS, or SR OS, treat the IOS-XR fragments as a specification of what to configure and translate to your vendor's syntax. A sibling router-blueprints/<vendor>/ tree can be added the same way once someone has a working end-to-end deployment to base it on.