Files
shx-network/bgp_gateway_failover.md
T

15 KiB
Raw Blame History

BGP Gateway Failover: SWE-HIPHOST → FIN-HIPHOST

Проблема

У вас есть:

  • BGP приносит список адресов
  • Трафик фильтруется на шлюз swe-hiphost
  • Нужно автоматически переключаться на fin-hiphost при недоступности swe-hiphost

Архитектура решения

graph TB
    subgraph "HOME"
        HOME[HOME<br/>home.rt.shx.su]
        BGP[BGP Routes]
        FILTER[Route Filter<br/>swe-hiphost]
        FAILOVER[Failover Logic]
    end
    
    subgraph "Швеция"
        SWE[SWE-HIPHOST<br/>swe.hiphost.rt.shx.su]
        BFD_SWE[BFD Session]
    end
    
    subgraph "Финляндия"
        FIN[FIN-HIPHOST<br/>fin.hiphost.rt.shx.su]
        BFD_FIN[BFD Session]
    end
    
    %% BGP и маршрутизация
    BGP -. "BGP routes" .- HOME
    FILTER -. "Primary gateway" .- SWE
    FAILOVER -. "Backup gateway" .- FIN
    
    %% BFD мониторинг
    HOME -. "BFD monitoring" .- SWE
    HOME -. "BFD monitoring" .- FIN
    
    %% Failover
    FAILOVER -. "Auto switch" .- FILTER
    
    style HOME fill:#e1f5fe
    style SWE fill:#4caf50
    style FIN fill:#ff9800
    style BFD_SWE fill:#9c27b0
    style BFD_FIN fill:#9c27b0

Решение 1: Динамические маршруты с check-gateway

Настройка на HOME (home.rt.shx.su):

# Создать address-list для адресов из BGP (пример)
/ip firewall address-list
add list=BGP-ROUTES list=173.194.0.0/16 comment="BGP route"
add list=BGP-ROUTES list=74.125.0.0/16 comment="BGP route"
add list=BGP-ROUTES list=142.250.0.0/16 comment="BGP route"
# ... добавьте все ваши BGP маршруты

# Создать статические маршруты с failover
/ip route
# Основной маршрут через SWE-HIPHOST
add dst-address=173.194.0.0/16 gateway=swe-hiphost distance=1 check-gateway=ping
add dst-address=74.125.0.0/16 gateway=swe-hiphost distance=1 check-gateway=ping
add dst-address=142.250.0.0/16 gateway=swe-hiphost distance=1 check-gateway=ping

# Резервный маршрут через FIN-HIPHOST
add dst-address=173.194.0.0/16 gateway=fin-hiphost distance=2 check-gateway=ping
add dst-address=74.125.0.0/16 gateway=fin-hiphost distance=2 check-gateway=ping
add dst-address=142.250.0.0/16 gateway=fin-hiphost distance=2 check-gateway=ping

Решение 2: BFD с динамическими маршрутами

Настройка BFD мониторинга:

# Настроить BFD для SWE-HIPHOST
/routing bfd
add interface=gre-SWE-HIPHOST interval=100ms multiplier=3

# Настроить BFD для FIN-HIPHOST
/routing bfd
add interface=gre-FIN-HIPHOST interval=100ms multiplier=3

# Создать маршруты с check-gateway=bfd
/ip route
add dst-address=173.194.0.0/16 gateway=swe-hiphost distance=1 check-gateway=bfd
add dst-address=74.125.0.0/16 gateway=swe-hiphost distance=1 check-gateway=bfd
add dst-address=142.250.0.0/16 gateway=swe-hiphost distance=1 check-gateway=bfd

# Резервные маршруты
add dst-address=173.194.0.0/16 gateway=fin-hiphost distance=2 check-gateway=bfd
add dst-address=74.125.0.0/16 gateway=fin-hiphost distance=2 check-gateway=bfd
add dst-address=142.250.0.0/16 gateway=fin-hiphost distance=2 check-gateway=bfd

Решение 3: Скрипт для автоматического управления маршрутами

Создание скрипта на HOME:

# Скрипт для мониторинга и переключения шлюзов
/system script
add name=gateway-failover source={
    :local sweStatus [/routing bfd print where interface=gre-SWE-HIPHOST]
    :local finStatus [/routing bfd print where interface=gre-FIN-HIPHOST]
    
    # Проверить статус SWE-HIPHOST
    :if ([:len $sweStatus] > 0) do={
        # SWE доступен - использовать его как primary
        :log info "SWE-HIPHOST is UP - using as primary gateway"
        /ip route set [find where dst-address=173.194.0.0/16 and gateway=swe-hiphost] distance=1
        /ip route set [find where dst-address=173.194.0.0/16 and gateway=fin-hiphost] distance=2
        /ip route set [find where dst-address=74.125.0.0/16 and gateway=swe-hiphost] distance=1
        /ip route set [find where dst-address=74.125.0.0/16 and gateway=fin-hiphost] distance=2
        /ip route set [find where dst-address=142.250.0.0/16 and gateway=swe-hiphost] distance=1
        /ip route set [find where dst-address=142.250.0.0/16 and gateway=fin-hiphost] distance=2
    } else={
        # SWE недоступен - переключиться на FIN
        :log info "SWE-HIPHOST is DOWN - switching to FIN-HIPHOST"
        /ip route set [find where dst-address=173.194.0.0/16 and gateway=swe-hiphost] distance=100
        /ip route set [find where dst-address=173.194.0.0/16 and gateway=fin-hiphost] distance=1
        /ip route set [find where dst-address=74.125.0.0/16 and gateway=swe-hiphost] distance=100
        /ip route set [find where dst-address=74.125.0.0/16 and gateway=fin-hiphost] distance=1
        /ip route set [find where dst-address=142.250.0.0/16 and gateway=swe-hiphost] distance=100
        /ip route set [find where dst-address=142.250.0.0/16 and gateway=fin-hiphost] distance=1
    }
}

