git-svn-id: https://svn.code.sf.net/p/xcat/code/xcat-core/trunk@12208 8638fb3e-16cb-4fca-ae20-7b5d299a9bcd
		
			
				
	
	
		
			279 lines
		
	
	
		
			7.3 KiB
		
	
	
	
		
			Perl
		
	
	
	
	
	
			
		
		
	
	
			279 lines
		
	
	
		
			7.3 KiB
		
	
	
	
		
			Perl
		
	
	
	
	
	
#!/usr/bin/env perl
 | 
						|
# IBM(c) 2007 EPL license http://www.eclipse.org/legal/epl-v10.html
 | 
						|
#-------------------------------------------------------
 | 
						|
package xCAT::ExtTab;
 | 
						|
BEGIN
 | 
						|
{
 | 
						|
$::XCATROOT = $ENV{'XCATROOT'} ? $ENV{'XCATROOT'} : -d '/opt/xcat' ? '/opt/xcat' : '/usr';
 | 
						|
 | 
						|
}
 | 
						|
#  
 | 
						|
#NO xCAT perl library routines should be used in this begin block
 | 
						|
#(i.e. MsgUtils,Utils, etc) 
 | 
						|
#  
 | 
						|
#use lib "$::XCATROOT/lib/perl";
 | 
						|
 | 
						|
use File::Path;
 | 
						|
%ext_tabspec=(); 
 | 
						|
%ext_defspec=();
 | 
						|
 | 
						|
 | 
						|
# loads user defined table spec. They are stored under /opt/xcat/lib/perl/xCAT_schema directory
 | 
						|
my $path="$::XCATROOT/lib/perl/xCAT_schema";
 | 
						|
my $filelist;  # no specific files
 | 
						|
my @extSchema = &get_filelist($path, $filelist,"pm");
 | 
						|
#   print "\nextSchema=@extSchema\n";
 | 
						|
 | 
						|
foreach (@extSchema) {
 | 
						|
    /.*\/([^\/]*).pm$/;
 | 
						|
    my $file=$_;
 | 
						|
    my $modname = $1;
 | 
						|
    no strict 'refs';
 | 
						|
    my $warning;
 | 
						|
    # `logger -t xCAT processing $_`; 
 | 
						|
    eval {require($_)};
 | 
						|
    if ($@) { 
 | 
						|
	$warning ="Warning: The user defined database table schema file $file cannot be located or has compiling errors.\n";
 | 
						|
        print $warning;
 | 
						|
        `logger -p local4.warning -t xCAT $warning`; 
 | 
						|
	next;
 | 
						|
    }   
 | 
						|
    if (${"xCAT_schema::" . "$modname" . "::"}{tabspec}) {
 | 
						|
	my %tabspec=%{${"xCAT_schema::" . "$modname" . "::"}{tabspec}};
 | 
						|
	foreach my $tabname (keys(%tabspec)) {
 | 
						|
            if (exists($ext_tabspec{$tabname})) {
 | 
						|
		$warning = "Warning: File $file: the table name $tabname is used by other applications. Please rename the table.\n";
 | 
						|
                print $warning;
 | 
						|
               `logger -p local4.warning -t xCAT $warning`; 
 | 
						|
	    } else {
 | 
						|
		$ext_tabspec{$tabname}=$tabspec{$tabname};
 | 
						|
	    }
 | 
						|
	}
 | 
						|
    } else {
 | 
						|
	$warning ="\n  Warning: Cannot find \%tabspec variable in the user defined database table schema file $file\n";
 | 
						|
         print $warning;
 | 
						|
         `logger -p local4.warning -t xCAT $warning`; 
 | 
						|
    }
 | 
						|
   
 | 
						|
    #get the defspec from each file and merge them into %ext_defspec
 | 
						|
    if (${"xCAT_schema::" . "$modname" . "::"}{defspec}) {
 | 
						|
	my %defspec=%{${"xCAT_schema::" . "$modname" . "::"}{defspec}};
 | 
						|
	foreach my $objname (keys(%defspec)) {
 | 
						|
	    if (exists($defspec{$objname}->{'attrs'})) {
 | 
						|
		if (exists($ext_defspec{$objname})) {
 | 
						|
                    #print "insert\n";
 | 
						|
		    my @attr_new=@{$defspec{$objname}->{'attrs'}};
 | 
						|
		    my @attr=@{$ext_defspec{$objname}->{'attrs'}};
 | 
						|
		    my %tmp_hash=();
 | 
						|
		    foreach my $orig (@attr) {
 | 
						|
			my $attrname=$orig->{attr_name};
 | 
						|
			$tmp_hash{$attrname}=1;
 | 
						|
		    }
 | 
						|
		    foreach my $h (@attr_new) {
 | 
						|
			my $attrname=$h->{attr_name};
 | 
						|
			if (exists($tmp_hash{$attrname})) {
 | 
						|
			    $warning= "  Warning: Conflict when adding user defined defspec from file $file. Attribute name $attrname is already defined in object $objname.  \n";
 | 
						|
                            print $warning;
 | 
						|
                           `logger  -p local4.warning  -t xCAT $warning`; 
 | 
						|
			} else {
 | 
						|
			    #print "\ngot here objname=$objname, attrname=" . $h->{attr_name} . "\n";
 | 
						|
			    push(@{$ext_defspec{$objname}->{'attrs'}}, $h); 
 | 
						|
			}
 | 
						|
		    }
 | 
						|
		} else {
 | 
						|
		    #print "\ngot here objname=$objname, file=$file\n";
 | 
						|
		    $ext_defspec{$objname}=$defspec{$objname};
 | 
						|
		}	    
 | 
						|
	    }
 | 
						|
	}
 | 
						|
    }   
 | 
						|
    
 | 
						|
} #foreach  
 | 
						|
 | 
						|
