--- loncom/Attic/lonManage 2003/08/18 09:56:01 1.7 +++ loncom/Attic/lonManage 2003/09/08 09:45:20 1.14 @@ -3,9 +3,9 @@ # # lonManage supports remote management of nodes in a LonCAPA cluster. # -# $Id: lonManage,v 1.7 2003/08/18 09:56:01 foxr Exp $ +# $Id: lonManage,v 1.14 2003/09/08 09:45:20 foxr Exp $ # -# $Id: lonManage,v 1.7 2003/08/18 09:56:01 foxr Exp $ +# $Id: lonManage,v 1.14 2003/09/08 09:45:20 foxr Exp $ # # Copyright Michigan State University Board of Trustees # @@ -50,6 +50,36 @@ # not the IP address of the host. # # $Log: lonManage,v $ +# Revision 1.14 2003/09/08 09:45:20 foxr +# Remove BUGBUG about comment about authentication as we'll be doing +# host based authentication initially (no need for lonManage to do anything), +# and certificate based later (need at that time). +# +# Revision 1.13 2003/08/19 10:26:24 foxr +# Initial working version... tested against an unmodified lond this +# produces an unknown_cmd response which is about what I'd expect. +# +# Revision 1.12 2003/08/18 11:08:07 foxr +# Debug request building in Transact. +# +# Revision 1.11 2003/08/18 10:45:32 foxr +# Felt strongly enough about hoisting ReadConfiguration into a separate sub +# that I did it now before I forgot. +# +# Revision 1.10 2003/08/18 10:43:31 foxr +# Code/test ValidHost. The hosts.tab and the perl variables are read in as +# global hashes as a side effect. May later want to clean this up by making +# a separate getconfig function and hoisting the config reads into that. +# +# Revision 1.9 2003/08/18 10:25:46 foxr +# Write ReinitProcess function in terms of ValidHost and Transact. +# +# Revision 1.8 2003/08/18 10:18:21 foxr +# Completed PushFile function in terms of +# - ValidHost - Determines if target host is valid. +# - Transact - Performs one of the valid transactions with the +# appropriate lonc<-->lond client/server pairs. +# # Revision 1.7 2003/08/18 09:56:01 foxr # 1. Require to be run as root. # 2. Catch case where no operation switch is supplied and put out usage. @@ -71,10 +101,25 @@ # Add usage and skeleton documentation. # # + + + +# Modules required: + use strict; # Because it's good practice. use English; # Cause I like meaningful names. use Getopt::Long; +use LONCAPA::Configuration; # To handle configuration I/O. +use IO::Socket::UNIX; # To communicate with lonc. + +# File scoped variables: + +my %perlvar; # Perl variable defs from apache config. +my %hostshash; # Host table as a host indexed hash. +# +# prints out utility's command usage info. +# sub Usage { print "Usage:"; print <new(Peer =>"$peerfile", + Type => SOCK_STREAM, + Timeout => 10) + or return "con_lost"; + print $client "$cmd\n"; + my $answer=<$client>; + if (!$answer) { $answer="con_lost"; } + chomp($answer); + return $answer; +} +# >>> BUGBUG <<< # # Use Getopt::Long to parse the parameters of the program. # @@ -179,6 +247,86 @@ sub ParseArgs { return @result; } # +# Read the loncapa configuration stuff. +# +sub ReadConfig { + my $perlvarref = LONCAPA::Configuration::read_conf('loncapa.conf'); + %perlvar = %{$perlvarref}; + my $hoststab = LONCAPA::Configuration::read_hosts( + "$perlvar{'lonTabDir'}/hosts.tab"); + %hostshash = %{$hoststab}; + +} +# +# Determine if the target host is valid. +# This is done by reading the current hosts.tab file. +# For the host to be valid, it must be inthe file. +# +# Parameters: +# host - Name of host to check on. +# Returns: +# true if host is valid. +# false if host is invalid. +# +sub ValidHost { + my $host = shift; + + ReadConfig; + + return defined $hostshash{$host}; + +} + + + +# +# Performs a transaction with lonc. +# By the time this is called, the transaction has already been +# validated by the caller. +# +# Parameters: +# +# host - hosts.tab name of the host whose lonc we'll be talking to. +# command - The base command we'll be asking lond to execute. +# body - [optional] If supplied, this is a command body that is a ref. +# to an array of lines that will be appended to the +# command. +# +# NOTE: +# The command will be done as an encrypted operation. +# +sub Transact { + my $host = shift; + my $command = shift; + my $haveBody= 0; + my $body; + my $i; + + if(scalar @ARG) { + $body = shift; + $haveBody = 1; + } + # Construct the command to send to the server: + + my $request = "encrypt\:"; # All requests are encrypted. + $request .= $command; + if($haveBody) { + $request .= "\:"; + my $bodylines = scalar @$body; + for($i = 0; $i < $bodylines; $i++) { + $request .= $$body[$i]; + } + } else { + $request .= "\n"; + } + # Body is now built... transact with lond.. + + my $answer = subreply($request, $host); + + print "$answer\n"; + +} +# # Called to push a file to the remote system. # The only legal files to push are hosts.tab and domain.tab. # Security is somewhat improved by @@ -194,15 +342,68 @@ sub ParseArgs { # tablefile - name of the file containing the table to push. # host - name of the host to push this file to. # +# >>>BUGBUG<<< This belongs in lonnet.pm. +# sub PushFile { my $tablename = shift; my $tablefile = shift; my $host = shift; -} + # Open the table file: + + if(!open(TABLEFILE, "<$tablefile")) { + die "ENOENT - No such file or directory $tablefile"; + } + + # Require that the host be valid: + + if(!ValidHost($host)) { + die "EHOSTINVAL - Invalid host $host"; # Ok so I invented this 'errno'. + } + # Read in the file. If the table name is valid, push it. + my @table = ; # These files are pretty small. + close TABLEFILE; + + if( ($tablename eq "host") || + ($tablename eq "domain")) { + Transact($host, "pushfile:$tablename",\@table); + } else { + die "EINVAL - Invalid parameter. tablename: $tablename must be host or domain"; + } +} +# +# This function is called to reinitialize a server in a remote host. +# The servers that can be reinitialized are: +# - lonc - The lonc client process. +# - lond - The lond daemon. +# NOTE: +# Reinitialization in this case means re-scanning the hosts table, +# starting new lond/lonc's as approprate and stopping existing lonc/lond's. +# +# Parameters: +# process - The name of the process to reinit (lonc or lond). +# host - The host in which this reinit will happen. +# +# >>>BUGBUG<<<< This belongs in lonnet.pm +# sub ReinitProcess { - print "Reinitializing a process\n"; + my $process = shift; + my $host = shift; + + # Ensure the host is valid: + + if(!ValidHost($host)) { + die "EHOSTINVAL - Invalid host $host"; + } + # Ensure target process selector is valid: + + if(($process eq "lonc") || + ($process eq "lond")) { + Transact($host, "reinit:$process"); + } else { + die "EINVAL -Invalid parameter. Process $process must be lonc or lond"; + } } #--------------------------- Entry point: -------------------------- @@ -275,6 +476,9 @@ Usage: =item strict =item Getopt::Long =item English +=item IO::Socket::UNIX + +=head1 KEY Subroutines. =head1 CATEGORIES Command line utility