a67ad94915
git-svn-id: https://svn.code.sf.net/p/xcat/code/xcat-core/trunk@9010 8638fb3e-16cb-4fca-ae20-7b5d299a9bcd
1196 lines
29 KiB
Perl
1196 lines
29 KiB
Perl
# IBM(c) 2007 EPL license http://www.eclipse.org/legal/epl-v10.html
|
|
#-------------------------------------------------------
|
|
|
|
=head 1
|
|
xCAT plugin package to handle webrun command
|
|
|
|
=cut
|
|
|
|
#-------------------------------------------------------
|
|
|
|
package xCAT_plugin::web;
|
|
use strict;
|
|
|
|
require xCAT::Utils;
|
|
|
|
require xCAT::MsgUtils;
|
|
|
|
use Getopt::Long;
|
|
use Data::Dumper;
|
|
use LWP::Simple;
|
|
use xCAT::Table;
|
|
use xCAT::NodeRange;
|
|
|
|
sub handled_commands {
|
|
return { webrun => "web", };
|
|
}
|
|
|
|
sub process_request {
|
|
my $request = shift;
|
|
my $callback = shift;
|
|
my $sub_req = shift;
|
|
my %authorized_cmds = (
|
|
|
|
#command => function
|
|
'pping' => \&web_pping,
|
|
'update' => \&web_update,
|
|
'chtab' => \&web_chtab,
|
|
'lscondition' => \&web_lscond,
|
|
'lsresponse' => \&web_lsresp,
|
|
'lscondresp' => \&web_lscondresp,
|
|
'mkcondresp' => \&web_mkcondresp,
|
|
'startcondresp' => \&web_startcondresp,
|
|
'stopcondresp' => \&web_stopcondresp,
|
|
'lsrsrc' => \&web_lsrsrc,
|
|
'lsrsrcdef-api' => \&web_lsrsrcdef,
|
|
'gettab' => \&web_gettab,
|
|
'lsevent' => \&web_lsevent,
|
|
'lsdef' => \&web_lsdef,
|
|
'unlock' => \&web_unlock,
|
|
'rmcstart' => \&web_rmcmonStart,
|
|
'rmcshow' => \&web_rmcmonShow,
|
|
'gangliastart' => \&web_gangliastart,
|
|
'gangliastop' => \&web_gangliastop,
|
|
'gangliastatus' => \&web_gangliastatus,
|
|
'gangliacheck' => \&web_gangliacheck,
|
|
'mkcondition' => \&web_mkcondition,
|
|
'monls' => \&web_monls,
|
|
'writeframe' => \&web_writeframe,
|
|
'writecec' => \&web_writecec,
|
|
'writehmc' => \&web_writehmc
|
|
#'xdsh' => \&web_xdsh,
|
|
#THIS list needs to be updated
|
|
);
|
|
|
|
#to check whether the request is authorized or not
|
|
split ' ', $request->{arg}->[0];
|
|
my $cmd = $_[0];
|
|
if ( grep { $_ eq $cmd } keys %authorized_cmds ) {
|
|
my $func = $authorized_cmds{$cmd};
|
|
$func->( $request, $callback, $sub_req );
|
|
}
|
|
else {
|
|
$callback->( { error => "$cmd is not authorized!\n", errorcode => [1] } );
|
|
}
|
|
}
|
|
|
|
sub web_lsdef {
|
|
my ( $request, $callback, $sub_req ) = @_;
|
|
print Dumper($request);
|
|
|
|
#TODO: web_lsdef works only for "lsdef <noderange> -i nodetype"
|
|
my $ret = `$request->{arg}->[0]`;
|
|
my @lines = split '\n', $ret;
|
|
|
|
split '=', $lines[2];
|
|
my $ntype = $_[1];
|
|
|
|
$callback->( { data => "$ntype" } );
|
|
}
|
|
|
|
sub web_lsevent {
|
|
my ( $request, $callback, $sub_req ) = @_;
|
|
my @ret = `$request->{arg}->[0]`;
|
|
|
|
#print Dumper(\@ret);
|
|
#please refer the manpage for the output format of "lsevent"
|
|
|
|
my $data = [];
|
|
|
|
my $record = '';
|
|
|
|
my $i = 0;
|
|
my $j = 0;
|
|
|
|
foreach my $item (@ret) {
|
|
if ( $item ne "\n" ) {
|
|
chomp $item;
|
|
my ( $key, $value ) = split( "=", $item );
|
|
if ($j < 2){
|
|
$record .= $value . ';';
|
|
}
|
|
else{
|
|
$record .= $value;
|
|
}
|
|
|
|
$j++;
|
|
if ( $j == 3 ) {
|
|
$i++;
|
|
$j = 0;
|
|
push(@$data, $record);
|
|
$record = '';
|
|
}
|
|
}
|
|
|
|
}
|
|
|
|
#print Dumper(\%data);
|
|
|
|
$callback->( { data => $data } );
|
|
}
|
|
|
|
sub web_lsrsrcdef {
|
|
my ( $request, $callback, $sub_req ) = @_;
|
|
my $ret = `$request->{arg}->[0]`;
|
|
|
|
my @lines = split '\n', $ret;
|
|
shift @lines;
|
|
print Dumper( \@lines );
|
|
my $data = join( "=", @lines );
|
|
$callback->( { data => "$data" } );
|
|
|
|
}
|
|
|
|
sub web_lsrsrc {
|
|
my ( $request, $callback, $sub_req ) = @_;
|
|
my $ret = `$request->{arg}->[0]`;
|
|
my @classes;
|
|
|
|
my @lines = split '\n', $ret;
|
|
shift @lines;
|
|
foreach my $line (@lines) {
|
|
my $index = index( $line, '"', 1 );
|
|
push @classes, substr( $line, 1, $index - 1 );
|
|
}
|
|
my $data = join( "=", @classes );
|
|
$callback->( { data => "$data" } );
|
|
}
|
|
|
|
sub web_mkcondresp {
|
|
my ( $request, $callback, $sub_req ) = @_;
|
|
my $conditionName = $request->{arg}->[1];
|
|
my $temp = $request->{arg}->[2];
|
|
my $cmd = '';
|
|
|
|
my @resp = split(':', $temp);
|
|
#create new associations
|
|
if (1 < length(@resp[0])){
|
|
$cmd = substr(@resp[0], 1);
|
|
$cmd =~ s/,/ /;
|
|
$cmd = 'mkcondresp ' . $conditionName . ' ' . $cmd;
|
|
my $retInfo = xCAT::Utils->runcmd($cmd, -1, 1);
|
|
}
|
|
|
|
#delete old associations
|
|
if (1 < length(@resp[1])){
|
|
$cmd = substr(@resp[1], 1);
|
|
$cmd =~ s/,/ /;
|
|
$cmd = 'rmcondresp ' . $conditionName . ' ' . $cmd;
|
|
my $retInfo = xCAT::Utils->runcmd($cmd, -1, 1);
|
|
}
|
|
#there's no output for "mkcondresp"
|
|
$cmd = 'startcondresp ' . $conditionName;
|
|
my $refInfo = xCAT::Utils->runcmd($cmd, -1, 1);
|
|
$callback->({ data => "Success." });
|
|
}
|
|
|
|
sub web_startcondresp {
|
|
my ( $request, $callback, $sub_req ) = @_;
|
|
my $conditionName = $request->{arg}->[1];
|
|
my $cmd = 'startcondresp "' . $conditionName . '"';
|
|
my $retInfo = xCAT::Utils->runcmd($cmd, -1, 1);
|
|
$callback->({ data => 'start monitor "' . $conditionName . '" Successful.' });
|
|
}
|
|
|
|
sub web_stopcondresp {
|
|
my ( $request, $callback, $sub_req ) = @_;
|
|
my $conditionName = $request->{arg}->[1];
|
|
my $cmd = 'stopcondresp "' . $conditionName . '"';
|
|
my $retInfo = xCAT::Utils->runcmd($cmd, -1, 1);
|
|
$callback->({ data => 'stop monitor "' . $conditionName . '" Successful.' });
|
|
}
|
|
|
|
sub web_lscond {
|
|
my ( $request, $callback, $sub_req ) = @_;
|
|
my $nodeRange = $request->{arg}->[1];
|
|
my $names = '';
|
|
|
|
#list all the conditions on all lpars in this group
|
|
if ($nodeRange){
|
|
my @nodes = xCAT::NodeRange::noderange($nodeRange);
|
|
my %tempHash;
|
|
my $nodeCount = @nodes;
|
|
#no node in this group
|
|
if (1 > $nodeCount){
|
|
return;
|
|
}
|
|
|
|
#no conditions return
|
|
my $tempCmd = 'lscondition -d :' . join(',', @nodes);
|
|
my $retInfo = xCAT::Utils->runcmd($tempCmd, -1, 1);
|
|
if (1 > @$retInfo){
|
|
return;
|
|
}
|
|
|
|
shift @$retInfo;
|
|
shift @$retInfo;
|
|
|
|
foreach my $line (@$retInfo){
|
|
my @temp = split(':', $line);
|
|
$tempHash{@temp[0]}++;
|
|
}
|
|
|
|
foreach my $name (keys (%tempHash)){
|
|
if ($nodeCount == $tempHash{$name}){
|
|
$names = $names . $name . ';';
|
|
}
|
|
}
|
|
}
|
|
#only list the conditions on local.
|
|
else{
|
|
my $retInfo = xCAT::Utils->runcmd('lscondition -d', -1, 1);
|
|
|
|
if (2 > @$retInfo){
|
|
return;
|
|
}
|
|
|
|
shift @$retInfo;
|
|
shift @$retInfo;
|
|
foreach my $line (@$retInfo) {
|
|
my @temp = split(':', $line);
|
|
$names = $names . @temp[0] . ':' . substr(@temp[2], 1, 3) . ';';
|
|
}
|
|
}
|
|
if ('' eq $names){
|
|
return;
|
|
}
|
|
$names = substr($names, 0, (length($names) - 1));
|
|
|
|
$callback->( { data => $names } );
|
|
}
|
|
|
|
sub web_mkcondition{
|
|
my ( $request, $callback, $sub_req ) = @_;
|
|
|
|
if ('change' eq $request->{arg}->[1]){
|
|
my @nodes;
|
|
my $conditionName = $request->{arg}->[2];
|
|
my $groupName = $request->{arg}->[3];
|
|
|
|
my $retInfo = xCAT::Utils->runcmd('nodels ' . $groupName . " nodetype.nodetype", -1, 1);
|
|
foreach my $line (@$retInfo){
|
|
my @temp = split(':', $line);
|
|
if (@temp[1] !~ /lpar/){
|
|
$callback->( { data => 'Error : only the compute nodes\' group could select.' } );
|
|
return;
|
|
}
|
|
push (@nodes, @temp[0]);
|
|
}
|
|
|
|
xCAT::Utils->runcmd('chcondition -n ' + join(',', @nodes) + '-m m ' + $conditionName);
|
|
$callback->( { data => 'Change scope success.' } );
|
|
}
|
|
|
|
}
|
|
|
|
sub web_lsresp {
|
|
my ( $request, $callback, $sub_req ) = @_;
|
|
my $names = '';
|
|
my @temp;
|
|
my $retInfo = xCAT::Utils->runcmd('lsresponse -d', -1, 1);
|
|
|
|
shift @$retInfo;
|
|
shift @$retInfo;
|
|
foreach my $line (@$retInfo) {
|
|
@temp = split(':', $line);
|
|
$names = $names . @temp[0] . ';';
|
|
}
|
|
|
|
$names = substr($names, 0, (length($names) - 1));
|
|
$callback->( { data => $names } );
|
|
}
|
|
|
|
sub web_lscondresp {
|
|
my ( $request, $callback, $sub_req ) = @_;
|
|
my $names = '';
|
|
my @temp;
|
|
#if there is condition name, then we only show the condition linked associations.
|
|
if ($request->{arg}->[1]){
|
|
my $cmd = 'lscondresp -d ' . $request->{arg}->[1];
|
|
my $retInfo = xCAT::Utils->runcmd($cmd, -1, 1);
|
|
if (2 > @$retInfo){
|
|
$callback->( { data => '' } );
|
|
return;
|
|
}
|
|
|
|
shift @$retInfo;
|
|
shift @$retInfo;
|
|
for my $line (@$retInfo){
|
|
@temp = split(':', $line);
|
|
$names = $names . @temp[1] . ';';
|
|
}
|
|
}
|
|
else{
|
|
}
|
|
|
|
$names = substr($names, 0, (length($names) - 1));
|
|
$callback->( { data => $names } );
|
|
}
|
|
|
|
sub web_gettab {
|
|
|
|
#right now, gettab only support the monitoring table
|
|
my ( $request, $callback, $sub_req ) = @_;
|
|
split ' ', $request->{arg}->[0];
|
|
my $tmp_str = $_[2];
|
|
split '\.', $tmp_str;
|
|
my $table = $_[0];
|
|
if ( $table == "monitoring" ) {
|
|
my $val = `$request->{arg}->[0]`;
|
|
chomp $val;
|
|
$callback->( { data => $val } );
|
|
}
|
|
else {
|
|
$callback->(
|
|
{
|
|
error => "The table $table is not authorized to get!\n",
|
|
errorcode => [1]
|
|
}
|
|
);
|
|
}
|
|
}
|
|
|
|
#-------------------------------------------------------
|
|
|
|
=head3 web_update
|
|
|
|
Description : Update the xCAT associate RPM on manangement node
|
|
Arguments : RPM Name
|
|
Repository address
|
|
Returns : Nothing
|
|
|
|
=cut
|
|
|
|
#-------------------------------------------------------
|
|
sub web_update {
|
|
my ( $request, $callback, $sub_req ) = @_;
|
|
my $os = "unknow";
|
|
my $RpmNames = $request->{arg}->[1];
|
|
my $repository = $request->{arg}->[2];
|
|
my $FileHandle;
|
|
my $cmd;
|
|
my $ReturnInfo;
|
|
my $WebpageContent = undef;
|
|
my $RemoteRpmFilePath = undef;
|
|
my $LocalRpmFilePath = undef;
|
|
|
|
if ( xCAT::Utils->isLinux() ) {
|
|
$os = xCAT::Utils->osver();
|
|
|
|
#suse linux
|
|
if ( $os =~ /sles.*/ ) {
|
|
$RpmNames =~ s/,/ /g;
|
|
|
|
#create zypper command
|
|
$cmd = "zypper -n -p " . $repository . " update " . $RpmNames;
|
|
}
|
|
|
|
#redhat
|
|
else {
|
|
|
|
#check the yum config file, and delect it if exist.
|
|
if ( -e "/tmp/xCAT_update.yum.conf" ) {
|
|
unlink("/tmp/xCAT_update.yum.conf");
|
|
}
|
|
|
|
#create file, return error if failed.
|
|
unless ( open( $FileHandle, '>>', "/tmp/xCAT_update.yum.conf" ) ) {
|
|
$callback->( { error => "Create temp file error!\n", errorcode => [1] } );
|
|
return;
|
|
}
|
|
|
|
#write the rpm path into config file.
|
|
print $FileHandle "[xcat_temp_update]\n";
|
|
print $FileHandle "name=temp prepository\n";
|
|
$repository = "baseurl=" . $repository . "\n";
|
|
print $FileHandle $repository;
|
|
print $FileHandle "enabled=1\n";
|
|
print $FileHandle "gpgcheck=0\n";
|
|
close($FileHandle);
|
|
|
|
#use system to run the cmd "yum -y -c config-file update rpm-names"
|
|
$RpmNames =~ s/,/ /g;
|
|
$cmd = "yum -y -c /tmp/xCAT_update.yum.conf update " . $RpmNames . " 2>&1";
|
|
}
|
|
|
|
#run the command and return the result
|
|
$ReturnInfo = readpipe($cmd);
|
|
$callback->( { info => $ReturnInfo } );
|
|
}
|
|
|
|
#AIX
|
|
else {
|
|
|
|
#open the rpmpath(may be error), and read the page's content
|
|
$WebpageContent = LWP::Simple::get($repository);
|
|
unless ( defined($WebpageContent) ) {
|
|
$callback->( { error => "open $repository error, please check!!", errorcode => [1] } );
|
|
return;
|
|
}
|
|
|
|
#must support for updating several rpms.
|
|
foreach ( split( /,/, $RpmNames ) ) {
|
|
|
|
#find out rpms' corresponding rpm href on the web page
|
|
$WebpageContent =~ m/href="($_-.*?[ppc64|noarch].rpm)/i;
|
|
unless ( defined($1) ) {
|
|
next;
|
|
}
|
|
$RemoteRpmFilePath = $repository . $1;
|
|
$LocalRpmFilePath = '/tmp/' . $1;
|
|
|
|
#download rpm package to temp
|
|
unless ( -e $LocalRpmFilePath ) {
|
|
$cmd = "wget -O " . $LocalRpmFilePath . " " . $RemoteRpmFilePath;
|
|
if ( 0 != system($cmd) ) {
|
|
$ReturnInfo = $ReturnInfo . "update " . $_ . " failed: can not download the rpm\n";
|
|
$callback->( { error => $ReturnInfo, errorcode => [1] } );
|
|
return;
|
|
}
|
|
}
|
|
|
|
#update rpm by rpm packages.
|
|
$cmd = "rpm -U " . $LocalRpmFilePath . " 2>&1";
|
|
$ReturnInfo = $ReturnInfo . readpipe($cmd);
|
|
}
|
|
$callback->( { info => $ReturnInfo } );
|
|
}
|
|
}
|
|
|
|
#-------------------------------------------------------
|
|
|
|
=head3 web_pping
|
|
|
|
Description : Get the ping status of a given node
|
|
Arguments : Node
|
|
Returns : Nothing
|
|
|
|
=cut
|
|
|
|
#-------------------------------------------------------
|
|
sub web_pping {
|
|
my ( $request, $callback, $sub_req ) = @_;
|
|
|
|
# Treat the argument as the commandline, run it, and get the return message
|
|
my $out = `$request->{arg}->[0]`;
|
|
|
|
# Parse output, and use $callback to send back to the web interface
|
|
# Output looks like:
|
|
# xcat_n02: ping
|
|
# xcat_n03: ping
|
|
# xcat_n51: ping
|
|
# xcat_n52: noping
|
|
my @lines = split( '\n', $out );
|
|
my $line;
|
|
foreach $line (@lines) {
|
|
split( ':', $line );
|
|
$callback->(
|
|
{
|
|
node => [
|
|
{
|
|
name => [ $_[0] ], # Node name
|
|
data => [ $_[1] ] # Output
|
|
}
|
|
]
|
|
}
|
|
);
|
|
}
|
|
}
|
|
|
|
#-------------------------------------------------------
|
|
|
|
=head3 web_unlock
|
|
|
|
Description : Unlock a node by setting up the SSH keys
|
|
Arguments : Node
|
|
Password
|
|
Returns : Nothing
|
|
|
|
=cut
|
|
|
|
#-------------------------------------------------------
|
|
sub web_unlock {
|
|
my ( $request, $callback, $sub_req ) = @_;
|
|
|
|
my $node = $request->{arg}->[1];
|
|
my $password = $request->{arg}->[2];
|
|
my $out = `DSH_REMOTE_PASSWORD=$password xdsh $node -K`;
|
|
|
|
$callback->( { data => $out } );
|
|
}
|
|
|
|
#-------------------------------------------------------
|
|
|
|
=head3 web_gangliastatus
|
|
|
|
Description : Get the status of Ganglia on a given node
|
|
Arguments : Node
|
|
Returns : Nothing
|
|
|
|
=cut
|
|
|
|
#-------------------------------------------------------
|
|
sub web_gangliastatus {
|
|
my ( $request, $callback, $sub_req ) = @_;
|
|
|
|
# Get node range
|
|
my $nr = $request->{arg}->[1];
|
|
my $out = `xdsh $nr "service gmond status"`;
|
|
|
|
# Parse output, and use $callback to send back to the web interface
|
|
# Output looks like:
|
|
# node_1: Checking for gmond: ..running
|
|
# node_2: Checking for gmond: ..running
|
|
my @lines = split( '\n', $out );
|
|
my $line;
|
|
my $status;
|
|
foreach $line (@lines) {
|
|
if ( $line =~ m/running/i ) {
|
|
$status = 'on';
|
|
}
|
|
else {
|
|
$status = 'off';
|
|
}
|
|
|
|
split( ': ', $line );
|
|
$callback->(
|
|
{
|
|
node => [
|
|
{
|
|
name => [ $_[0] ], # Node name
|
|
data => [$status] # Output
|
|
}
|
|
]
|
|
}
|
|
);
|
|
}
|
|
}
|
|
|
|
#-------------------------------------------------------
|
|
|
|
=head3 web_gangliastart
|
|
|
|
Description : Start ganglia monitoring
|
|
Arguments : Node range
|
|
Returns : Nothing
|
|
|
|
=cut
|
|
|
|
#-------------------------------------------------------
|
|
sub web_gangliastart() {
|
|
my ( $request, $callback, $sub_req ) = @_;
|
|
|
|
# Get node range
|
|
my $nr = $request->{arg}->[1];
|
|
if ( !$nr ) {
|
|
|
|
# If no node range is given, then assume all nodes
|
|
$nr = '';
|
|
}
|
|
|
|
# Add gangliamon to the monitoring table
|
|
my $info;
|
|
my $output = `monadd gangliamon`;
|
|
my @lines = split( '\n', $output );
|
|
foreach (@lines) {
|
|
if ($_) {
|
|
$info .= ( $_ . "\n" );
|
|
}
|
|
}
|
|
|
|
# Run the ganglia configuration script on node
|
|
$output = `moncfg gangliamon $nr -r`;
|
|
@lines = split( '\n', $output );
|
|
foreach (@lines) {
|
|
if ($_) {
|
|
$info .= ( $_ . "\n" );
|
|
}
|
|
}
|
|
|
|
# Start the gmond daemon on node
|
|
$output = `monstart gangliamon $nr -r`;
|
|
@lines = split( '\n', $output );
|
|
foreach (@lines) {
|
|
if ($_) {
|
|
$info .= ( $_ . "\n" );
|
|
}
|
|
}
|
|
|
|
$callback->( { info => $info } );
|
|
return;
|
|
}
|
|
|
|
#-------------------------------------------------------
|
|
|
|
=head3 web_gangliastop
|
|
|
|
Description : Stop ganglia monitoring
|
|
Arguments : Node range
|
|
Returns : Nothing
|
|
|
|
=cut
|
|
|
|
#-------------------------------------------------------
|
|
sub web_gangliastop() {
|
|
my ( $request, $callback, $sub_req ) = @_;
|
|
|
|
# Get node range
|
|
my $nr = $request->{arg}->[1];
|
|
if ( !$nr ) {
|
|
$nr = '';
|
|
}
|
|
|
|
# Start the gmond daemon on node
|
|
my $info;
|
|
my $output = `monstop gangliamon $nr -r`;
|
|
my @lines = split( '\n', $output );
|
|
foreach (@lines) {
|
|
if ($_) {
|
|
$info .= ( $_ . "\n" );
|
|
}
|
|
}
|
|
|
|
$callback->( { info => $info } );
|
|
return;
|
|
}
|
|
|
|
#-------------------------------------------------------
|
|
|
|
=head3 web_gangliacheck
|
|
|
|
Description : Check if ganglia RPMs are installed
|
|
Arguments : Node range
|
|
Returns : Nothing
|
|
|
|
=cut
|
|
|
|
#-------------------------------------------------------
|
|
sub web_gangliacheck() {
|
|
my ( $request, $callback, $sub_req ) = @_;
|
|
|
|
# Get node range
|
|
my $nr = $request->{arg}->[1];
|
|
if ( !$nr ) {
|
|
$nr = '';
|
|
}
|
|
|
|
# Check if ganglia RPMs are installed
|
|
my $info;
|
|
my $info = `xdsh $nr "rpm -q ganglia-gmond libganglia libconfuse"`;
|
|
$callback->( { info => $info } );
|
|
return;
|
|
}
|
|
|
|
#-------------------------------------------------------
|
|
|
|
=head3 web_chtab
|
|
|
|
Description : Add, delete or update rows in the database tables
|
|
Arguments : The chtab command to run
|
|
Returns : Nothing
|
|
|
|
=cut
|
|
|
|
#-------------------------------------------------------
|
|
sub web_chtab {
|
|
my ( $request, $callback, $sub_req ) = @_;
|
|
|
|
# Get command
|
|
my $cmd = $request->{arg}->[0];
|
|
|
|
# Get node name
|
|
my @args = split( ' ', $cmd );
|
|
my $node = $args[1];
|
|
$node =~ s/node=//g;
|
|
|
|
my $info;
|
|
if ( $args[0] =~ m/chtab/i ) {
|
|
# Take argument as command and run it
|
|
system($cmd);
|
|
$info = 'Tables updated';
|
|
}
|
|
else {
|
|
$info = 'Unsupported command';
|
|
}
|
|
|
|
$callback->({
|
|
node => [{
|
|
name => [$node], # Node name
|
|
data => [$info] # Output
|
|
}]
|
|
});
|
|
}
|
|
|
|
#-------------------------------------------------------
|
|
|
|
=head3 web_rmcStart
|
|
|
|
Description : Start the RMC monitoring on management node
|
|
Arguments : Nothing
|
|
Returns : Nothing
|
|
|
|
=cut
|
|
|
|
#-------------------------------------------------------
|
|
sub web_rmcmonStart {
|
|
my ( $request, $callback, $sub_req ) = @_;
|
|
my $nodeRange = $request->{arg}->[1];
|
|
my $table;
|
|
my $retData = "";
|
|
my $output;
|
|
|
|
#check the running status
|
|
$table = xCAT::Table->new('monitoring');
|
|
my $rmcWorkingStatus = $table->getAttribs( { name => 'rmcmon' }, 'disable' );
|
|
$table . close();
|
|
|
|
#the rmc monitoring is running so return directly
|
|
if ($rmcWorkingStatus) {
|
|
if ( $rmcWorkingStatus->{disable} =~ /0|No|no|NO|N|n/ ) {
|
|
$callback->( { info => 'RMC Monitoring is running now.' } );
|
|
return;
|
|
}
|
|
}
|
|
|
|
$retData .= "RMC is not running, start it now.\n";
|
|
|
|
#check the monsetting table rmc's montype contains "performance"
|
|
$table = xCAT::Table->new('monsetting');
|
|
my $rmcmonType = $table->getAttribs( { name => 'rmcmon', key => 'montype' }, 'value' );
|
|
$table . close();
|
|
|
|
#the rmc monitoring is not configure right we should configure it again
|
|
#there is no rmcmon in monsetting table
|
|
if ( !$rmcmonType ) {
|
|
$output = xCAT::Utils->runcmd( 'monadd rmcmon -s [montype=perf]', -1, 1 );
|
|
foreach (@$output) {
|
|
$retData .= ( $_ . "\n" );
|
|
}
|
|
$retData .= "Add the rmcmon to monsetting table complete.\n";
|
|
}
|
|
|
|
#configure before but there is not performance monitoring, so change the table
|
|
else {
|
|
if ( !( $rmcmonType->{value} =~ /perf/ ) ) {
|
|
$output = xCAT::Utils->runcmd( 'chtab name=rmcmon,key=montype monsetting.value=perf', -1, 1 );
|
|
foreach (@$output) {
|
|
$retData .= ( $_ . "\n" );
|
|
}
|
|
$retData .= "Change the rmcmon configure in monsetting table finish.\n";
|
|
}
|
|
}
|
|
|
|
#run the rmccfg command to add all nodes into local RMC configuration
|
|
$output = xCAT::Utils->runcmd( "moncfg rmcmon $nodeRange", -1, 1 );
|
|
foreach (@$output) {
|
|
$retData .= ( $_ . "\n" );
|
|
}
|
|
|
|
#run the rmccfg command to add all nodes into remote RMC configuration
|
|
$output = xCAT::Utils->runcmd( "moncfg rmcmon $nodeRange -r", -1, 1 );
|
|
foreach (@$output) {
|
|
$retData .= ( $_ . "\n" );
|
|
}
|
|
|
|
#check the monfiguration
|
|
#use lsrsrc -a IBM.Host Name. compare the command's return and the noderange, then decide witch node should be refrsrc
|
|
|
|
#start the rmc monitor
|
|
$output = xCAT::Utils->runcmd( "monstart rmcmon", -1, 1 );
|
|
foreach (@$output) {
|
|
$retData .= ( $_ . "\n" );
|
|
}
|
|
|
|
$callback->( { info => $retData } );
|
|
return;
|
|
|
|
#configure the rmc monitoring
|
|
}
|
|
|
|
sub web_rmcmonShow() {
|
|
my ( $request, $callback, $sub_req ) = @_;
|
|
my $nodeRange = $request->{arg}->[1];
|
|
my $attr = $request->{arg}->[2];
|
|
my @nodes;
|
|
my $retInfo;
|
|
my $retHash = {};
|
|
my $output;
|
|
my @activeNodes;
|
|
my @rmcNodes;
|
|
my $tempNodes;
|
|
my $temp = "";
|
|
|
|
#only get the system rmc info
|
|
#like this PctTotalTimeIdle=>"10.0000, 20.0000, 12.0000, 30.0000"
|
|
if ( 'summary' eq $nodeRange ) {
|
|
$output =
|
|
xCAT::Utils->runcmd( "monshow rmcmon -s -t 60 -a " . $attr, -1, 1 );
|
|
foreach $temp (@$output) {
|
|
|
|
#the attribute name
|
|
if ( $temp =~ /Pct/ ) {
|
|
$temp =~ s/ //g;
|
|
|
|
#the first one
|
|
if ( "" eq $retInfo ) {
|
|
$retInfo .= ( $temp . ':' );
|
|
}
|
|
else {
|
|
$retInfo =~ s/,$/;/;
|
|
$retInfo .= ( $temp . ':' );
|
|
}
|
|
next;
|
|
}
|
|
|
|
#the content of the attribute
|
|
$temp =~ m/\s+(\d+\.\d{4})/;
|
|
if ( defined($1) ) {
|
|
$retInfo .= ( $1 . ',' );
|
|
}
|
|
}
|
|
|
|
#return the rmc info
|
|
$retInfo =~ s/,$//;
|
|
$callback->( { info => $retInfo } );
|
|
return;
|
|
}
|
|
|
|
if ( 'lpar' eq $nodeRange ) {
|
|
|
|
#get nodes detail containt
|
|
@nodes = xCAT::NodeRange::noderange($nodeRange);
|
|
if ( (@nodes) && ( @nodes > 0 ) ) {
|
|
|
|
#get all the active nodes
|
|
$temp = join( ' ', @nodes );
|
|
$output = `fping -a $temp 2> /dev/null`;
|
|
chomp($output);
|
|
@activeNodes = split( /\n/, $output );
|
|
|
|
#get all the inactive nodes by substracting the active nodes from all.
|
|
my %temp2;
|
|
foreach (@activeNodes) {
|
|
$temp2{$_} = 1;
|
|
}
|
|
foreach (@nodes) {
|
|
if ( !$temp2{$_} ) {
|
|
push( @{ $retHash->{node} }, { name => $_, data => 'NA' } );
|
|
}
|
|
}
|
|
}
|
|
|
|
if ( @activeNodes < 1 ) {
|
|
$callback->($retHash);
|
|
return;
|
|
}
|
|
|
|
$tempNodes = join( ',', @activeNodes );
|
|
$output = xCAT::Utils->runcmd( "xdsh $tempNodes rpm -q rsct.core", -1, 1 );
|
|
|
|
#non-installed
|
|
foreach (@$output) {
|
|
my @temp = split( /:/, $_ );
|
|
if ( @temp[1] =~ /not installed/ ) {
|
|
push( @{ $retHash->{node} }, { name => @temp[0], data => 'NI' } );
|
|
}
|
|
else {
|
|
push( @rmcNodes, @temp[0] );
|
|
}
|
|
}
|
|
|
|
#there are not rmc nodes, so we should return directly
|
|
if ( @rmcNodes < 1 ) {
|
|
$callback->($retHash);
|
|
return;
|
|
}
|
|
|
|
$tempNodes = join( ',', @rmcNodes );
|
|
$output = xCAT::Utils->runcmd( "xdsh $tempNodes \"/bin/ps -ef | /bin/grep rmcd | /bin/grep -v grep\" | /bin/awk '{print \$1\$9}'", -1, 1 );
|
|
foreach (@$output) {
|
|
my @temp = split( /:/, $_ );
|
|
if ( @temp[1] =~ /rmcd/ ) {
|
|
push( @{ $retHash->{node} }, { name => @temp[0], data => 'OK' } );
|
|
}
|
|
|
|
#not running
|
|
else {
|
|
push( @{ $retHash->{node} }, { name => @temp[0], data => 'NR' } );
|
|
}
|
|
}
|
|
|
|
$callback->($retHash);
|
|
return;
|
|
}
|
|
|
|
my $attrName = "";
|
|
my @attrValue = ();
|
|
$output =
|
|
xCAT::Utils->runcmd( "monshow rmcmon $nodeRange -t 60 -a " . $attr, -1, 1 );
|
|
foreach (@$output) {
|
|
$temp = $_;
|
|
if ( $temp =~ /\t/ ) {
|
|
$temp =~ s/\t/ /g;
|
|
chomp($temp);
|
|
}
|
|
|
|
#the attribute name
|
|
if ( $temp =~ m/\s+(Pct.*)\s+/ ) {
|
|
$temp = $1;
|
|
|
|
#the first one
|
|
if ( "" ne $attrName ) {
|
|
push( @{ $retHash->{node} }, { name => $attrName, data => join( ',', @attrValue ) } );
|
|
$attrName = "";
|
|
@attrValue = ();
|
|
}
|
|
$attrName = $temp;
|
|
next;
|
|
}
|
|
|
|
#the content of the attribute
|
|
$temp =~ m/\s+(\d+\.\d{4})\s*$/;
|
|
if ( defined($1) ) {
|
|
push( @attrValue, $1 );
|
|
}
|
|
}
|
|
|
|
#push the last attribute name and values.
|
|
push( @{ $retHash->{node} }, { name => $attrName, data => join( ',', @attrValue ) } );
|
|
$callback->($retHash);
|
|
}
|
|
|
|
sub web_monls(){
|
|
my ( $request, $callback, $sub_req ) = @_;
|
|
my $retInfo = xCAT::Utils->runcmd( "monls", -1, 1 );
|
|
my $ret = '';
|
|
foreach my $line (@$retInfo){
|
|
my @temp = split(/\s+/, $line);
|
|
$ret .= @temp[0];
|
|
if('not-monitored' eq @temp[1]){
|
|
$ret .= ':Not Monitored;';
|
|
}
|
|
else{
|
|
$ret .= ':Monitored;';
|
|
}
|
|
}
|
|
if ('' eq $ret){
|
|
return;
|
|
}
|
|
|
|
$ret = substr($ret, 0, length($ret) - 1);
|
|
$callback->({data=>$ret});
|
|
}
|
|
sub web_opentables{
|
|
my %tableHash;
|
|
my $tempNameArray = shift @_;
|
|
foreach my $tableName (@$tempNameArray){
|
|
$tableHash{$tableName} = xCAT::Table->new($tableName);
|
|
if (!($tableHash{$tableName})){
|
|
web_closetables(\%tableHash);
|
|
return undef;
|
|
}
|
|
}
|
|
return \%tableHash;
|
|
}
|
|
|
|
sub web_closetables{
|
|
my $tempHash = shift @_;
|
|
foreach my $tab (keys %$tempHash){
|
|
if ($tempHash->{$tab}){
|
|
$tempHash->{$tab}->close();
|
|
}
|
|
}
|
|
}
|
|
#-------------------------------------------------------
|
|
|
|
=head3 web_writehmc
|
|
|
|
Description : work for cluster setup wizard, write hmc into nodelist, ppc, site table
|
|
Arguments : hmcnamerange
|
|
Returns : Nothing
|
|
|
|
=cut
|
|
|
|
#-------------------------------------------------------
|
|
sub web_writehmc{
|
|
my ( $request, $callback, $sub_req ) = @_;
|
|
my $hmcNameRange = $request->{arg}->[1];
|
|
|
|
#connect all used tables;
|
|
my $tablePoint = web_opentables(['nodelist', 'ppc', 'site']);
|
|
if (!$tablePoint){
|
|
$callback->({data=>'Error: Connect tables failed!'});
|
|
return;
|
|
}
|
|
|
|
my @names = xCAT::NodeRange::noderange($hmcNameRange, 0);
|
|
if (scalar(@names) < 1){
|
|
$callback->({data=>'Error: node range input error!'});
|
|
web_closetables($tablePoint);
|
|
return;
|
|
}
|
|
|
|
for my $tempName (@names){
|
|
$tablePoint->{'nodelist'}->setNodeAttribs($tempName, {groups => 'hmc,all'});
|
|
$tablePoint->{'ppc'}->setNodeAttribs($tempName, {nodetype => 'hmc'});
|
|
}
|
|
|
|
$tablePoint->{'site'}->setAttribs({key => 'ea_primary_hmc'}, {value => $names[0]});
|
|
if (scalar(@names) > 2){
|
|
$tablePoint->{'site'}->setAttribs({key => 'ea_backup_hmc'}, {value => $names[1]});
|
|
}
|
|
|
|
web_closetables($tablePoint);
|
|
$callback->({data=>'Success: Write all HMCs into xCAT database!'});
|
|
}
|
|
#-------------------------------------------------------
|
|
|
|
=head3 web_writeframe
|
|
|
|
Description : work for cluster setup wizard, write frame into nodelist, ppc, nodehm table
|
|
the command is "webrun writeframe framename hmc/dfm hmcname framenumperhmc"
|
|
Arguments : nodegroupname, management method(hmc or dfm)
|
|
Returns : Nothing
|
|
|
|
=cut
|
|
|
|
#-------------------------------------------------------
|
|
sub web_writeframe{
|
|
my ( $request, $callback, $sub_req ) = @_;
|
|
my $frameNameRange = $request->{arg}->[1];
|
|
my $hmcFlag = $request->{arg}->[2];
|
|
my $framenumperhmc;
|
|
my @hmcNames;
|
|
my $tempname = '';
|
|
my $id = 0;
|
|
my $index = 0;
|
|
|
|
if ('hmc' eq $hmcFlag){
|
|
my $hmcName = $request->{arg}->[3];
|
|
$framenumperhmc = $request->{arg}->[4] + 0;
|
|
unless ($framenumperhmc){
|
|
$callback->({data=>'Error: frame number per hmc is error!'});
|
|
return;
|
|
}
|
|
@hmcNames = xCAT::NodeRange::noderange($hmcName, 0);
|
|
}
|
|
|
|
#open nodelist, ppc and nodehm table for update or add
|
|
my $tablePoint = web_opentables(['nodelist', 'ppc', 'nodehm']);
|
|
unless ($tablePoint){
|
|
$callback->({data=>'Error: Connect tables failed!'});
|
|
return;
|
|
}
|
|
|
|
my %nodelistHash;
|
|
my %nodehmHash;
|
|
my %ppcHash;
|
|
|
|
#expand the node range and set attributes in database.
|
|
my @frameNames = xCAT::NodeRange::noderange($frameNameRange, 0);
|
|
foreach $tempname (@frameNames){
|
|
#find it's id
|
|
if ($tempname =~ /\S+?(\d+)$/){
|
|
$id = $1;
|
|
}
|
|
else{
|
|
$id++;
|
|
}
|
|
$ppcHash{$tempname}{'id'} = $id;
|
|
$ppcHash{$tempname}{'nodetype'} = 'frame';
|
|
|
|
if ('hmc' eq $hmcFlag){
|
|
$nodehmHash{$tempname}{'mgt'} = 'hmc';
|
|
$ppcHash{$tempname}{'hcp'} = $hmcNames[int($index / $framenumperhmc)];
|
|
}
|
|
else{
|
|
$nodehmHash{$tempname}{'mgt'} = 'bpa';
|
|
$ppcHash{$tempname}{'hcp'} = $tempname;
|
|
}
|
|
$nodelistHash{$tempname}{'groups'} = 'frame,all';
|
|
$index++;
|
|
}
|
|
|
|
$tablePoint->{'nodelist'}->setNodesAttribs(\%nodelistHash);
|
|
$tablePoint->{'ppc'}->setNodesAttribs(\%ppcHash);
|
|
$tablePoint->{'nodehm'}->setNodesAttribs(\%nodehmHash);
|
|
|
|
web_closetables($tablePoint);
|
|
$callback->({data=>'Success: Write all Frames into xCAT database!'});
|
|
}
|
|
|
|
#-------------------------------------------------------
|
|
|
|
=head3 web_writecec
|
|
|
|
Description : work for cluster setup wizard, write cec into nodelist, ppc, nodehm table
|
|
command is "webrun writecec frameNameRange hmc/dfm cecNameRange cecnumperframe"
|
|
Arguments : nodegroupname, management method(hmc or dfm), cecname, cecnumperframe
|
|
Returns : Nothing
|
|
|
|
=cut
|
|
|
|
#-------------------------------------------------------
|
|
sub web_writecec{
|
|
my ( $request, $callback, $sub_req ) = @_;
|
|
my $frameNameRange = $request->{arg}->[1];
|
|
my $hmcFlag = $request->{arg}->[2];
|
|
my $cecNameRange = $request->{arg}->[3];
|
|
my $cecnumperframe = $request->{arg}->[4];;
|
|
my @frameNames = xCAT::NodeRange::noderange($frameNameRange, 0);
|
|
my @cecNames = xCAT::NodeRange::noderange($cecNameRange, 0);
|
|
my $tempname = '';
|
|
my $index = 0;
|
|
|
|
unless ($cecnumperframe){
|
|
$callback->({data=>'Error: cec number per frame is error!'});
|
|
return;
|
|
}
|
|
|
|
#open nodelist, ppc and nodehm table for update or add
|
|
my $tablePoint = web_opentables(['nodelist', 'ppc', 'nodehm', 'nodepos']);
|
|
unless ($tablePoint){
|
|
$callback->({data=>'Error: Connect tables failed!'});
|
|
return;
|
|
}
|
|
|
|
my %ppcHash;
|
|
my %nodelistHash;
|
|
my %nodehmHash;
|
|
my %nodeposHash;
|
|
|
|
foreach $tempname (@cecNames){
|
|
my $tempFrameid = int($index / $cecnumperframe) + 1;
|
|
my $tempCageid = 5 + ($index % $cecnumperframe) * 2;
|
|
my $parentName = $frameNames[$tempFrameid];
|
|
$nodelistHash{$tempname}{'groups'} = 'cec,all';
|
|
if ('hmc' eq $hmcFlag){
|
|
$nodehmHash{$tempname}{'mgt'} = 'hmc';
|
|
my $parentHcp = $tablePoint->getNodeAttribs($parentName, ['hcp']);
|
|
if ($parentHcp && $parentHcp->{'hcp'}){
|
|
$ppcHash{$tempname}{'hcp'} = $parentHcp->{'hcp'};
|
|
}
|
|
}
|
|
else{
|
|
$nodehmHash{$tempname}{'mgt'} = 'cec';
|
|
$ppcHash{$tempname}{'hcp'} = $tempname;
|
|
}
|
|
|
|
$ppcHash{$tempname}{'id'} = $tempCageid;
|
|
$ppcHash{$tempname}{'parent'} = $parentName;
|
|
|
|
$nodeposHash{$tempname} = {'rack' => $tempFrameid, 'u' =>$tempCageid};
|
|
|
|
$index++;
|
|
}
|
|
|
|
$tablePoint->{'nodelist'}->setNodesAttribs(\%nodelistHash);
|
|
$tablePoint->{'ppc'}->setNodesAttribs(\%ppcHash);
|
|
$tablePoint->{'nodehm'}->setNodesAttribs(\%nodehmHash);
|
|
$tablePoint->{'nodepos'}->setNodesAttribs(\%nodeposHash);
|
|
|
|
web_closetables($tablePoint);
|
|
$callback->({data=>'Success: Write all CECs into xCAT database!'});
|
|
}
|
|
|
|
1; |