#print out the defspec
 | 
						|
#print "\nexternal defspec:\n";
 | 
						|
#foreach(%ext_defspec) {
 | 
						|
#    print "  $_:\n";
 | 
						|
#    my @attr=@{$ext_defspec{$_}->{'attrs'}};
 | 
						|
#    foreach my $h (@attr) {
 | 
						|
#	print "    " . $h->{attr_name} . "\n";
 | 
						|
#    }
 | 
						|
#}  
 | 
						|
 | 
						|
#-------------------------------------------------------
 | 
						|
=head1 xCAT::ExtTab
 | 
						|
 | 
						|
    Handles user defined database tables.
 | 
						|
 | 
						|
=cut
 | 
						|
 | 
						|
#-------------------------------------------------------
 | 
						|
 | 
						|
=head3  updateTables
 | 
						|
 | 
						|
     It is called by xcatd to generate the user-defined tables 
 | 
						|
  if they do not exist, it also updates the tables if there is 
 | 
						|
  a schema change. 
 | 
						|
 | 
						|
 | 
						|
=cut
 | 
						|
#-------------------------------------------------------
 | 
						|
 | 
						|
sub updateTables
 | 
						|
{
 | 
						|
    #print "\nupdateTables\n";
 | 
						|
    #print "\n";
 | 
						|
    foreach (keys %ext_tabspec) {
 | 
						|
	my $table= xCAT::Table->new($_,-create=>1);
 | 
						|
        my $rc=$table->updateschema();
 | 
						|
        $table->close();
 | 
						|
    }
 | 
						|
}
 | 
						|
#--------------------------------------------------------------------------
 | 
						|
 | 
						|
=head3   
 | 
						|
    Note this is a copy of the one in Table.pm but we cannot use any of the
 | 
						|
    xCAT perl libraries in this routine,since the function was done in the
 | 
						|
    Begin block.
 | 
						|
    Description: get_filelist 
 | 
						|
 | 
						|
    Arguments:
 | 
						|
             directory,filelist,type 
 | 
						|
    Returns:
 | 
						|
            The list of sql files to be processed which consists of all the
 | 
						|
			files with <name>.sql  and <name>_<databasename>.sql
 | 
						|
		        or 	
 | 
						|
			files with <name>.pm  and <name>_<databasename>.pm
 | 
						|
    Globals:
 | 
						|
 | 
						|
    Error:
 | 
						|
 | 
						|
    Example:
 | 
						|
	my @filelist =get_filelist($directory,$filelist,$type);
 | 
						|
            where type = "sql" or "pm"
 | 
						|
 | 
						|
=cut
 | 
						|
 | 
						|
#--------------------------------------------------------------------------------
 | 
						|
 | 
						|
