From 5dea7ec50434d0d9bd1449c5a458d7f2b48e1ffc Mon Sep 17 00:00:00 2001 From: Oliver Tappe Date: Fri, 4 Jan 2008 00:28:45 +0000 Subject: more work at refactoring of the way attributes are handled: * finished and integrated support for declaring known attributes from within plugins (they need to install a AttrInfo module) * implemented support for checking which attributes are applicable to systems and clients respectively * adjusted slxconfig to new attribute handling (systems only at the moment) git-svn-id: http://svn.openslx.org/svn/openslx/trunk@1442 95ad53e4-c205-0410-b2fa-d234c58c8868 --- config-db/OpenSLX/AttrInfo/Core.pm | 651 +++++++++++++++++++------------------ config-db/OpenSLX/ConfigDB.pm | 168 ++++++++-- config-db/OpenSLX/DBSchema.pm | 41 ++- config-db/OpenSLX/MetaDB/DBI.pm | 115 +++++-- 4 files changed, 587 insertions(+), 388 deletions(-) (limited to 'config-db') diff --git a/config-db/OpenSLX/AttrInfo/Core.pm b/config-db/OpenSLX/AttrInfo/Core.pm index a1c06019..9716fb34 100644 --- a/config-db/OpenSLX/AttrInfo/Core.pm +++ b/config-db/OpenSLX/AttrInfo/Core.pm @@ -18,331 +18,336 @@ use warnings; use OpenSLX::Utils; -use vars qw(@ISA @EXPORT $VERSION %AttrInfo); +sub new +{ + my $class = shift; -use Exporter; -$VERSION = 1.01; -@ISA = qw(Exporter); + my $self = { + }; -@EXPORT = qw( %AttrInfo ); + return bless $self, $class; +} -%AttrInfo = ( - 'automnt_dir' => { - applies_to_systems => 1, - applies_to_clients => 1, - description => unshiftHereDoc(<<' End-of-Here'), - !!!descriptive text missing here!!! - End-of-Here - content_regex => undef, - content_descr => undef, - }, - 'automnt_src' => { - applies_to_systems => 1, - applies_to_clients => 1, - description => unshiftHereDoc(<<' End-of-Here'), - !!!descriptive text missing here!!! - End-of-Here - content_regex => undef, - content_descr => undef, - }, - 'country' => { - applies_to_systems => 1, - applies_to_clients => 1, - description => unshiftHereDoc(<<' End-of-Here'), - !!!descriptive text missing here!!! - End-of-Here - content_regex => undef, - content_descr => undef, - }, - 'dm_allow_shutdown' => { - applies_to_systems => 1, - applies_to_clients => 1, - description => unshiftHereDoc(<<' End-of-Here'), - !!!descriptive text missing here!!! - End-of-Here - content_regex => undef, - content_descr => undef, - }, - 'hw_graphic' => { - applies_to_systems => 1, - applies_to_clients => 1, - description => unshiftHereDoc(<<' End-of-Here'), - !!!descriptive text missing here!!! - End-of-Here - content_regex => undef, - content_descr => undef, - }, - 'hw_monitor' => { - applies_to_systems => 1, - applies_to_clients => 1, - description => unshiftHereDoc(<<' End-of-Here'), - !!!descriptive text missing here!!! - End-of-Here - content_regex => undef, - content_descr => undef, - }, - 'hw_mouse' => { - applies_to_systems => 1, - applies_to_clients => 1, - description => unshiftHereDoc(<<' End-of-Here'), - !!!descriptive text missing here!!! - End-of-Here - content_regex => undef, - content_descr => undef, - }, - 'late_dm' => { - applies_to_systems => 1, - applies_to_clients => 1, - description => unshiftHereDoc(<<' End-of-Here'), - !!!descriptive text missing here!!! - End-of-Here - content_regex => undef, - content_descr => undef, - }, - 'netbios_workgroup' => { - applies_to_systems => 1, - applies_to_clients => 1, - description => unshiftHereDoc(<<' End-of-Here'), - !!!descriptive text missing here!!! - End-of-Here - content_regex => undef, - content_descr => undef, - }, - 'nis_domain' => { - applies_to_systems => 1, - applies_to_clients => 1, - description => unshiftHereDoc(<<' End-of-Here'), - !!!descriptive text missing here!!! - End-of-Here - content_regex => undef, - content_descr => undef, - }, - 'nis_servers' => { - applies_to_systems => 1, - applies_to_clients => 1, - description => unshiftHereDoc(<<' End-of-Here'), - !!!descriptive text missing here!!! - End-of-Here - content_regex => undef, - content_descr => undef, - }, - 'sane_scanner' => { - applies_to_systems => 1, - applies_to_clients => 1, - description => unshiftHereDoc(<<' End-of-Here'), - !!!descriptive text missing here!!! - End-of-Here - content_regex => undef, - content_descr => undef, - }, - 'scratch' => { - applies_to_systems => 1, - applies_to_clients => 1, - description => unshiftHereDoc(<<' End-of-Here'), - !!!descriptive text missing here!!! - End-of-Here - content_regex => undef, - content_descr => undef, - }, - 'slxgrp' => { - applies_to_systems => 1, - applies_to_clients => 1, - description => unshiftHereDoc(<<' End-of-Here'), - !!!descriptive text missing here!!! - End-of-Here - content_regex => undef, - content_descr => undef, - }, - 'start_alsasound' => { - applies_to_systems => 1, - applies_to_clients => 1, - description => unshiftHereDoc(<<' End-of-Here'), - !!!descriptive text missing here!!! - End-of-Here - content_regex => undef, - content_descr => undef, - }, - 'start_atd' => { - applies_to_systems => 1, - applies_to_clients => 1, - description => unshiftHereDoc(<<' End-of-Here'), - !!!descriptive text missing here!!! - End-of-Here - content_regex => undef, - content_descr => undef, - }, - 'start_cron' => { - applies_to_systems => 1, - applies_to_clients => 1, - description => unshiftHereDoc(<<' End-of-Here'), - !!!descriptive text missing here!!! - End-of-Here - content_regex => undef, - content_descr => undef, - }, - 'start_dreshal' => { - applies_to_systems => 1, - applies_to_clients => 1, - description => unshiftHereDoc(<<' End-of-Here'), - !!!descriptive text missing here!!! - End-of-Here - content_regex => undef, - content_descr => undef, - }, - 'start_ntp' => { - applies_to_systems => 1, - applies_to_clients => 1, - description => unshiftHereDoc(<<' End-of-Here'), - !!!descriptive text missing here!!! - End-of-Here - content_regex => undef, - content_descr => undef, - }, - 'start_nfsv4' => { - applies_to_systems => 1, - applies_to_clients => 1, - description => unshiftHereDoc(<<' End-of-Here'), - !!!descriptive text missing here!!! - End-of-Here - content_regex => undef, - content_descr => undef, - }, - 'start_printer' => { - applies_to_systems => 1, - applies_to_clients => 1, - description => unshiftHereDoc(<<' End-of-Here'), - !!!descriptive text missing here!!! - End-of-Here - content_regex => undef, - content_descr => undef, - }, - 'start_samba' => { - applies_to_systems => 1, - applies_to_clients => 1, - description => unshiftHereDoc(<<' End-of-Here'), - !!!descriptive text missing here!!! - End-of-Here - content_regex => undef, - content_descr => undef, - }, - 'start_snmp' => { - applies_to_systems => 1, - applies_to_clients => 1, - description => unshiftHereDoc(<<' End-of-Here'), - !!!descriptive text missing here!!! - End-of-Here - content_regex => undef, - content_descr => undef, - }, - 'start_sshd' => { - applies_to_systems => 1, - applies_to_clients => 1, - description => unshiftHereDoc(<<' End-of-Here'), - !!!descriptive text missing here!!! - End-of-Here - content_regex => undef, - content_descr => undef, - }, - 'start_syslogd' => { - applies_to_systems => 1, - applies_to_clients => 1, - description => unshiftHereDoc(<<' End-of-Here'), - !!!descriptive text missing here!!! - End-of-Here - content_regex => undef, - content_descr => undef, - }, - 'start_x' => { - applies_to_systems => 1, - applies_to_clients => 1, - description => unshiftHereDoc(<<' End-of-Here'), - !!!descriptive text missing here!!! - End-of-Here - content_regex => undef, - content_descr => undef, - }, - 'start_xdmcp' => { - applies_to_systems => 1, - applies_to_clients => 1, - description => unshiftHereDoc(<<' End-of-Here'), - !!!descriptive text missing here!!! - End-of-Here - content_regex => undef, - content_descr => undef, - }, - 'tex_enable' => { - applies_to_systems => 1, - applies_to_clients => 1, - description => unshiftHereDoc(<<' End-of-Here'), - !!!descriptive text missing here!!! - End-of-Here - content_regex => undef, - content_descr => undef, - }, - 'timezone' => { - applies_to_systems => 1, - applies_to_clients => 1, - description => unshiftHereDoc(<<' End-of-Here'), - textual timezone (e.g. 'Europe/Berlin') - End-of-Here - content_regex => undef, - content_descr => undef, - }, - 'tvout' => { - applies_to_systems => 1, - applies_to_clients => 1, - description => unshiftHereDoc(<<' End-of-Here'), - !!!descriptive text missing here!!! - End-of-Here - content_regex => undef, - content_descr => undef, - }, - 'vmware' => { - applies_to_systems => 1, - applies_to_clients => 1, - description => unshiftHereDoc(<<' End-of-Here'), - !!!descriptive text missing here!!! - End-of-Here - content_regex => undef, - content_descr => undef, - }, - - 'ramfs_fsmods' => { - applies_to_systems => 1, - applies_to_clients => 0, - description => unshiftHereDoc(<<' End-of-Here'), - list of filesystem kernel modules to load - End-of-Here - content_regex => undef, - content_descr => undef, - }, - 'ramfs_miscmods' => { - applies_to_systems => 1, - applies_to_clients => 0, - description => unshiftHereDoc(<<' End-of-Here'), - list of miscellaneous kernel modules to load - End-of-Here - content_regex => undef, - content_descr => undef, - }, - 'ramfs_nicmods' => { - applies_to_systems => 1, - applies_to_clients => 0, - description => unshiftHereDoc(<<' End-of-Here'), - list of network card modules to load - End-of-Here - content_regex => undef, - content_descr => undef, - }, - 'ramfs_screen' => { - applies_to_systems => 1, - applies_to_clients => 0, - description => unshiftHereDoc(<<' End-of-Here'), - resolution of splash screen to use in stage3 - End-of-Here - content_regex => undef, - content_descr => undef, - }, -); +sub AttrInfo +{ + return { + 'automnt_dir' => { + applies_to_systems => 1, + applies_to_clients => 1, + description => unshiftHereDoc(<<' End-of-Here'), + !!!descriptive text missing here!!! + End-of-Here + content_regex => undef, + content_descr => undef, + }, + 'automnt_src' => { + applies_to_systems => 1, + applies_to_clients => 1, + description => unshiftHereDoc(<<' End-of-Here'), + !!!descriptive text missing here!!! + End-of-Here + content_regex => undef, + content_descr => undef, + }, + 'country' => { + applies_to_systems => 1, + applies_to_clients => 1, + description => unshiftHereDoc(<<' End-of-Here'), + !!!descriptive text missing here!!! + End-of-Here + content_regex => undef, + content_descr => undef, + }, + 'dm_allow_shutdown' => { + applies_to_systems => 1, + applies_to_clients => 1, + description => unshiftHereDoc(<<' End-of-Here'), + !!!descriptive text missing here!!! + End-of-Here + content_regex => undef, + content_descr => undef, + }, + 'hw_graphic' => { + applies_to_systems => 1, + applies_to_clients => 1, + description => unshiftHereDoc(<<' End-of-Here'), + !!!descriptive text missing here!!! + End-of-Here + content_regex => undef, + content_descr => undef, + }, + 'hw_monitor' => { + applies_to_systems => 1, + applies_to_clients => 1, + description => unshiftHereDoc(<<' End-of-Here'), + !!!descriptive text missing here!!! + End-of-Here + content_regex => undef, + content_descr => undef, + }, + 'hw_mouse' => { + applies_to_systems => 1, + applies_to_clients => 1, + description => unshiftHereDoc(<<' End-of-Here'), + !!!descriptive text missing here!!! + End-of-Here + content_regex => undef, + content_descr => undef, + }, + 'late_dm' => { + applies_to_systems => 1, + applies_to_clients => 1, + description => unshiftHereDoc(<<' End-of-Here'), + !!!descriptive text missing here!!! + End-of-Here + content_regex => undef, + content_descr => undef, + }, + 'netbios_workgroup' => { + applies_to_systems => 1, + applies_to_clients => 1, + description => unshiftHereDoc(<<' End-of-Here'), + !!!descriptive text missing here!!! + End-of-Here + content_regex => undef, + content_descr => undef, + }, + 'nis_domain' => { + applies_to_systems => 1, + applies_to_clients => 1, + description => unshiftHereDoc(<<' End-of-Here'), + !!!descriptive text missing here!!! + End-of-Here + content_regex => undef, + content_descr => undef, + }, + 'nis_servers' => { + applies_to_systems => 1, + applies_to_clients => 1, + description => unshiftHereDoc(<<' End-of-Here'), + !!!descriptive text missing here!!! + End-of-Here + content_regex => undef, + content_descr => undef, + }, + 'sane_scanner' => { + applies_to_systems => 1, + applies_to_clients => 1, + description => unshiftHereDoc(<<' End-of-Here'), + !!!descriptive text missing here!!! + End-of-Here + content_regex => undef, + content_descr => undef, + }, + 'scratch' => { + applies_to_systems => 1, + applies_to_clients => 1, + description => unshiftHereDoc(<<' End-of-Here'), + !!!descriptive text missing here!!! + End-of-Here + content_regex => undef, + content_descr => undef, + }, + 'slxgrp' => { + applies_to_systems => 1, + applies_to_clients => 1, + description => unshiftHereDoc(<<' End-of-Here'), + !!!descriptive text missing here!!! + End-of-Here + content_regex => undef, + content_descr => undef, + }, + 'start_alsasound' => { + applies_to_systems => 1, + applies_to_clients => 1, + description => unshiftHereDoc(<<' End-of-Here'), + !!!descriptive text missing here!!! + End-of-Here + content_regex => undef, + content_descr => undef, + }, + 'start_atd' => { + applies_to_systems => 1, + applies_to_clients => 1, + description => unshiftHereDoc(<<' End-of-Here'), + !!!descriptive text missing here!!! + End-of-Here + content_regex => undef, + content_descr => undef, + }, + 'start_cron' => { + applies_to_systems => 1, + applies_to_clients => 1, + description => unshiftHereDoc(<<' End-of-Here'), + !!!descriptive text missing here!!! + End-of-Here + content_regex => undef, + content_descr => undef, + }, + 'start_dreshal' => { + applies_to_systems => 1, + applies_to_clients => 1, + description => unshiftHereDoc(<<' End-of-Here'), + !!!descriptive text missing here!!! + End-of-Here + content_regex => undef, + content_descr => undef, + }, + 'start_ntp' => { + applies_to_systems => 1, + applies_to_clients => 1, + description => unshiftHereDoc(<<' End-of-Here'), + !!!descriptive text missing here!!! + End-of-Here + content_regex => undef, + content_descr => undef, + }, + 'start_nfsv4' => { + applies_to_systems => 1, + applies_to_clients => 1, + description => unshiftHereDoc(<<' End-of-Here'), + !!!descriptive text missing here!!! + End-of-Here + content_regex => undef, + content_descr => undef, + }, + 'start_printer' => { + applies_to_systems => 1, + applies_to_clients => 1, + description => unshiftHereDoc(<<' End-of-Here'), + !!!descriptive text missing here!!! + End-of-Here + content_regex => undef, + content_descr => undef, + }, + 'start_samba' => { + applies_to_systems => 1, + applies_to_clients => 1, + description => unshiftHereDoc(<<' End-of-Here'), + !!!descriptive text missing here!!! + End-of-Here + content_regex => undef, + content_descr => undef, + }, + 'start_snmp' => { + applies_to_systems => 1, + applies_to_clients => 1, + description => unshiftHereDoc(<<' End-of-Here'), + !!!descriptive text missing here!!! + End-of-Here + content_regex => undef, + content_descr => undef, + }, + 'start_sshd' => { + applies_to_systems => 1, + applies_to_clients => 1, + description => unshiftHereDoc(<<' End-of-Here'), + !!!descriptive text missing here!!! + End-of-Here + content_regex => undef, + content_descr => undef, + }, + 'start_syslogd' => { + applies_to_systems => 1, + applies_to_clients => 1, + description => unshiftHereDoc(<<' End-of-Here'), + !!!descriptive text missing here!!! + End-of-Here + content_regex => undef, + content_descr => undef, + }, + 'start_x' => { + applies_to_systems => 1, + applies_to_clients => 1, + description => unshiftHereDoc(<<' End-of-Here'), + !!!descriptive text missing here!!! + End-of-Here + content_regex => undef, + content_descr => undef, + }, + 'start_xdmcp' => { + applies_to_systems => 1, + applies_to_clients => 1, + description => unshiftHereDoc(<<' End-of-Here'), + !!!descriptive text missing here!!! + End-of-Here + content_regex => undef, + content_descr => undef, + }, + 'tex_enable' => { + applies_to_systems => 1, + applies_to_clients => 1, + description => unshiftHereDoc(<<' End-of-Here'), + !!!descriptive text missing here!!! + End-of-Here + content_regex => undef, + content_descr => undef, + }, + 'timezone' => { + applies_to_systems => 1, + applies_to_clients => 1, + description => unshiftHereDoc(<<' End-of-Here'), + textual timezone (e.g. 'Europe/Berlin') + End-of-Here + content_regex => undef, + content_descr => undef, + }, + 'tvout' => { + applies_to_systems => 1, + applies_to_clients => 1, + description => unshiftHereDoc(<<' End-of-Here'), + !!!descriptive text missing here!!! + End-of-Here + content_regex => undef, + content_descr => undef, + }, + 'vmware' => { + applies_to_systems => 1, + applies_to_clients => 1, + description => unshiftHereDoc(<<' End-of-Here'), + !!!descriptive text missing here!!! + End-of-Here + content_regex => undef, + content_descr => undef, + }, + + 'ramfs_fsmods' => { + applies_to_systems => 1, + applies_to_clients => 0, + description => unshiftHereDoc(<<' End-of-Here'), + list of filesystem kernel modules to load + End-of-Here + content_regex => undef, + content_descr => undef, + }, + 'ramfs_miscmods' => { + applies_to_systems => 1, + applies_to_clients => 0, + description => unshiftHereDoc(<<' End-of-Here'), + list of miscellaneous kernel modules to load + End-of-Here + content_regex => undef, + content_descr => undef, + }, + 'ramfs_nicmods' => { + applies_to_systems => 1, + applies_to_clients => 0, + description => unshiftHereDoc(<<' End-of-Here'), + list of network card modules to load + End-of-Here + content_regex => undef, + content_descr => undef, + }, + 'ramfs_screen' => { + applies_to_systems => 1, + applies_to_clients => 0, + description => unshiftHereDoc(<<' End-of-Here'), + resolution of splash screen to use in stage3 + End-of-Here + content_regex => undef, + content_descr => undef, + }, + }; +} 1; diff --git a/config-db/OpenSLX/ConfigDB.pm b/config-db/OpenSLX/ConfigDB.pm index debbef9c..95183c95 100644 --- a/config-db/OpenSLX/ConfigDB.pm +++ b/config-db/OpenSLX/ConfigDB.pm @@ -104,8 +104,6 @@ use OpenSLX::Utils; =item C Returns an object representing a database handle to the config database. -N.B. this class is implemented as a singleton, so several successive calls to -new will return the *same* object =cut @@ -283,11 +281,57 @@ sub getColumnsOfTable my $self = shift; my $tableName = shift; - return + return map { (/^(\w+)\W/) ? $1 : $_; } @{$DbSchema->{tables}->{$tableName}->{cols}}; } +=item C + +Returns the attribute names that apply to systems. + +=over + +=item Return Value + +An array of attribute names. + +=back + +=cut + +sub getKnownSystemAttrs +{ + my $self = shift; + + return + grep { $AttributeInfo{$_}->{"applies_to_systems"} } + keys %AttributeInfo +} + +=item C + +Returns the attribute names that apply to clients. + +=over + +=item Return Value + +An array of attribute names. + +=back + +=cut + +sub getKnownClientAttrs +{ + my $self = shift; + + return + grep { $AttributeInfo{$_}->{"applies_to_clients"} } + keys %AttributeInfo +} + =item C Fetches and returns information about all vendor-OSes that match the given @@ -318,8 +362,8 @@ sub fetchVendorOSByFilter my $filter = shift; my $resultCols = shift; - my @vendorOS = - $self->{'meta-db'}->fetchVendorOSByFilter($filter, $resultCols); + my @vendorOS + = $self->{'meta-db'}->fetchVendorOSByFilter($filter, $resultCols); return wantarray() ? @vendorOS : shift @vendorOS; } @@ -493,6 +537,11 @@ is no filtering. See L for more info. A comma-separated list of colunm names that shall be returned. If not defined, all available data must be returned. +=item Param C<$attrFilter> [Optional] + +A hash-ref containing the filter criteria that shall be applied against +attributes. + =item Return Value An array of hash-refs containing the resulting data rows. @@ -506,19 +555,11 @@ sub fetchSystemByFilter my $self = shift; my $filter = shift; my $resultCols = shift; + my $attrFilter = shift; - my @systems = $self->{'meta-db'}->fetchSystemByFilter($filter, $resultCols); - - # unless specific result cols have been given, we mix in the attributes - # of each system, too: - if (!defined $resultCols) { - foreach my $system (@systems) { - my @attrs = $self->{'meta-db'}->fetchSystemAttrs($system->{id}); - foreach my $attr (@attrs) { - $system->{"attr_$attr->{name}"} = $attr->{value}; - } - } - } + my @systems = $self->{'meta-db'}->fetchSystemByFilter( + $filter, $resultCols, $attrFilter + ); return wantarray() ? @systems : shift @systems; } @@ -555,18 +596,91 @@ sub fetchSystemByID # unless specific result cols have been given, we mix in the attributes # of each system, too: - if (!defined $resultCols) { - foreach my $system (@systems) { - my @attrs = $self->{'meta-db'}->fetchSystemAttrs($system->{id}); - foreach my $attr (@attrs) { - $system->{"attr_$attr->{name}"} = $attr->{value}; - } - } - } +# if (!defined $resultCols) { +# foreach my $system (@systems) { +# $system->{attrs} +# = $self->{'meta-db'}->fetchSystemAttrs($system->{id}); +# } +# } return wantarray() ? @systems : shift @systems; } +=item C + +Fetches and returns the information about the attributes of the system +with the given ID. + +=over + +=item Param C<$systemID> + +The ID of the system whose attributes you are interested in. + +=item Param C<$attrNames> [Optional] + +A comma-separated list of attribute names that shall be returned. If not +defined,all available attributes will be returned. + +=item Return Value + +An array of hash-refs containing the resulting data rows (or a single hash-ref +mapping all attribute names to the respective value). + +=back + +=cut + +sub fetchSystemAttrs +{ + my $self = shift; + my $systemID = shift; + my $attrNames = shift; + + my @attrs = $self->{'meta-db'}->fetchSystemAttrs($systemID, $attrNames); + + return wantarray() ? @attrs : shift @attrs; +} + +=item C + +Fetches and returns the information about the attributes of the system +with the given ID. + +=over + +=item Param C<$systemID> + +The ID of the system whose attributes you are interested in. + +=item Param C<$attrNames> [Optional] + +A comma-separated list of attribute names that shall be returned. If not +defined,all available attributes will be returned. + +=item Return Value + +A single hash-ref mapping all attribute names to their respective value. + +=back + +=cut + +sub fetchSystemAttrsAsHash +{ + my $self = shift; + my $systemID = shift; + my $attrNames = shift; + + my @attrs = $self->{'meta-db'}->fetchSystemAttrs($systemID, $attrNames); + + my $Result = {}; + foreach my $attr (@attrs) { + $Result->{$attr->{name}} = $attr->{value}; + } + return $Result; +} + =item C Fetches the IDs of all systems that make use of the export with the given ID. @@ -2702,6 +2816,7 @@ sub _checkAndUpgradeDBSchemaIfNecessary $DbSchema->{tables}->{$tableName}->{vals} ); } + $metaDB->schemaSetDBVersion($DbSchema->{version}); vlog(1, _tr('DB has been created successfully')); } elsif ($currVersion < $DbSchema->{version}) { vlog( @@ -2759,6 +2874,7 @@ sub _checkAndUpgradeDBSchemaIfNecessary } } } + $metaDB->schemaSetDBVersion($DbSchema->{version}); vlog(1, _tr('upgrade done')); } else { vlog(1, _tr('DB matches current schema version (%s)', $currVersion)); @@ -2770,6 +2886,7 @@ sub _checkAndUpgradeDBSchemaIfNecessary sub _aref { # transparently converts the given reference to an array-ref my $ref = shift; + return [] unless defined $ref; $ref = [$ref] unless ref($ref) eq 'ARRAY'; @@ -2779,7 +2896,6 @@ sub _aref sub _unique { # return given array filtered to unique elements my %seenIDs; - return grep { !$seenIDs{$_}++; } @_; } diff --git a/config-db/OpenSLX/DBSchema.pm b/config-db/OpenSLX/DBSchema.pm index 9b692b59..54596c9f 100644 --- a/config-db/OpenSLX/DBSchema.pm +++ b/config-db/OpenSLX/DBSchema.pm @@ -23,10 +23,13 @@ $VERSION = 0.2; @ISA = qw(Exporter); @EXPORT = qw( - $DbSchema %DbSchemaHistory + $DbSchema %DbSchemaHistory %AttributeInfo ); -our ($DbSchema, %DbSchemaHistory); +our ($DbSchema, %DbSchemaHistory, %AttributeInfo); + + +use OpenSLX::Basics; use POSIX qw(locale_h); my $lang = setlocale(LC_MESSAGES); @@ -254,12 +257,22 @@ $DbSchema = { 'name' => 'ramfs_fsmods', 'value' => '', }, + { + 'system_id' => 0, + 'name' => 'ramfs_miscmods', + 'value' => '', + }, { 'system_id' => 0, 'name' => 'ramfs_nicmods', 'value' => 'forcedeth e1000 e100 tg3 via-rhine r8169 pcnet32', }, + { + 'system_id' => 0, + 'name' => 'ramfs_screen', + 'value' => '', + }, { 'system_id' => 0, 'name' => 'sane_scanner', @@ -448,7 +461,7 @@ $DbSchema = { foreach my $key (keys %$system) { next if substr($key, 0, 5) ne 'attr_'; my $attrValue = $system->{$key} || ''; - next if !length($attrValue); + next if $system->{id}>0 && !length($attrValue); my $newAttrName = substr($key, 5); $configDB->setSystemAttr( $system->{id}, $newAttrName, $attrValue @@ -516,4 +529,26 @@ $DbSchema = { ], ); + +################################################################################ +### +### Load all available AttrInfo modules and build the complete hash containing +### info about all known attributes from that. +### +################################################################################ + +%AttributeInfo = (); + +my $libPath = "$openslxConfig{'base-path'}/lib"; +foreach my $module (glob("$libPath/OpenSLX/AttrInfo/*.pm")) { + next if $module !~ m{/([^/]+)\.pm$}; + my $class = "OpenSLX::AttrInfo::$1"; + vlog(2, "loading attr-info from module '$module'"); + my $instance = instantiateClass($class); + my $attrInfo = $instance->AttrInfo(); + foreach my $attr (keys %$attrInfo) { + $AttributeInfo{$attr} = $attrInfo->{$attr}; + } +} + 1; diff --git a/config-db/OpenSLX/MetaDB/DBI.pm b/config-db/OpenSLX/MetaDB/DBI.pm index dbc1faa8..774ab90e 100644 --- a/config-db/OpenSLX/MetaDB/DBI.pm +++ b/config-db/OpenSLX/MetaDB/DBI.pm @@ -67,7 +67,7 @@ sub rollbackTransaction } ################################################################################ -### data access functions +### data access ################################################################################ sub _trim { @@ -76,6 +76,62 @@ sub _trim return $s; } +sub _buildFilterClause +{ + my $self = shift; + my $filter = shift || {}; + my $connector = shift; + + my $filterClause = ''; + my ($quotedVal); + foreach my $col (keys %$filter) { + $connector = !defined $connector ? 'WHERE' : 'AND'; + if (defined $filter->{$col}) { + $quotedVal = $self->{dbh}->quote($filter->{$col}); + $filterClause .= " $connector $col = $quotedVal"; + } else { + $filterClause .= " $connector $col IS NULL"; + } + } + + return $filterClause; +} + +sub _buildAttrFilterClause +{ + my $self = shift; + my $attrFilter = shift || {}; + my $connector = shift; + + my $attrFilterClause = ''; + my ($quotedName, $quotedValue); + foreach my $name (keys %$attrFilter) { + $connector = !defined $connector ? 'WHERE' : 'AND'; + $quotedName = $self->{dbh}->quote($name); + if (defined $attrFilter->{$name}) { + $quotedValue = $self->{dbh}->quote($attrFilter->{$name}); + $attrFilterClause .= <<" End-of-Here"; + $connector EXISTS ( + SELECT name FROM system_attr + WHERE name = $quotedName + AND value = $quotedValue + AND system_id = system.id + ) + End-of-Here + } else { + $attrFilterClause .= <<" End-of-Here"; + $connector NOT EXISTS ( + SELECT name FROM system_attr + WHERE name = $quotedName + AND system_id = system.id + ) + End-of-Here + } + } + + return $attrFilterClause; +} + sub _doSelect { my $self = shift; @@ -117,13 +173,8 @@ sub fetchVendorOSByFilter my $resultCols = shift; $resultCols = '*' unless (defined $resultCols); - my $sql = "SELECT $resultCols FROM vendor_os"; - my ($connector, $quotedVal); - foreach my $col (keys %$filter) { - $connector = !defined $connector ? 'WHERE' : 'AND'; - $quotedVal = $self->{dbh}->quote($filter->{$col}); - $sql .= " $connector $col = $quotedVal"; - } + my $filterClause = $self->_buildFilterClause($filter); + my $sql = "SELECT $resultCols FROM vendor_os $filterClause"; return $self->_doSelect($sql); } @@ -147,13 +198,8 @@ sub fetchExportByFilter my $resultCols = shift; $resultCols = '*' unless (defined $resultCols); - my $sql = "SELECT $resultCols FROM export"; - my ($connector, $quotedVal); - foreach my $col (keys %$filter) { - $connector = !defined $connector ? 'WHERE' : 'AND'; - $quotedVal = $self->{dbh}->quote($filter->{$col}); - $sql .= " $connector $col = $quotedVal"; - } + my $filterClause = $self->_buildFilterClause($filter); + my $sql = "SELECT $resultCols FROM export $filterClause"; return $self->_doSelect($sql); } @@ -196,15 +242,17 @@ sub fetchSystemByFilter my $self = shift; my $filter = shift; my $resultCols = shift; + my $attrFilter = shift; $resultCols = '*' unless (defined $resultCols); - my $sql = "SELECT $resultCols FROM system"; - my ($connector, $quotedVal); - foreach my $col (keys %$filter) { - $connector = !defined $connector ? 'WHERE' : 'AND'; - $quotedVal = $self->{dbh}->quote($filter->{$col}); - $sql .= " $connector $col = $quotedVal"; - } + my $filterClause = $self->_buildFilterClause($filter, 'AND'); + my $attrFilterClause = $self->_buildAttrFilterClause($attrFilter, 'AND'); + my $sql = <<" End-of-Here"; + SELECT $resultCols FROM system + WHERE 1=1 + $filterClause + $attrFilterClause + End-of-Here return $self->_doSelect($sql); } @@ -225,11 +273,16 @@ sub fetchSystemAttrs { my $self = shift; my $systemID = $self->{dbh}->quote(shift); + my $attrNames = shift; my $sql = <<" End-of-Here"; SELECT id, name, value FROM system_attr WHERE system_id = $systemID End-of-Here + if (defined $attrNames) { + my $attrList = join ',', map { $self->{dbh}->quote($_) } @$attrNames; + $sql .= " AND name IN ($attrList)"; + } return $self->_doSelect($sql); } @@ -273,13 +326,8 @@ sub fetchClientByFilter my $resultCols = shift; $resultCols = '*' unless (defined $resultCols); - my $sql = "SELECT $resultCols FROM client"; - my ($connector, $quotedVal); - foreach my $col (keys %$filter) { - $connector = !defined $connector ? 'WHERE' : 'AND'; - $quotedVal = $self->{dbh}->quote($filter->{$col}); - $sql .= " $connector $col = $quotedVal"; - } + my $filterClause = $self->_buildFilterClause($filter); + my $sql = "SELECT $resultCols FROM client $filterClause"; return $self->_doSelect($sql); } @@ -325,13 +373,8 @@ sub fetchGroupByFilter my $resultCols = shift; $resultCols = '*' unless (defined $resultCols); - my $sql = "SELECT $resultCols FROM groups"; - my ($connector, $quotedVal); - foreach my $col (keys %$filter) { - $connector = !defined $connector ? 'WHERE' : 'AND'; - $quotedVal = $self->{dbh}->quote($filter->{$col}); - $sql .= " $connector $col = $quotedVal"; - } + my $filterClause = $self->_buildFilterClause($filter); + my $sql = "SELECT $resultCols FROM groups $filterClause"; return $self->_doSelect($sql); } -- cgit v1.2.3-55-g7522