# Запускать скрипт каждые 5 секунд
/system scheduler
add name=gateway-failover interval=5s on-event=gateway-failover

Решение 4: Routing Rules с динамическими таблицами

Создание динамических routing tables:

# Создать routing tables для каждого шлюза
/routing table
add name=SWE-Gateway fib
add name=FIN-Gateway fib

# Создать address-list для BGP маршрутов
/ip firewall address-list
add list=BGP-ROUTES list=173.194.0.0/16 comment="BGP route"
add list=BGP-ROUTES list=74.125.0.0/16 comment="BGP route"
add list=BGP-ROUTES list=142.250.0.0/16 comment="BGP route"

# Routing rules для BGP маршрутов
/routing rule
add dst-address=173.194.0.0/16 action=lookup table=SWE-Gateway
add dst-address=74.125.0.0/16 action=lookup table=SWE-Gateway
add dst-address=142.250.0.0/16 action=lookup table=SWE-Gateway

# Маршруты в таблице SWE-Gateway
/ip route
add dst-address=0.0.0.0/0 gateway=swe-hiphost routing-table=SWE-Gateway distance=1

# Маршруты в таблице FIN-Gateway (резервные)
/ip route
add dst-address=0.0.0.0/0 gateway=fin-hiphost routing-table=FIN-Gateway distance=1

Скрипт для переключения таблиц:

# Скрипт для переключения между routing tables
/system script
add name=switch-routing-table source={
    :local sweStatus [/routing bfd print where interface=gre-SWE-HIPHOST]
    
    :if ([:len $sweStatus] > 0) do={
        # SWE доступен - использовать SWE-Gateway
        :log info "SWE-HIPHOST is UP - using SWE-Gateway"
        /routing rule set [find where table=SWE-Gateway] action=lookup
        /routing rule set [find where table=FIN-Gateway] action=lookup-only
    } else={
        # SWE недоступен - переключиться на FIN-Gateway
        :log info "SWE-HIPHOST is DOWN - switching to FIN-Gateway"
        /routing rule set [find where table=SWE-Gateway] action=lookup-only
        /routing rule set [find where table=FIN-Gateway] action=lookup
    }
}

# Запускать каждые 5 секунд
/system scheduler
add name=switch-routing-table interval=5s on-event=switch-routing-table

Решение 5: OSPF с динамическими cost

Настройка OSPF с динамическим cost:

# Создать скрипт для изменения OSPF cost на основе доступности
/system script
add name=adjust-ospf-cost source={
    :local sweStatus [/routing bfd print where interface=gre-SWE-HIPHOST]
    :local finStatus [/routing bfd print where interface=gre-FIN-HIPHOST]
    
    :local sweInterface [/routing ospf interface-template find where interfaces=gre-SWE-HIPHOST]
    :local finInterface [/routing ospf interface-template find where interfaces=gre-FIN-HIPHOST]
    
    # Настроить cost для SWE-HIPHOST
    :if ([:len $sweStatus] > 0) do={
        /routing ospf interface-template set $sweInterface cost=10
        :log info "SWE-HIPHOST UP - OSPF cost=10"
    } else={
        /routing ospf interface-template set $sweInterface cost=1000
        :log info "SWE-HIPHOST DOWN - OSPF cost=1000"
    }
    
    # Настроить cost для FIN-HIPHOST
    :if ([:len $finStatus] > 0) do={
        /routing ospf interface-template set $finInterface cost=20
        :log info "FIN-HIPHOST UP - OSPF cost=20"
    } else={
        /routing ospf interface-template set $finInterface cost=1000
        :log info "FIN-HIPHOST DOWN - OSPF cost=1000"
    }
}

# Запускать каждые 5 секунд
/system scheduler
add name=adjust-ospf-cost interval=5s on-event=adjust-ospf-cost

Автоматическое создание маршрутов из BGP

Скрипт для автоматического создания маршрутов:

