From 30c2b1a1ab54aa3a015ea684a101b86173e0cbd9 Mon Sep 17 00:00:00 2001 From: Monviech <79600909+Monviech@users.noreply.github.com> Date: Fri, 21 Mar 2025 07:55:33 +0100 Subject: [PATCH] net/frr: Add BGP/OSPF/OSPF6 route redistribution with route-map feature (#4578) * net/frr: Add BGP route redistribution with route-map feature. Add migration. * net/frr: Small template fix in redistribution since route-map is optional * net/frr: Add OSPF and OSPF6 route redistribution with route-map feature. Adjust migration to migrate OSPF, OSPF6 and BGP models. * net/frr: make sweep * net/frr: Fix wrong diff in ospf6 template * net/frr: Add a little css to make the redistribution grid look like its part of the base form, more seamless integration * net/frr: Show route-map in grid and hide description --- net/frr/pkg-descr | 2 + .../OPNsense/Quagga/Api/BgpController.php | 31 ++++++ .../Quagga/Api/Ospf6settingsController.php | 25 +++++ .../Quagga/Api/OspfsettingsController.php | 26 +++++ .../OPNsense/Quagga/BgpController.php | 3 + .../OPNsense/Quagga/Ospf6Controller.php | 3 + .../OPNsense/Quagga/OspfController.php | 3 + .../controllers/OPNsense/Quagga/forms/bgp.xml | 6 -- .../Quagga/forms/dialogEditRedistribution.xml | 33 +++++++ .../OPNsense/Quagga/forms/ospf.xml | 12 --- .../OPNsense/Quagga/forms/ospf6.xml | 12 --- .../mvc/app/models/OPNsense/Quagga/BGP.xml | 45 ++++++--- .../OPNsense/Quagga/Migrations/M1_1_0.php | 96 +++++++++++++++++++ .../mvc/app/models/OPNsense/Quagga/OSPF.xml | 58 ++++++----- .../mvc/app/models/OPNsense/Quagga/OSPF6.xml | 52 ++++++---- .../mvc/app/views/OPNsense/Quagga/bgp.volt | 35 +++++++ .../mvc/app/views/OPNsense/Quagga/ospf.volt | 35 +++++++ .../mvc/app/views/OPNsense/Quagga/ospf6.volt | 35 ++++++- .../templates/OPNsense/Quagga/bgpd.conf | 10 +- .../templates/OPNsense/Quagga/ospf6d.conf | 10 +- .../templates/OPNsense/Quagga/ospfd.conf | 10 +- 21 files changed, 437 insertions(+), 105 deletions(-) create mode 100644 net/frr/src/opnsense/mvc/app/controllers/OPNsense/Quagga/forms/dialogEditRedistribution.xml create mode 100644 net/frr/src/opnsense/mvc/app/models/OPNsense/Quagga/Migrations/M1_1_0.php diff --git a/net/frr/pkg-descr b/net/frr/pkg-descr index 3ca685557..aa57d45c4 100644 --- a/net/frr/pkg-descr +++ b/net/frr/pkg-descr @@ -14,6 +14,8 @@ Plugin Changelog 1.44 +* Add route-map functionality to route redistribution in bgp (opnsense/plugins/issues/4570) +* Add route-map functionality to route redistribution in ospf/ospf6 (opnsense/plugins/issues/4580) * Add BGP remote-as internal and external (opnsense/plugins/issues/4609) 1.43 diff --git a/net/frr/src/opnsense/mvc/app/controllers/OPNsense/Quagga/Api/BgpController.php b/net/frr/src/opnsense/mvc/app/controllers/OPNsense/Quagga/Api/BgpController.php index 2d1759dce..3a4a93158 100644 --- a/net/frr/src/opnsense/mvc/app/controllers/OPNsense/Quagga/Api/BgpController.php +++ b/net/frr/src/opnsense/mvc/app/controllers/OPNsense/Quagga/Api/BgpController.php @@ -187,6 +187,31 @@ class BgpController extends ApiMutableModelControllerBase return $this->setBase('peergroup', 'peergroups.peergroup', $uuid); } + public function searchRedistributionAction() + { + return $this->searchBase('redistributions.redistribution'); + } + + public function getRedistributionAction($uuid = null) + { + return $this->getBase('redistribution', 'redistributions.redistribution', $uuid); + } + + public function addRedistributionAction() + { + return $this->addBase('redistribution', 'redistributions.redistribution'); + } + + public function delRedistributionAction($uuid) + { + return $this->delBase('redistributions.redistribution', $uuid); + } + + public function setRedistributionAction($uuid) + { + return $this->setBase('redistribution', 'redistributions.redistribution', $uuid); + } + public function toggleCommunitylistAction($uuid) { return $this->toggleBase('communitylists.communitylist', $uuid); @@ -216,4 +241,10 @@ class BgpController extends ApiMutableModelControllerBase { return $this->toggleBase('peergroups.peergroup', $uuid); } + + public function toggleRedistributionAction($uuid) + { + return $this->toggleBase('redistributions.redistribution', $uuid); + } + } diff --git a/net/frr/src/opnsense/mvc/app/controllers/OPNsense/Quagga/Api/Ospf6settingsController.php b/net/frr/src/opnsense/mvc/app/controllers/OPNsense/Quagga/Api/Ospf6settingsController.php index 5019e029b..65c2610b5 100644 --- a/net/frr/src/opnsense/mvc/app/controllers/OPNsense/Quagga/Api/Ospf6settingsController.php +++ b/net/frr/src/opnsense/mvc/app/controllers/OPNsense/Quagga/Api/Ospf6settingsController.php @@ -137,4 +137,29 @@ class Ospf6settingsController extends ApiMutableModelControllerBase { return $this->toggleBase('routemaps.routemap', $uuid); } + public function searchRedistributionAction() + { + return $this->searchBase('redistributions.redistribution'); + } + public function getRedistributionAction($uuid = null) + { + return $this->getBase('redistribution', 'redistributions.redistribution', $uuid); + } + public function addRedistributionAction() + { + return $this->addBase('redistribution', 'redistributions.redistribution'); + } + public function delRedistributionAction($uuid) + { + return $this->delBase('redistributions.redistribution', $uuid); + } + public function setRedistributionAction($uuid) + { + return $this->setBase('redistribution', 'redistributions.redistribution', $uuid); + } + public function toggleRedistributionAction($uuid) + { + return $this->toggleBase('redistributions.redistribution', $uuid); + } + } diff --git a/net/frr/src/opnsense/mvc/app/controllers/OPNsense/Quagga/Api/OspfsettingsController.php b/net/frr/src/opnsense/mvc/app/controllers/OPNsense/Quagga/Api/OspfsettingsController.php index cb495c1c2..763449420 100644 --- a/net/frr/src/opnsense/mvc/app/controllers/OPNsense/Quagga/Api/OspfsettingsController.php +++ b/net/frr/src/opnsense/mvc/app/controllers/OPNsense/Quagga/Api/OspfsettingsController.php @@ -133,4 +133,30 @@ class OspfsettingsController extends ApiMutableModelControllerBase { return $this->toggleBase('routemaps.routemap', $uuid); } + + public function searchRedistributionAction() + { + return $this->searchBase('redistributions.redistribution'); + } + public function getRedistributionAction($uuid = null) + { + return $this->getBase('redistribution', 'redistributions.redistribution', $uuid); + } + public function addRedistributionAction() + { + return $this->addBase('redistribution', 'redistributions.redistribution'); + } + public function delRedistributionAction($uuid) + { + return $this->delBase('redistributions.redistribution', $uuid); + } + public function setRedistributionAction($uuid) + { + return $this->setBase('redistribution', 'redistributions.redistribution', $uuid); + } + public function toggleRedistributionAction($uuid) + { + return $this->toggleBase('redistributions.redistribution', $uuid); + } + } diff --git a/net/frr/src/opnsense/mvc/app/controllers/OPNsense/Quagga/BgpController.php b/net/frr/src/opnsense/mvc/app/controllers/OPNsense/Quagga/BgpController.php index 1374be541..6949d12e3 100644 --- a/net/frr/src/opnsense/mvc/app/controllers/OPNsense/Quagga/BgpController.php +++ b/net/frr/src/opnsense/mvc/app/controllers/OPNsense/Quagga/BgpController.php @@ -52,6 +52,9 @@ class BgpController extends \OPNsense\Base\IndexController $this->view->formDialogEditBGPPeergroups = $this->getForm("dialogEditBGPPeergroups"); $this->view->formGridEditBGPPeergroups = $this->getFormGrid("dialogEditBGPPeergroups"); + $this->view->formDialogEditRedistribution = $this->getForm("dialogEditRedistribution"); + $this->view->formGridEditRedistribution = $this->getFormGrid("dialogEditRedistribution"); + $this->view->pick('OPNsense/Quagga/bgp'); } } diff --git a/net/frr/src/opnsense/mvc/app/controllers/OPNsense/Quagga/Ospf6Controller.php b/net/frr/src/opnsense/mvc/app/controllers/OPNsense/Quagga/Ospf6Controller.php index 107cafa78..e782096b9 100644 --- a/net/frr/src/opnsense/mvc/app/controllers/OPNsense/Quagga/Ospf6Controller.php +++ b/net/frr/src/opnsense/mvc/app/controllers/OPNsense/Quagga/Ospf6Controller.php @@ -43,6 +43,9 @@ class Ospf6Controller extends \OPNsense\Base\IndexController $this->view->formDialogEditRouteMaps = $this->getForm("dialogEditOSPF6RouteMaps"); $this->view->formGridEditRouteMaps = $this->getFormGrid("dialogEditOSPF6RouteMaps"); + $this->view->formDialogEditRedistribution = $this->getForm("dialogEditRedistribution"); + $this->view->formGridEditRedistribution = $this->getFormGrid("dialogEditRedistribution"); + $this->view->pick('OPNsense/Quagga/ospf6'); } } diff --git a/net/frr/src/opnsense/mvc/app/controllers/OPNsense/Quagga/OspfController.php b/net/frr/src/opnsense/mvc/app/controllers/OPNsense/Quagga/OspfController.php index 0ab2f1588..584c5da00 100644 --- a/net/frr/src/opnsense/mvc/app/controllers/OPNsense/Quagga/OspfController.php +++ b/net/frr/src/opnsense/mvc/app/controllers/OPNsense/Quagga/OspfController.php @@ -46,6 +46,9 @@ class OspfController extends \OPNsense\Base\IndexController $this->view->formDialogEditRouteMaps = $this->getForm("dialogEditOSPFRouteMaps"); $this->view->formGridEditRouteMaps = $this->getFormGrid("dialogEditOSPFRouteMaps"); + $this->view->formDialogEditRedistribution = $this->getForm("dialogEditRedistribution"); + $this->view->formGridEditRedistribution = $this->getFormGrid("dialogEditRedistribution"); + $this->view->pick('OPNsense/Quagga/ospf'); } } diff --git a/net/frr/src/opnsense/mvc/app/controllers/OPNsense/Quagga/forms/bgp.xml b/net/frr/src/opnsense/mvc/app/controllers/OPNsense/Quagga/forms/bgp.xml index 85e104b23..f515a7b71 100644 --- a/net/frr/src/opnsense/mvc/app/controllers/OPNsense/Quagga/forms/bgp.xml +++ b/net/frr/src/opnsense/mvc/app/controllers/OPNsense/Quagga/forms/bgp.xml @@ -53,10 +53,4 @@ checkbox Enable extended logging of BGP neighbor changes. - - bgp.redistribute - - select_multiple - Select routing sources to redistribute to other nodes. - diff --git a/net/frr/src/opnsense/mvc/app/controllers/OPNsense/Quagga/forms/dialogEditRedistribution.xml b/net/frr/src/opnsense/mvc/app/controllers/OPNsense/Quagga/forms/dialogEditRedistribution.xml new file mode 100644 index 000000000..cd3eb2a08 --- /dev/null +++ b/net/frr/src/opnsense/mvc/app/controllers/OPNsense/Quagga/forms/dialogEditRedistribution.xml @@ -0,0 +1,33 @@ +
+ + redistribution.enabled + + checkbox + + 6em + boolean + rowtoggle + + + + redistribution.redistribute + + dropdown + Select routing sources to redistribute to other nodes. + + + redistribution.linkedRoutemap + + dropdown + Optional Route-map to apply to this redistribution. + + + redistribution.description + + text + Optional description for this redistribution. + + false + + +
diff --git a/net/frr/src/opnsense/mvc/app/controllers/OPNsense/Quagga/forms/ospf.xml b/net/frr/src/opnsense/mvc/app/controllers/OPNsense/Quagga/forms/ospf.xml index 3600e8497..e6935b8a8 100644 --- a/net/frr/src/opnsense/mvc/app/controllers/OPNsense/Quagga/forms/ospf.xml +++ b/net/frr/src/opnsense/mvc/app/controllers/OPNsense/Quagga/forms/ospf.xml @@ -31,18 +31,6 @@ select_multiple Select the interfaces where no OSPF packets should be sent. - - ospf.redistribute - - select_multiple - Select other routing sources to redistribute to other nodes. - - - ospf.redistributemap - - dropdown - Route Map to set for Redistribution, can be used to send a specific network as advertisement when it is defined in a Prefix List attached to a Route Map. - ospf.logadjacencychanges diff --git a/net/frr/src/opnsense/mvc/app/controllers/OPNsense/Quagga/forms/ospf6.xml b/net/frr/src/opnsense/mvc/app/controllers/OPNsense/Quagga/forms/ospf6.xml index 5432da38f..8b4b01455 100644 --- a/net/frr/src/opnsense/mvc/app/controllers/OPNsense/Quagga/forms/ospf6.xml +++ b/net/frr/src/opnsense/mvc/app/controllers/OPNsense/Quagga/forms/ospf6.xml @@ -11,18 +11,6 @@ checkbox Register CARP status monitor. When no neighbors are found, consider this node less attractive. Requires syslog enabled with “Debugging” logging. Incompatible with “Enable CARP Failover”. - - ospf6.redistribute - - select_multiple - Select other routing sources to redistribute to other nodes. - - - ospf6.redistributemap - - dropdown - Route Map to set for Redistribution, can be used to send a specific network as advertisement when it is defined in a Prefix List attached to a Route Map. - ospf6.routerid diff --git a/net/frr/src/opnsense/mvc/app/models/OPNsense/Quagga/BGP.xml b/net/frr/src/opnsense/mvc/app/models/OPNsense/Quagga/BGP.xml index 88f5e92bd..108c85714 100644 --- a/net/frr/src/opnsense/mvc/app/models/OPNsense/Quagga/BGP.xml +++ b/net/frr/src/opnsense/mvc/app/models/OPNsense/Quagga/BGP.xml @@ -1,7 +1,7 @@ //OPNsense/quagga/bgp BGP Routing configuration - 1.0.9 + 1.1.0 0 @@ -37,18 +37,6 @@ N - - N - Y - - - Open Shortest Path First (OSPF) - Connected routes (directly attached subnet or host) - Kernel routes (not installed via the zebra RIB) - Routing Information Protocol (RIP) - Statically configured routes - - @@ -493,5 +481,36 @@ + + + + 1 + Y + + + + Y + connected + + Open Shortest Path First (OSPF) + Connected routes (directly attached subnet or host) + Kernel routes (not installed via the zebra RIB) + Routing Information Protocol (RIP) + Statically configured routes + + + + + + + Related Route-Map item not found + + + diff --git a/net/frr/src/opnsense/mvc/app/models/OPNsense/Quagga/Migrations/M1_1_0.php b/net/frr/src/opnsense/mvc/app/models/OPNsense/Quagga/Migrations/M1_1_0.php new file mode 100644 index 000000000..9bcb8a2b7 --- /dev/null +++ b/net/frr/src/opnsense/mvc/app/models/OPNsense/Quagga/Migrations/M1_1_0.php @@ -0,0 +1,96 @@ +object(); + + if ($model->getNodeByReference('redistributions') === null) { + $model->addChild('redistributions'); + } + $redistributions = $model->getNodeByReference('redistributions.redistribution'); + + // We migrate multiple models at the same time + $protocols = ['bgp', 'ospf', 'ospf6']; + + foreach ($protocols as $protocol) { + if (isset($config->OPNsense->quagga->{$protocol})) { + $this->migrateRedistribute( + $redistributions, + $config->OPNsense->quagga->{$protocol}, + $protocol + ); + } + } + } + + private function migrateRedistribute($redistributions, $configNode, $protocol) + { + if (!$configNode || empty($configNode->redistribute)) { + return; + } + + $redistributeValues = explode(',', (string)$configNode->redistribute); + $redistributemap = isset($configNode->redistributemap) ? (string)$configNode->redistributemap : ''; + + if ($redistributions === null) { + $redistributions = $model->addChild('redistributions'); + } + + // Collect existing redistribution values to prevent duplicates + $existingRedistributions = []; + foreach ($redistributions->iterateItems() as $existing) { + if (!empty((string)$existing->redistribute)) { + $existingRedistributions[] = (string)$existing->redistribute; + } + } + + foreach ($redistributeValues as $value) { + $value = trim($value); + if (empty($value) || in_array($value, $existingRedistributions, true)) { + continue; + } + + // Create a new redistribution entry + $redistributionNode = $redistributions->add(); + $redistributionNode->enabled = '1'; + $redistributionNode->description = "Migrated route redistribution ($protocol)"; + $redistributionNode->redistribute = $value; + $redistributionNode->linkedRoutemap = !empty($redistributemap) ? $redistributemap : ''; + } + } + + // Model is saved by 'run_migrations.php' +} diff --git a/net/frr/src/opnsense/mvc/app/models/OPNsense/Quagga/OSPF.xml b/net/frr/src/opnsense/mvc/app/models/OPNsense/Quagga/OSPF.xml index 755d553c7..1fa0885e6 100644 --- a/net/frr/src/opnsense/mvc/app/models/OPNsense/Quagga/OSPF.xml +++ b/net/frr/src/opnsense/mvc/app/models/OPNsense/Quagga/OSPF.xml @@ -1,7 +1,7 @@ //OPNsense/quagga/ospf OSPF Routing configuration - 1.0.5 + 1.1.0 0 @@ -49,31 +49,6 @@ /^(?!0).*$/ - - N - Y - - - Border Gateway Protocol (BGP) - Connected routes (directly attached subnet or host) - Kernel routes (not installed via the zebra RIB) - Routing Information Protocol (RIP) - Statically configured routes - - - - - - - Related Route-Map item not found - N - N - @@ -311,5 +286,36 @@ + + + + 1 + Y + + + + Y + connected + + Open Shortest Path First (OSPF) + Connected routes (directly attached subnet or host) + Kernel routes (not installed via the zebra RIB) + Routing Information Protocol (RIP) + Statically configured routes + + + + + + + Related Route-Map item not found + + + diff --git a/net/frr/src/opnsense/mvc/app/models/OPNsense/Quagga/OSPF6.xml b/net/frr/src/opnsense/mvc/app/models/OPNsense/Quagga/OSPF6.xml index 5bd6613ac..3e2675ece 100644 --- a/net/frr/src/opnsense/mvc/app/models/OPNsense/Quagga/OSPF6.xml +++ b/net/frr/src/opnsense/mvc/app/models/OPNsense/Quagga/OSPF6.xml @@ -1,7 +1,7 @@ //OPNsense/quagga/ospf6 OSPFv3 Routing configuration - 1.0.4 + 1.1.0 0 @@ -11,25 +11,6 @@ 0 Y - - Y - - Connected routes (directly attached subnet or host) - Kernel routes (not installed via the zebra RIB) - Statically configured routes - - - - - - - Related Route-Map item not found - /^\d{1,3}\.\d{1,3}\.\d{1,3}\.\d{1,3}$/ @@ -224,5 +205,36 @@ + + + + 1 + Y + + + + Y + connected + + Open Shortest Path First (OSPF) + Connected routes (directly attached subnet or host) + Kernel routes (not installed via the zebra RIB) + Routing Information Protocol (RIP) + Statically configured routes + + + + + + + Related Route-Map item not found + + + diff --git a/net/frr/src/opnsense/mvc/app/views/OPNsense/Quagga/bgp.volt b/net/frr/src/opnsense/mvc/app/views/OPNsense/Quagga/bgp.volt index a1835c598..04c561ca9 100644 --- a/net/frr/src/opnsense/mvc/app/views/OPNsense/Quagga/bgp.volt +++ b/net/frr/src/opnsense/mvc/app/views/OPNsense/Quagga/bgp.volt @@ -95,9 +95,42 @@ POSSIBILITY OF SUCH DAMAGE. 'del':'/api/quagga/bgp/delPeergroup/', 'toggle':'/api/quagga/bgp/togglePeergroup/' }); + $("#{{formGridEditRedistribution['table_id']}}").UIBootgrid({ + 'search':'/api/quagga/bgp/searchRedistribution', + 'get':'/api/quagga/bgp/getRedistribution/', + 'set':'/api/quagga/bgp/setRedistribution/', + 'add':'/api/quagga/bgp/addRedistribution/', + 'del':'/api/quagga/bgp/delRedistribution/', + 'toggle':'/api/quagga/bgp/toggleRedistribution/' + }); + + const $header = $(".bootgrid-header[id*='{{formGridEditRedistribution['table_id']}}']"); + if ($header.length) { + $header.find("div.actionBar").parent().prepend( + '' + + '' + + '{{ lang._("Route Redistribution") }}' + + '' + ); + } + }); + +