sub get_filelist
 | 
						|
 | 
						|
{
 | 
						|
    use File::Basename; 
 | 
						|
    my $directory = shift;
 | 
						|
    my $files     = shift;
 | 
						|
    my $ext       = shift;
 | 
						|
    my $dbname    = "sqlite";
 | 
						|
    my $xcatcfg   = get_xcatcfg();
 | 
						|
 | 
						|
    if ($xcatcfg =~ /^DB2:/)
 | 
						|
    {
 | 
						|
        $dbname = "db2";
 | 
						|
    }
 | 
						|
    else
 | 
						|
    {
 | 
						|
        if ($xcatcfg =~ /^mysql:/)
 | 
						|
        {
 | 
						|
            $dbname = "mysql";
 | 
						|
        }
 | 
						|
        else
 | 
						|
        {
 | 
						|
            if ($xcatcfg =~ /^Pg:/)
 | 
						|
            {
 | 
						|
                $dbname = "pgsql";
 | 
						|
            }
 | 
						|
        }
 | 
						|
    }
 | 
						|
    $directory .= "/";
 | 
						|
 | 
						|
    my @filelist = ();
 | 
						|
 | 
						|
    my @list = glob($directory . "*.$ext");    # all files
 | 
						|
    foreach my $file (@list)
 | 
						|
    {
 | 
						|
        my $filename= basename($file);  # strip filename
 | 
						|
        my($name,$ext1) = split '\.', $filename;
 | 
						|
        my($tmpname,$ext2) = split '\_', $name;
 | 
						|
        if ($ext2 eq $dbname)   # matches the database
 | 
						|
        {
 | 
						|
            push @filelist, $file;
 | 
						|
        }
 | 
						|
        else
 | 
						|
        {
 | 
						|
            if ($ext2 eq "") # no database designated
 | 
						|
            {
 | 
						|
                push @filelist, $file;
 | 
						|
            } else { # if not one of the databases, they just have _ in
 | 
						|
                     # the file name
 | 
						|
               if ($ext2 ne "db2" && $ext2 ne "mysql" && $ext2 ne "pgsql" && $ext2 ne "sqlite" ) {
 | 
						|
                    push @filelist, $file;
 | 
						|
               }
 | 
						|
            }
 | 
						|
        } 
 | 
						|
         $ext2 = "";
 | 
						|
         $ext1 = "";
 | 
						|
    }
 | 
						|
    return @filelist;
 | 
						|
}
 | 
						|
#--------------------------------------------------------------------------
 | 
						|
 | 
						|
=head3   
 | 
						|
 | 
						|
    Note this is a copy of the one in Table.pm but we cannot use any of the
 | 
						|
    xCAT perl libraries in this routine,since the function was done in the
 | 
						|
 | 
						|
    Description: get_xcatcfg 
 | 
						|
 | 
						|
    Arguments:
 | 
						|
              none 
 | 
						|
    Returns:
 | 
						|
              the database name from /etc/xcat/cfgloc or sqlite
 | 
						|
    Globals:
 | 
						|
 | 
						|
    Error:
 | 
						|
 | 
						|
    Example:
 | 
						|
	my $xcatcfg =get_xcatcfg();
 | 
						|
 | 
						|
 | 
						|
=cut
 | 
						|
 | 
						|
#--------------------------------------------------------------------------------
 | 
						|
 | 
						|
sub get_xcatcfg
 | 
						|
{
 | 
						|
    my $xcatcfg = (defined $ENV{'XCATCFG'} ? $ENV{'XCATCFG'} : '');
 | 
						|
    unless ($xcatcfg) {
 | 
						|
        if (-r "/etc/xcat/cfgloc") {
 | 
						|
	    my $cfgl;
 | 
						|
	    open($cfgl,"<","/etc/xcat/cfgloc");
 | 
						|
	    $xcatcfg = <$cfgl>;
 | 
						|
	    close($cfgl);
 | 
						|
	    chomp($xcatcfg);
 | 
						|
	    $ENV{'XCATCFG'}=$xcatcfg; #Store it in env to avoid many file reads
 | 
						|
        }
 | 
						|
    }
 | 
						|
    if ($xcatcfg =~ /^$/)
 | 
						|
    {
 | 
						|
        if (-d "/opt/xcat/cfg")
 | 
						|
        {
 | 
						|
            $xcatcfg = "SQLite:/opt/xcat/cfg";
 | 
						|
        }
 | 
						|
        else
 | 
						|
        {
 | 
						|
            if (-d "/etc/xcat")
 | 
						|
            {
 | 
						|
                $xcatcfg = "SQLite:/etc/xcat";
 | 
						|
            }
 | 
						|
        }
 | 
						|
    }
 | 
						|
    unless ($xcatcfg =~ /:/)
 | 
						|
    {
 | 
						|
        $xcatcfg = "SQLite:" . $xcatcfg;
 | 
						|
    }
 | 
						|
    return $xcatcfg;
 | 
						|
}
 | 
						|
 | 
						|
 | 
						|
1;
 |