From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: <pve-devel-bounces@lists.proxmox.com> Received: from firstgate.proxmox.com (firstgate.proxmox.com [212.224.123.68]) by lore.proxmox.com (Postfix) with ESMTPS id A9F581FF15E for <inbox@lore.proxmox.com>; Tue, 25 Mar 2025 16:13:44 +0100 (CET) Received: from firstgate.proxmox.com (localhost [127.0.0.1]) by firstgate.proxmox.com (Proxmox) with ESMTP id 210DECB93; Tue, 25 Mar 2025 16:13:10 +0100 (CET) From: Daniel Kral <d.kral@proxmox.com> To: pve-devel@lists.proxmox.com Date: Tue, 25 Mar 2025 16:12:43 +0100 Message-Id: <20250325151254.193177-6-d.kral@proxmox.com> X-Mailer: git-send-email 2.39.5 In-Reply-To: <20250325151254.193177-1-d.kral@proxmox.com> References: <20250325151254.193177-1-d.kral@proxmox.com> MIME-Version: 1.0 X-SPAM-LEVEL: Spam detection results: 0 AWL 0.010 Adjusted score from AWL reputation of From: address BAYES_00 -1.9 Bayes spam probability is 0 to 1% DMARC_MISSING 0.1 Missing DMARC policy KAM_DMARC_STATUS 0.01 Test Rule for DKIM or SPF Failure with Strict Alignment SPF_HELO_NONE 0.001 SPF: HELO does not publish an SPF Record SPF_PASS -0.001 SPF: sender matches SPF record Subject: [pve-devel] [PATCH ha-manager 04/15] add rules section config base plugin X-BeenThere: pve-devel@lists.proxmox.com X-Mailman-Version: 2.1.29 Precedence: list List-Id: Proxmox VE development discussion <pve-devel.lists.proxmox.com> List-Unsubscribe: <https://lists.proxmox.com/cgi-bin/mailman/options/pve-devel>, <mailto:pve-devel-request@lists.proxmox.com?subject=unsubscribe> List-Archive: <http://lists.proxmox.com/pipermail/pve-devel/> List-Post: <mailto:pve-devel@lists.proxmox.com> List-Help: <mailto:pve-devel-request@lists.proxmox.com?subject=help> List-Subscribe: <https://lists.proxmox.com/cgi-bin/mailman/listinfo/pve-devel>, <mailto:pve-devel-request@lists.proxmox.com?subject=subscribe> Reply-To: Proxmox VE development discussion <pve-devel@lists.proxmox.com> Content-Type: text/plain; charset="us-ascii" Content-Transfer-Encoding: 7bit Errors-To: pve-devel-bounces@lists.proxmox.com Sender: "pve-devel" <pve-devel-bounces@lists.proxmox.com> Add a rules section config base plugin to allow users to specify different kinds of rules in a single configuration file. The interface is designed to allow sub plugins to implement their own {decode,encode}_value() methods and also offer a canonicalized version of their rules with canonicalize(), i.e. with any inconsistencies removed and ambiguities resolved. There is also a are_satisfiable() method for anticipation of the verification of additions or changes to the rules config via the API. Signed-off-by: Daniel Kral <d.kral@proxmox.com> --- debian/pve-ha-manager.install | 1 + src/PVE/HA/Makefile | 2 +- src/PVE/HA/Rules.pm | 118 ++++++++++++++++++++++++++++++++++ src/PVE/HA/Tools.pm | 5 ++ 4 files changed, 125 insertions(+), 1 deletion(-) create mode 100644 src/PVE/HA/Rules.pm diff --git a/debian/pve-ha-manager.install b/debian/pve-ha-manager.install index 0ffbd8d..9bbd375 100644 --- a/debian/pve-ha-manager.install +++ b/debian/pve-ha-manager.install @@ -32,6 +32,7 @@ /usr/share/perl5/PVE/HA/Resources.pm /usr/share/perl5/PVE/HA/Resources/PVECT.pm /usr/share/perl5/PVE/HA/Resources/PVEVM.pm +/usr/share/perl5/PVE/HA/Rules.pm /usr/share/perl5/PVE/HA/Tools.pm /usr/share/perl5/PVE/HA/Usage.pm /usr/share/perl5/PVE/HA/Usage/Basic.pm diff --git a/src/PVE/HA/Makefile b/src/PVE/HA/Makefile index 8c91b97..489cbc0 100644 --- a/src/PVE/HA/Makefile +++ b/src/PVE/HA/Makefile @@ -1,4 +1,4 @@ -SIM_SOURCES=CRM.pm Env.pm Groups.pm Resources.pm LRM.pm Manager.pm \ +SIM_SOURCES=CRM.pm Env.pm Groups.pm Rules.pm Resources.pm LRM.pm Manager.pm \ NodeStatus.pm Tools.pm FenceConfig.pm Fence.pm Usage.pm SOURCES=${SIM_SOURCES} Config.pm diff --git a/src/PVE/HA/Rules.pm b/src/PVE/HA/Rules.pm new file mode 100644 index 0000000..bff3375 --- /dev/null +++ b/src/PVE/HA/Rules.pm @@ -0,0 +1,118 @@ +package PVE::HA::Rules; + +use strict; +use warnings; + +use PVE::JSONSchema qw(get_standard_option); +use PVE::SectionConfig; +use PVE::HA::Tools; + +use base qw(PVE::SectionConfig); + +# TODO Add descriptions, completions, etc. +my $defaultData = { + propertyList => { + type => { description => "Rule type." }, + ruleid => get_standard_option('pve-ha-rule-id'), + comment => { + type => 'string', + maxLength => 4096, + description => "Rule description.", + }, + }, +}; + +sub private { + return $defaultData; +} + +sub options { + return { + type => { optional => 0 }, + ruleid => { optional => 0 }, + comment => { optional => 1 }, + }; +}; + +sub decode_value { + my ($class, $type, $key, $value) = @_; + + if ($key eq 'comment') { + return PVE::Tools::decode_text($value); + } + + my $plugin = __PACKAGE__->lookup($type); + return $plugin->decode_value($type, $key, $value); +} + +sub encode_value { + my ($class, $type, $key, $value) = @_; + + if ($key eq 'comment') { + return PVE::Tools::encode_text($value); + } + + my $plugin = __PACKAGE__->lookup($type); + return $plugin->encode_value($type, $key, $value); +} + +sub parse_section_header { + my ($class, $line) = @_; + + if ($line =~ m/^(\S+):\s*(\S+)\s*$/) { + my ($type, $ruleid) = (lc($1), $2); + my $errmsg = undef; # set if you want to skip whole section + eval { PVE::JSONSchema::pve_verify_configid($ruleid); }; + $errmsg = $@ if $@; + my $config = {}; # to return additional attributes + return ($type, $ruleid, $errmsg, $config); + } + return undef; +} + +sub foreach_service_rule { + my ($rules, $func, $opts) = @_; + + my $sid = $opts->{sid}; + my $type = $opts->{type}; + + my @ruleids = sort { + $rules->{order}->{$a} <=> $rules->{order}->{$b} + } keys %{$rules->{ids}}; + + for my $ruleid (@ruleids) { + my $rule = $rules->{ids}->{$ruleid}; + + next if !$rule; # invalid rules are kept undef in section config, delete them + next if $type && $rule->{type} ne $type; + next if $sid && !defined($rule->{services}->{$sid}); + + $func->($rule, $ruleid); + } +} + +sub canonicalize { + my ($class, $rules, $groups, $services) = @_; + + die "implement in subclass"; +} + +sub are_satisfiable { + my ($class, $rules, $groups, $services) = @_; + + die "implement in subclass"; +} + +sub checked_config { + my ($rules, $groups, $services) = @_; + + my $types = __PACKAGE__->lookup_types(); + + for my $type (@$types) { + my $plugin = __PACKAGE__->lookup($type); + + $plugin->canonicalize($rules, $groups, $services); + } +} + +1; diff --git a/src/PVE/HA/Tools.pm b/src/PVE/HA/Tools.pm index fc3282c..35107c9 100644 --- a/src/PVE/HA/Tools.pm +++ b/src/PVE/HA/Tools.pm @@ -92,6 +92,11 @@ PVE::JSONSchema::register_standard_option('pve-ha-group-id', { type => 'string', format => 'pve-configid', }); +PVE::JSONSchema::register_standard_option('pve-ha-rule-id', { + description => "The HA rule identifier.", + type => 'string', format => 'pve-configid', +}); + sub read_json_from_file { my ($filename, $default) = @_; -- 2.39.5 _______________________________________________ pve-devel mailing list pve-devel@lists.proxmox.com https://lists.proxmox.com/cgi-bin/mailman/listinfo/pve-devel