diff --git a/xCAT-OpenStack/lib/perl/xCAT_plugin/cloud.pm b/xCAT-OpenStack/lib/perl/xCAT_plugin/cloud.pm new file mode 100644 index 000000000..826894886 --- /dev/null +++ b/xCAT-OpenStack/lib/perl/xCAT_plugin/cloud.pm @@ -0,0 +1,194 @@ +# IBM(c) 2010 EPL license http://www.eclipse.org/legal/epl-v10.html +package xCAT_plugin::cloud; +BEGIN +{ + $::XCATROOT = $ENV{'XCATROOT'} ? $ENV{'XCATROOT'} : '/opt/xcat'; +} +use lib "$::XCATROOT/lib/perl"; + +use strict; +use xCAT::Table; +use Getopt::Long; +Getopt::Long::Configure("bundling"); +Getopt::Long::Configure("pass_through"); +#use xCAT::Utils; +#use xCAT::TableUtils; +use xCAT::Template; + + + +sub handled_commands +{ + return {makeclouddata => "cloud",}; +} + +############################################################ +# check_options will process the options for makeclouddata and +# give a usage error for any invalid options +############################################################ +sub check_options +{ + my $req = shift; + my $callback = shift; + my $rc = 0; + + Getopt::Long::Configure("bundling"); + $Getopt::Long::ignorecase = 0; + Getopt::Long::Configure("no_pass_through"); + + # Exit if the packet has been preprocessed + if ($req->{_xcatpreprocessed}->[0] == 1) { return [$req]; } + + # Save the arguements in ARGV for GetOptions + if ($req && $req->{arg}) { @ARGV = @{$req->{arg}}; } + else { @ARGV = (); } + + + # Parse the options for makedhcp + if (!GetOptions( + 'h|help' => \$::opt_h, + )) + { + # If the arguements do not pass GetOptions then issue error message and return + return -1; + } + + # display the usage if -h + if ($::opt_h) + { + return 1; + + } + + my $cloudlist =shift( @ARGV ); + + if( defined($cloudlist) ) { + my @clouds = split(",", $cloudlist); + $req->{clouds} = \@clouds; + } + + return 0; +} + +sub cloudvars { + + my $inf = shift; + my $outf = shift; + my $cloud = shift; + my $callback = shift; + my $outh; + my $inh; + open($inh,"<",$inf); + unless ($inh) { + my $rsp; + $rsp->{errorcode}->[0]=1; + $rsp->{error}->[0]="Unable to open $inf, aborting\n"; + $callback->($rsp); + return; + } + my $inc; + #First load input into memory.. + while (<$inh>) { + $inc.=$_; + } + close($inh); + $inc =~ s/\$CLOUD/$cloud/eg; + $inc =~ s/#TABLE:([^:]+):([^:]+):([^#]+)#/xCAT::Template::tabdb($1,$2,$3)/eg; + + open($outh,">",$outf); + unless($outh) { + my $rsp; + $rsp->{errorcode}->[0]=1; + $rsp->{error}->[0]="Unable to open $inf, aborting\n"; + $callback->($rsp); + return; + } + print $outh $inc; + close($outh); + return 0; +} + + +sub process_request +{ + my $req = shift; + my $callback = shift; + my $rc = 0; + + # define usage statement + my $usage="Usage: \n\tmkcloudata\n\tmakeclouddata \n\tmakeclouddata [-h|--help]"; + + $rc = check_options($req,$callback); + if ($rc == -1) { + my $rsp = {}; + $rsp->{data}->[0] = $usage; + xCAT::MsgUtils->message("E", $rsp, $callback, 1); + return; + } elsif ($rc == 1) { + my $rsp = {}; + $rsp->{data}->[0] = $usage; + xCAT::MsgUtils->message("I", $rsp, $callback, 0); + return; + } + + my $tab = "clouds"; + my $ptab = xCAT::Table->new("$tab"); + + unless ($ptab) { + my $rsp; + $rsp->{errorcode}->[0]=1; + $rsp->{error}->[0]="Unable to open $tab table"; + $callback->($rsp); + return; + } + + + my $t = $req->{clouds}; + my %h; + if( defined(@$t) ) { + %h = map { $_ => 1} @$t; + } + + my @cloudentries = $ptab->getAllAttribs('name', 'template', 'repository'); + + foreach my $cloudentry (@cloudentries) { + + my $cloud = $cloudentry->{name}; + if( %h ) { + # if makeclouddata , and + if( $h{$cloud} != 1) { + next; + } + } + + my $tmplfile = $cloudentry->{template}; + my $repos = $cloudentry->{repository}; + + unless ( -r "$tmplfile") { + my $rsp; + $rsp->{errorcode}->[0]=1; + $rsp->{error}->[0]="The $cloud environment template $tmplfile doesn't exist."; + $callback->($rsp); + next; + } + + unless ( -r "$repos") { + my $rsp; + $rsp->{errorcode}->[0]=1; + $rsp->{error}->[0]="The $cloud repository $repos doesn't exist."; + $callback->($rsp); + next; + } + + my $tmperr = cloudvars( + $tmplfile, + "$repos/environments/$cloud.rb", + $cloud, + $callback + ); + + } + return; +} + +1; diff --git a/xCAT-server/lib/perl/xCAT/Postage.pm b/xCAT-server/lib/perl/xCAT/Postage.pm index cb25caeca..4970f81c1 100644 --- a/xCAT-server/lib/perl/xCAT/Postage.pm +++ b/xCAT-server/lib/perl/xCAT/Postage.pm @@ -213,6 +213,8 @@ sub makescript { $mn = xCAT::Utils->noderangecontainsMn(@$nodes); + my $cfgflag=0; + my $cloudflag=0; my $inc; my $t_inc; my %table; @@ -239,6 +241,14 @@ sub makescript { } } + if( $line =~ /#CFGMGTINFO_EXPORT#/ ) { + $cfgflag = 1; + } + if ($cfgflag == 1) { + if( $line =~ /#CLOUDINFO_EXPORT#/ ) { + $cloudflag = 1; + } + } } close($inh); @@ -334,7 +344,23 @@ sub makescript { # get all the nodes' setstate my $nodes_setstate_hash = getNodesSetState($nodes); - + + my $cfginfo_hash; + my $cloudinfo_hash; + # + # if #CFGCLIENTLIST_EXPORT# exists, ... + if( $cfgflag == 1 ) { + $cfginfo_hash = getcfginfo(); + # + # if #CLOUDINFO_EXPORT# exists, ... + if( $cloudflag == 1) { + $cloudinfo_hash = getcloudinfo(); + + } + } + + + foreach my $n (@$nodes ) { $node = $n; $inc = $t_inc; @@ -447,7 +473,15 @@ sub makescript { my $enablesshbetweennodes = enableSSHbetweennodes($node, \%::GLOBAL_SN_HASH, $groups_hash); - + my @clients; + my $cfgres; + my $cloudres; + if ( $cfgflag == 1 ) { + $cfgres = getcfgres($cfginfo_hash, $node, \@clients); + if ( $cloudflag == 1 ) { + $cloudres = getcloudres($cloudinfo_hash, \@clients); + } + } #ok, now do everything else.. #$inc =~ s/#XCATVAR:([^#]+)#/envvar($1)/eg; #$inc =~ s/#ENV:([^#]+)#/envvar($1)/eg; @@ -462,6 +496,9 @@ sub makescript { $inc =~ s/#NETWORK_FOR_DISKLESS_EXPORT#/$diskless_net_vars/eg; $inc =~ s/#INCLUDE_POSTSCRIPTS_LIST#/$postscripts/eg; $inc =~ s/#INCLUDE_POSTBOOTSCRIPTS_LIST#/$postbootscripts/eg; + + $inc =~ s/#CFGMGTINFO_EXPORT#/$cfgres/eg; + $inc =~ s/#CLOUDINFO_EXPORT#/$cloudres/eg; $inc =~ s/\$ENABLESSHBETWEENNODES/$enablesshbetweennodes/eg; $inc =~ s/\$NSETSTATE/$nodesetstate/eg; @@ -1699,7 +1736,127 @@ sub getPostbootScripts return $result; } +sub getcfginfo +{ + my %info = (); + my $tab = "cfgmgt"; + my $ptab = xCAT::Table->new($tab); + unless ($ptab) { + xCAT::MsgUtils->message("E", "Unable to open $tab table"); + return undef + } + my @rs = $ptab->getAllAttribs('node','cfgserver','roles'); + + foreach my $r ( @rs ) { + my $node = $r->{'node'}; + my $server = $r->{'cfgserver'}; + my $roles = $r->{'roles'}; + $info{ $server }{clientlist} .= "$node,"; + $info{ $node }{roles} = $roles; + + } + + return \%info; + + +} + +sub getcfgres +{ + my $cfginfo_hash = shift; + my $server = shift; + my $clients = shift; + my $cfgclient_list; + my $cfgres; + if( ! ( exists($cfginfo_hash->{$server}) && exists( $cfginfo_hash->{$server}->{clientlist} ) ) ) { + return $cfgres; + } + + $cfgclient_list = $cfginfo_hash->{$server}->{clientlist}; + chop $cfgclient_list; + $cfgres = "CFGCLIENTLIST='$cfgclient_list'\n"; + $cfgres .= "export CFGCLIENTLIST\n"; + @$clients = split(',', $cfgclient_list); + foreach my $client (@$clients) { + my $roles = $cfginfo_hash->{$client}->{roles}; + #$cfgres .= "hput $client roles $roles\n"; + $cfgres .= "HASH".$client."roles='$roles'\nexport HASH".$client."roles\n"; + } + + return $cfgres; +} + +sub getcloudinfo +{ + my %info = (); + + my $tab = "clouds"; + my $ptab = xCAT::Table->new($tab); + unless ($ptab) { + xCAT::MsgUtils->message("E", "Unable to open $tab table"); + return undef; + } + my @rs = $ptab->getAllAttribs('name','repository'); + + foreach my $r ( @rs ) { + my $cloud = $r->{'name'}; + my $repos = $r->{'repository'}; + $info{ $cloud }{repository} = $repos; + } + + $tab = "cloud"; + $ptab = xCAT::Table->new($tab); + unless ($ptab) { + xCAT::MsgUtils->message("E", "Unable to open $tab table"); + return undef; + } + @rs = $ptab->getAllAttribs('node','cloudname'); + + my $pre; + my $curr; + foreach my $r ( @rs ) { + my $node = $r->{'node'}; + my $cloud = $r->{'cloudname'}; + $info{ $node }{cloud} = $cloud; + } + + return \%info; +} + +sub getcloudres +{ + my $cloudinfo_hash = shift; + my $clients = shift; + my $cloudres; + my $cloudlist; + my $repos; + if( @$clients == 0 ) { + return $cloudres; + } + foreach my $client (@$clients) { + my $cloud; + if( defined($cloudinfo_hash) && defined($cloudinfo_hash->{$client}) ) { + $cloud = $cloudinfo_hash->{$client}->{cloud}; + } + #$cloudres .= "hput $client cloud $cloud\n"; + $cloudres .= "HASH".$client."cloud='$cloud'\nexport HASH".$client."cloud\n"; + $cloudlist .="$cloud,"; + + my $t = $cloudinfo_hash->{$cloud}->{repository}; + if( !defined($repos) ) { + $repos = $t; + } + if( defined($repos) && ( $repos != $t && "$repos/" != $t && $repos != "$t/" ) ) { + xCAT::MsgUtils->message("E", "Two cloud repositories: $repos and $t.\n There should be only one cloud repository one ont chef-server."); + return undef; + } + } + chop $cloudlist; + $cloudres = "REPOSITORY='$repos'\nexport REPOSITORY\nCLOUDLIST='$cloudlist'\nexport CLOUDLIST\n$cloudres"; + return $cloudres; +} + 1;