diff --git a/changelogs/fragments/217_pfsense_setup_webguicert.yml b/changelogs/fragments/217_pfsense_setup_webguicert.yml new file mode 100644 index 00000000..3ea44f03 --- /dev/null +++ b/changelogs/fragments/217_pfsense_setup_webguicert.yml @@ -0,0 +1,2 @@ +minor_changes: + - pfsense_setup - add ``webguicert`` parameter (https://github.com/pfsensible/core/pull/217). diff --git a/plugins/module_utils/arg_route.py b/plugins/module_utils/arg_route.py index c1703962..063b65f8 100644 --- a/plugins/module_utils/arg_route.py +++ b/plugins/module_utils/arg_route.py @@ -7,8 +7,12 @@ __metaclass__ = type -# NOTE - Ansible sets unsepecified parameters to None, so these functions -# must be able to handle the case where params[name] is None +# module_base _params_to_obj currently does not call thse functions if +# params[name] is None. + +def p2o_cert(self, name, params, obj): + obj[name] = self.pfsense.get_certref(params[name]) + def p2o_interface(self, name, params, obj): obj[name] = self.pfsense.parse_interface(params[name], with_virtual=True) diff --git a/plugins/module_utils/arg_validate.py b/plugins/module_utils/arg_validate.py new file mode 100644 index 00000000..5dea6061 --- /dev/null +++ b/plugins/module_utils/arg_validate.py @@ -0,0 +1,13 @@ +# -*- coding: utf-8 -*- + +# Copyright: (c) 2025, Orion Poplawski +# GNU General Public License v3.0+ (see COPYING or https://www.gnu.org/licenses/gpl-3.0.txt) + +from __future__ import (absolute_import, division, print_function) +__metaclass__ = type + + +# TODO - allow specifying type of cert, e.g. HTTPS +def validate_cert(self, cert): + if self.pfsense.get_certref(cert) is None: + raise ValueError(f"Unknown certificate '{cert}'.") diff --git a/plugins/module_utils/module_base.py b/plugins/module_utils/module_base.py index f9f29495..4ea4a0e2 100644 --- a/plugins/module_utils/module_base.py +++ b/plugins/module_utils/module_base.py @@ -209,7 +209,7 @@ def _params_to_obj(self, obj=None): force = True # If we have defined a parser for this arg, use it - if param in self.arg_route and 'parse' in self.arg_route[param]: + if param in self.arg_route and 'parse' in self.arg_route[param] and self.params.get(param) is not None: self.arg_route[param]['parse'](self, param, self.params, obj) elif self.argument_spec[param].get('type') == 'bool': if param in self.bool_values: diff --git a/plugins/modules/pfsense_setup.py b/plugins/modules/pfsense_setup.py index 4ce46e6c..e3f6ef1d 100644 --- a/plugins/modules/pfsense_setup.py +++ b/plugins/modules/pfsense_setup.py @@ -71,6 +71,11 @@ type: str choices: ['bs', 'de_DE', 'en_US', 'es_AR', 'es_ES', 'fr_FR', 'it_IT', 'ko_FR', 'nb_NO', 'nl_NL', 'pl_PL', 'pt_BR', 'pt_PT', 'ru_RU', 'zh_CN', 'zh_Hans_CN', 'zh_Hans_HK', 'zh_Hant_TW'] + webguicert: + description: SSL/TLS certificate for the web GUI. + required: false + type: str + version_added: 0.7.2 webguicss: description: > Choose an alternative CSS file (if installed) to change the appearance of the webConfigurator. Custom themes are also supported. @@ -178,6 +183,8 @@ from os import listdir from os.path import isfile, join from ansible.module_utils.basic import AnsibleModule +from ansible_collections.pfsensible.core.plugins.module_utils.arg_route import p2o_cert +from ansible_collections.pfsensible.core.plugins.module_utils.arg_validate import validate_cert from ansible_collections.pfsensible.core.plugins.module_utils.module_config_base import PFSenseModuleConfigBase @@ -206,6 +213,7 @@ session_timeout=dict(required=False, type='int'), authmode=dict(required=False, type='str'), shellauth=dict(required=False, type='bool'), + webguicert=dict(required=False, type='str'), webguicss=dict(required=False, type='str'), webguifixedmenu=dict(required=False, type='bool'), webguihostnamemenu=dict(required=False, type='str', choices=['nohost', 'hostonly', 'fqdn']), @@ -254,6 +262,7 @@ def validate_webguicss(self, webguicss): SETUP_ARG_ROUTE = dict( dnslocalhost=dict(parse=p2o_dnslocalhost), + webguicert=dict(parse=p2o_cert, validate=validate_cert), webguicss=dict(parse=p2o_webguicss, validate=validate_webguicss), ) @@ -277,6 +286,7 @@ def validate_webguicss(self, webguicss): ('statusmonitoringsettingspanel', 'webgui/statusmonitoringsettingspanel'), ('systemlogsfilterpanel', 'webgui/systemlogsfilterpanel'), ('systemlogsmanagelogpanel', 'webgui/systemlogsmanagelogpanel'), + ('webguicert', 'webgui/ssl-certref'), ('webguicss', 'webgui/webguicss'), ('webguifixedmenu', 'webgui/webguifixedmenu'), ('webguihostnamemenu', 'webgui/webguihostnamemenu'), @@ -493,6 +503,7 @@ def _update(self): cmd = ''' require_once("auth.inc"); require_once("filter.inc"); +require_once("system_advanced_admin.inc"); $retval = 0; $retval |= system_hostname_configure(); $retval |= system_hosts_generate(); @@ -515,6 +526,14 @@ def _update(self): cmd += '$retval |= filter_configure();\n' + restart_webgui = False + for param in ['ssl-certref']: + if self.obj['webgui'].get(param) != self.diff['before']['webgui'].get(param): + restart_webgui = True + if restart_webgui: + cmd += 'restart_GUI();\n' + + self.result['cmd'] = cmd return self.pfsense.phpshell(cmd) ############################## @@ -548,6 +567,7 @@ def _log_fields(self, before=None): values += self.format_updated_cli_field(self.obj, self.diff['before'], 'dnsallowoverride', fvalue=self.fvalue_bool, add_comma=(values), log_none=False) values += self.format_updated_cli_field(self.obj, self.diff['before'], 'dnslocalhost', add_comma=(values), log_none=False) + values += self.format_updated_cli_field(obj_after, obj_before, 'webguicert', add_comma=(values), log_none=False) values += self.format_updated_cli_field(obj_after, obj_before, 'webguicss', add_comma=(values), log_none=False) values += self.format_updated_cli_field(webgui, bwebgui, 'webguifixedmenu', fvalue=self.fvalue_bool, add_comma=(values), log_none=False) values += self.format_updated_cli_field(webgui, bwebgui, 'webguihostnamemenu', add_comma=(values), log_none=False)