Fix VRP duplicate BGP Peers (#14431)

* fix VRP not cleaning BGP peers properly

* fix missing field in BgpPeer model

* Update includes/discovery/bgp-peers/vrp.inc.php

Co-authored-by: Tony Murray <murraytony@gmail.com>
This commit is contained in:
PipoCanaja
2022-10-11 20:26:56 +02:00
committed by GitHub
parent 90bbbed3c9
commit 1fd915c8a3
2 changed files with 22 additions and 35 deletions

View File

@@ -49,6 +49,7 @@ class BgpPeer extends DeviceRelatedModel
'bgpPeerOutTotalMessages',
'bgpPeerFsmEstablishedTime',
'bgpPeerInUpdateElapsedTime',
'bgpPeerDescr',
'astext',
];
// ---- Query scopes ----

View File

@@ -24,7 +24,6 @@
* @author PipoCanaja
*/
use App\Models\BgpPeer;
use LibreNMS\Config;
use LibreNMS\Util\IP;
@@ -39,7 +38,7 @@ if (Config::get('enable_bgp')) {
// So if we have HUAWEI BGP entries or if we don't have anything from HUAWEI nor BGP4-MIB
if (count($bgpPeersCache) > 0 || count($bgpPeersCache_ietf) == 0) {
$vrfs = DeviceCache::getPrimary()->vrfs()->select('vrf_id', 'vrf_name');
$vrfs = DeviceCache::getPrimary()->vrfs()->select('vrf_id', 'vrf_name')->get();
foreach ($vrfs as $vrf) {
$map_vrf['byId'][$vrf['vrf_id']]['vrf_name'] = $vrf['vrf_name'];
$map_vrf['byName'][$vrf['vrf_name']]['vrf_id'] = $vrf['vrf_id'];
@@ -70,10 +69,11 @@ if (Config::get('enable_bgp')) {
}
$bgpPeers[$vrfInstance][$address] = $value;
$bgpPeers[$vrfInstance][$address]['vrf_id'] = $map_vrf['byName'][$vrfInstance]['vrf_id'];
$bgpPeers[$vrfInstance][$address]['vrf_id'] = $map_vrf['byName'][$vrfInstance]['vrf_id'] ?? null;
$bgpPeers[$vrfInstance][$address]['afi'] = $oid[1];
$bgpPeers[$vrfInstance][$address]['safi'] = $oid[2];
$bgpPeers[$vrfInstance][$address]['typePeer'] = $oid[3];
$bgpPeers[$vrfInstance][$address]['bgpPeerDescr'] = '';
if (array_key_exists('0.' . $oid[3] . '.' . $oid_address, $bgpPeersDesc)) {
// We may have a description
$bgpPeers[$vrfInstance][$address]['bgpPeerDescr'] = $bgpPeersDesc['0.' . $oid[3] . '.' . $oid_address]['hwBgpPeerSessionExtDescription'];
@@ -82,10 +82,6 @@ if (Config::get('enable_bgp')) {
foreach ($bgpPeers as $vrfName => $vrf) {
$vrfId = $map_vrf['byName'][$vrfName]['vrf_id'];
$checkVrf = ' AND vrf_id = ? ';
if (empty($vrfId)) {
$checkVrf = ' AND `vrf_id` IS NULL ';
}
foreach ($vrf as $address => $value) {
$astext = get_astext($value['hwBgpPeerRemoteAs']);
@@ -94,9 +90,9 @@ if (Config::get('enable_bgp')) {
'device_id' => $device['device_id'],
'vrf_id' => $vrfId,
'bgpPeerIdentifier' => $address,
'bgpPeerRemoteAs' => $value['hwBgpPeerRemoteAs'],
'bgpPeerState' => $value['hwBgpPeerState'],
'bgpPeerAdminStatus' => $value['hwBgpPeerAdminStatus'],
'bgpPeerRemoteAs' => $value['hwBgpPeerRemoteAs'] ?? '',
'bgpPeerState' => $value['hwBgpPeerState'] ?? '',
'bgpPeerAdminStatus' => $value['hwBgpPeerAdminStatus'] ?? '',
'bgpLocalAddr' => '0.0.0.0',
'bgpPeerRemoteAddr' => $value['hwBgpPeerRemoteAddr'],
'bgpPeerInUpdates' => 0,
@@ -105,14 +101,13 @@ if (Config::get('enable_bgp')) {
'bgpPeerOutTotalMessages' => 0,
'bgpPeerFsmEstablishedTime' => $value['hwBgpPeerFsmEstablishedTime'],
'bgpPeerInUpdateElapsedTime' => 0,
'bgpPeerDescr' => $value['bgpPeerDescr'],
'bgpPeerDescr' => $value['bgpPeerDescr'] ?? '',
'astext' => $astext,
];
if (empty($vrfId)) {
unset($peers['vrf_id']);
}
dbInsert($peers, 'bgpPeers');
$seenPeer[$address] = 1;
$seenPeerID[] = DeviceCache::getPrimary()->bgppeers()->create($peers)->bgpPeer_id;
if (Config::get('autodiscovery.bgp')) {
$name = gethostbyaddr($address);
@@ -121,10 +116,16 @@ if (Config::get('enable_bgp')) {
echo '+';
$vrp_bgp_peer_count++;
} else {
dbUpdate(['bgpPeerDescr' => $value['bgpPeerDescr'], 'bgpPeerRemoteAs' => $value['hwBgpPeerRemoteAs'], 'astext' => $astext], 'bgpPeers', 'device_id = ? AND bgpPeerIdentifier = ? ' . $checkVrf, [$device['device_id'], $address, $vrfId]);
$seenPeer[$address] = 1;
echo '.';
$vrp_bgp_peer_count++;
$peers = [
'bgpPeerRemoteAs' => $value['hwBgpPeerRemoteAs'],
'astext' => $astext,
'bgpPeerDescr' => $value['bgpPeerDescr'] ?? '',
];
$affected = DeviceCache::getPrimary()->bgppeers()->where('bgpPeerIdentifier', $address)->where('vrf_id', $vrfId)->update($peers);
$seenPeerID[] = (DeviceCache::getPrimary()->bgppeers()->where('bgpPeerIdentifier', $address)->where('vrf_id', $vrfId)->select('bgpPeer_id')->orderBy('bgpPeer_id', 'ASC')->first()->bgpPeer_id);
echo str_repeat('.', $affected);
$vrp_bgp_peer_count += $affected;
}
if (dbFetchCell('SELECT COUNT(*) from `bgpPeers_cbgp` WHERE device_id = ? AND bgpPeerIdentifier = ? AND afi=? AND safi=?', [$device['device_id'], $value['hwBgpPeerRemoteAddr'], $value['afi'], $value['safi']]) < 1) {
if ($vrfName != '') {
@@ -138,25 +139,10 @@ if (Config::get('enable_bgp')) {
}
}
// clean up peers
$peers = DeviceCache::getPrimary()->bgppeers()->select('vrf_id', 'bgpPeerIdentifier');
foreach ($peers as $value) {
$vrfId = $value['vrf_id'];
$vrfName = $map_vrf['byId'][$vrfId]['vrf_name'];
$address = $value['bgpPeerIdentifier'];
if (isset($seenPeer[$address])) {
continue; //we just added this peer
}
if ((empty($vrfId) && empty($bgpPeers[''][$address])) ||
(! empty($vrfId) && ! empty($vrfName) && empty($bgpPeers[$vrfName][$address])) ||
(! empty($vrfId) && empty($vrfName))) {
$deleted = BgpPeer::where('device_id', $device['device_id'])
->where('bgpPeerIdentifier', $address)
->where('vrf_id', $vrfId)
->delete();
echo str_repeat('-', $deleted);
echo PHP_EOL;
}
if (! is_null($seenPeerID)) {
$deleted = DeviceCache::getPrimary()->bgppeers()->whereNotIn('bgpPeer_id', $seenPeerID)->delete();
echo str_repeat('-', $deleted);
}
$af_query = 'SELECT bgpPeerIdentifier, afi, safi FROM bgpPeers_cbgp WHERE `device_id`=? AND bgpPeerIdentifier=?';