# Скрипт для создания маршрутов из BGP с failover
/system script
add name=create-bgp-routes source={
    :local bgpRoutes [/routing bgp route print where active=yes]
    :local sweStatus [/routing bfd print where interface=gre-SWE-HIPHOST]
    
    :foreach route in=$bgpRoutes do={
        :local dstAddress [:pick $route 0 [:find $route " "]]
        
        # Проверить существует ли уже маршрут
        :local existingRoute [/ip route print count-only where dst-address=$dstAddress]
        
        :if ($existingRoute = 0) do={
            # Создать маршрут с failover
            :if ([:len $sweStatus] > 0) do={
                # SWE доступен - создать с distance=1
                /ip route add dst-address=$dstAddress gateway=swe-hiphost distance=1 check-gateway=bfd
                /ip route add dst-address=$dstAddress gateway=fin-hiphost distance=2 check-gateway=bfd
                :log info "Created route $dstAddress with SWE primary"
            } else={
                # SWE недоступен - создать с FIN primary
                /ip route add dst-address=$dstAddress gateway=fin-hiphost distance=1 check-gateway=bfd
                /ip route add dst-address=$dstAddress gateway=swe-hiphost distance=2 check-gateway=bfd
                :log info "Created route $dstAddress with FIN primary"
            }
        }
    }
}

# Запускать каждые 30 секунд
/system scheduler
add name=create-bgp-routes interval=30s on-event=create-bgp-routes

Проверка настройки

Проверка BFD статуса:

# Проверить BFD сессии
/routing bfd print

# Проверить детали BFD
/routing bfd print detail

Проверка маршрутов:

# Проверить все маршруты
/ip route print

# Проверить маршруты к конкретному адресу
/ip route print where dst-address~"173.194"

# Проверить routing tables
/ip route print where routing-table=SWE-Gateway
/ip route print where routing-table=FIN-Gateway

Проверка BGP маршрутов:

# Проверить активные BGP маршруты
/routing bgp route print where active=yes

# Проверить BGP соседей
/routing bgp neighbor print

Тестирование failover

Тест 1: Проверка переключения при отключении SWE:

# Отключить GRE туннель к SWE
/interface gre disable [find where name=gre-SWE-HIPHOST]

# Подождать 10-30 секунд и проверить маршруты
/ip route print where dst-address~"173.194"

# Включить туннель обратно
/interface gre enable [find where name=gre-SWE-HIPHOST]

Тест 2: Проверка traceroute:

# Проверить маршрут к BGP адресу
traceroute 173.194.0.1

# Должен показать путь через активный шлюз

Мониторинг и логирование

Настройка логирования:

# Включить логирование для BFD
/system logging
add topics=bfd

# Включить логирование для routing
/system logging
add topics=route

# Включить логирование для BGP
/system logging
add topics=bgp

Создание дашборда:

# Скрипт для отображения статуса
/system script
add name=show-gateway-status source={
    :log info "=== Gateway Status Report ==="
    :log info "BFD Status:"
    /routing bfd print
    :log info "Active Routes:"
    /ip route print where dst-address~"173.194"
    :log info "BGP Routes:"
    /routing bgp route print where active=yes
    :log info "=== End Report ==="
}

# Запускать каждую минуту
/system scheduler
add name=gateway-status interval=1m on-event=show-gateway-status

Полная конфигурация для копирования

HOME (home.rt.shx.su):

# BFD для мониторинга шлюзов
/routing bfd
add interface=gre-SWE-HIPHOST interval=100ms multiplier=3
add interface=gre-FIN-HIPHOST interval=100ms multiplier=3

# Создать routing tables
/routing table
add name=SWE-Gateway fib
add name=FIN-Gateway fib

# Address-list для BGP маршрутов
/ip firewall address-list
add list=BGP-ROUTES list=173.194.0.0/16 comment="BGP route"
add list=BGP-ROUTES list=74.125.0.0/16 comment="BGP route"
add list=BGP-ROUTES list=142.250.0.0/16 comment="BGP route"

# Routing rules
/routing rule
add dst-address=173.194.0.0/16 action=lookup table=SWE-Gateway
add dst-address=74.125.0.0/16 action=lookup table=SWE-Gateway
add dst-address=142.250.0.0/16 action=lookup table=SWE-Gateway

# Маршруты в таблицах
/ip route
add dst-address=0.0.0.0/0 gateway=swe-hiphost routing-table=SWE-Gateway distance=1
add dst-address=0.0.0.0/0 gateway=fin-hiphost routing-table=FIN-Gateway distance=1

# Логирование
/system logging
add topics=bfd
add topics=route
add topics=bgp

Заключение

Данное решение обеспечивает:

  1. Автоматический failover между SWE-HIPHOST и FIN-HIPHOST
  2. Быстрое обнаружение проблем через BFD (100ms интервал)
  3. Динамическое управление маршрутами в зависимости от доступности шлюзов
  4. Поддержку BGP маршрутов с автоматическим созданием failover маршрутов
  5. Гибкость настройки через routing tables и rules

Теперь при недоступности SWE-HIPHOST трафик автоматически переключится на FIN-HIPHOST, а при восстановлении SWE-HIPHOST вернется к нему.