From 5bf6256367aea435ba25714d7229065958d1dee5 Mon Sep 17 00:00:00 2001 From: Ad Schellevis Date: Mon, 19 Sep 2022 18:26:48 +0200 Subject: [PATCH] Interfaces/Other Types/VLAN - user configurable device names. closes https://github.com/opnsense/core/issues/6038 --- .../Interfaces/Api/VlanSettingsController.php | 7 ++-- .../OPNsense/Interfaces/forms/dialogVlan.xml | 7 +++- .../app/models/OPNsense/Interfaces/Vlan.php | 36 +++++++++++++++++++ 3 files changed, 47 insertions(+), 3 deletions(-) diff --git a/src/opnsense/mvc/app/controllers/OPNsense/Interfaces/Api/VlanSettingsController.php b/src/opnsense/mvc/app/controllers/OPNsense/Interfaces/Api/VlanSettingsController.php index 64429c477..978e14a5c 100644 --- a/src/opnsense/mvc/app/controllers/OPNsense/Interfaces/Api/VlanSettingsController.php +++ b/src/opnsense/mvc/app/controllers/OPNsense/Interfaces/Api/VlanSettingsController.php @@ -42,7 +42,10 @@ class VlanSettingsController extends ApiMutableModelControllerBase { $tmp = $this->request->getPost('vlan'); $prefix = (strpos($tmp['if'], 'vlan') === false ? 'vlan' : 'qinq'); - if ($current != null && (string)$current->vlanif == "{$tmp['if']}_vlan{$tmp['tag']}") { + if (!empty($tmp['vlanif'])) { + // user provided vlan name, field validation applies so we may just paste it in here + return $tmp['vlanif']; + } elseif ($current != null && (string)$current->vlanif == "{$tmp['if']}_vlan{$tmp['tag']}") { /* keep legacy naming */ return "{$tmp['if']}_vlan{$tmp['tag']}"; } elseif ( @@ -55,7 +58,7 @@ class VlanSettingsController extends ApiMutableModelControllerBase /* auto-number new device */ $ifid = 0; foreach ($this->getModel()->vlan->iterateItems() as $node) { - if (strpos((string)$node->vlanif, $prefix) === 0) { + if (preg_match("/^({$prefix})(\d)*$/i",(string)$node->vlanif)) { $ifid = max($ifid, (int)filter_var((string)$node->vlanif, FILTER_SANITIZE_NUMBER_INT)); } } diff --git a/src/opnsense/mvc/app/controllers/OPNsense/Interfaces/forms/dialogVlan.xml b/src/opnsense/mvc/app/controllers/OPNsense/Interfaces/forms/dialogVlan.xml index d97c5160d..b6580c217 100644 --- a/src/opnsense/mvc/app/controllers/OPNsense/Interfaces/forms/dialogVlan.xml +++ b/src/opnsense/mvc/app/controllers/OPNsense/Interfaces/forms/dialogVlan.xml @@ -2,7 +2,12 @@ vlan.vlanif - info + text + + Leave empty to generate a device name for you. Custom names are possible, + but only if the start of the name matches the type and contains standard alphanumeric characters + or underscores (e.g. vlan_1_2_3, qinq_1_2_3). + vlan.if diff --git a/src/opnsense/mvc/app/models/OPNsense/Interfaces/Vlan.php b/src/opnsense/mvc/app/models/OPNsense/Interfaces/Vlan.php index 83709376f..37d96aca4 100644 --- a/src/opnsense/mvc/app/models/OPNsense/Interfaces/Vlan.php +++ b/src/opnsense/mvc/app/models/OPNsense/Interfaces/Vlan.php @@ -28,8 +28,44 @@ namespace OPNsense\Interfaces; +use Phalcon\Messages\Message; use OPNsense\Base\BaseModel; class Vlan extends BaseModel { + /** + * {@inheritdoc} + */ + public function performValidation($validateFullModel = false) + { + $messages = parent::performValidation($validateFullModel); + $all_nodes = $this->getFlatNodes(); + foreach ($all_nodes as $key => $node) { + if ($validateFullModel || $node->isFieldChanged()) { + // the item container may have different validations attached. + $parent = $node->getParentNode(); + // perform plugin specific validations + switch ($node->getInternalXMLTagName()) { + case 'vlanif': + $prefix = (strpos((string)$parent->if, 'vlan') === false ? 'vlan' : 'qinq'); + if ((string)$node == "{$parent->if}_vlan{$parent->tag}") { + // legacy device name + break; + } elseif (!(strpos((string)$node, (string)$prefix) === 0)) { + $messages->appendMessage(new Message( + sprintf(gettext("device name does not match type (e.g. %s_xxx)."), (string)$prefix) , + $key + )); + } elseif (!preg_match("/^([a-zA-Z0-9_]){1,16}$/", (string)$node)) { + $messages->appendMessage(new Message( + gettext("Invalid device name, only up to 16 alphanumeric characters are supported."), + $key + )); + } + break; + } + } + } + return $messages; + } }