--- loncom/clusteradmin 2009/05/13 19:58:32 1.3 +++ loncom/clusteradmin 2018/08/20 22:42:05 1.8 @@ -1,4 +1,29 @@ #!/usr/bin/perl +# The LearningOnline Network with CAPA +# Push admin files from cluster manager to cluster's "name servers". +# +# $Id: clusteradmin,v 1.8 2018/08/20 22:42:05 raeburn Exp $ +# +# Copyright Michigan State University Board of Trustees +# +# This file is part of the LearningOnline Network with CAPA (LON-CAPA). +# LON-CAPA is free software; you can redistribute it and/or modify +# it under the terms of the GNU General Public License as published by +# the Free Software Foundation; either version 2 of the License, or +# (at your option) any later version. +# +# LON-CAPA is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with LON-CAPA; if not, write to the Free Software +# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +# +# /home/httpd/html/adm/gpl.txt +# +# http://www.lon-capa.org/ =pod @@ -8,15 +33,18 @@ =head1 DESCRIPTION -Performs an adiminstrative action on all hosts in the current dns_hosts.tab -file. For this to work, the current host must be the cluster administrator -on the target systems. That is this must be a host in managers.tab +Performs an adminstrative update on (a) "DNS" hosts or domains in the current +dns_hosts.tab or dns_domain.tab files, or (b) update of the Certificate +Revocation List (CRL) file for the cluster. + +For this to work, the current host must be the cluster administrator +on the target systems. That is this must be a host in managers.tab. Furthermore, lonc must be running on this system. The action is specified by the 'command' parameter which may have additional arguments. All communications with remote clients are made critical so that -they will eventually happen even if the147 host we want to talk with +they will eventually happen even if the host we want to talk with is dead. @@ -39,8 +67,8 @@ on this system. 'file' is the name of t =head1 ASSUMPTIONS -Assume that loncapa is installedin /home/httpd/lib/perl so that we can use -it's modules. If this is not the case, you mus modify the +Assume that loncapa is installed in /home/httpd/lib/perl so that we can use +it's modules. If this is not the case, you must modify the use lib line in the program before you can use it. @@ -128,7 +156,8 @@ sub usage { print STDERR " subcommand describes what to actually do:\n"; print STDERR " help - Prints this message (args ignored)\n"; print STDERR " update - Updates an administrative file\n"; - print STDERR " args is one of dns_hosts.tab or dns_domain.tab\n"; + print STDERR " args is one of dns_hosts.tab, dns_domain.tab\n"; + print STDERR " or loncapaCAcrl.pem\n"; } @@ -152,12 +181,19 @@ sub usage { my $config_vars = LONCAPA::Configuration::read_conf('loncapa.conf'); my %config = %{$config_vars}; +my $logfile = $config{'lonDaemons'}.'/logs/dns_updates.log'; sub construct_table_path { my ($basename) = @_; - my $directory = $config{'lonTabDir'}; - + my $directory; + if ($basename eq 'managers.tab') { + $directory = $config{'lonTabDir'}; + } elsif ($basename eq 'loncapaCAcrl.pem') { + $directory = $config{'lonCertificateDirectory'}; + } elsif ($basename =~ /^(dns_|)(hosts|domain)\.tab$/) { + $directory = $config{'lonTabDir'}; + } return $directory . '/' . $basename; } @@ -171,14 +207,15 @@ sub get_dns_hosts() { my @result; my $hosts_tab = &construct_table_path('hosts.tab'); - open(HOSTS, "<$hosts_tab"); - while (my $line = ) { - chomp($line); - if ($line =~ /^\^/) { - $line =~ s/^\^//; # Get rid of leading ^ - $line =~ s/\s*$//; # and any trailing whitespace. - push(@result, $line); - } + if (open(HOSTS,'<',$hosts_tab)) { + while (my $line = ) { + chomp($line); + if ($line =~ /^\^/) { + if ($line =~ /^\^([\w.\-]+)/) { + push(@result,$1); + } + } + } } return (@result); } @@ -198,13 +235,13 @@ sub get_dns_hosts() # 0 - Failure with appropriate output to stderr. # sub push_file { - my ($specifier, $pushfile, $hosts) = @_; + my ($specifier, $pushfile, $hosts, $fh) = @_; # Read in the entire file: my $contents; my $line; - open(FILE, "<$pushfile"); + open(FILE,'<',$pushfile); while ($line = ) { $contents .= $line; } @@ -217,14 +254,21 @@ sub push_file { # Iterate over the hosts and run cmd as a critical # operation: + my @ids=&Apache::lonnet::current_machine_ids(); foreach my $host (@$hosts) { my $loncapa_name = &Apache::lonnet::host_from_dns($host); + next if (grep(/^\Q$loncapa_name\E$/,@ids)); my $reply = &Apache::lonnet::critical($cmd, $loncapa_name); - if ($reply ne 'ok') { - print STDERR "Reply from $host ($loncapa_name) not 'ok' was: $reply\n"; - } + my $msg; + if ($reply eq 'ok') { + $msg = "$pushfile pushed to $host ($loncapa_name): $reply\n"; + } else { + $msg = "Reply from $host ($loncapa_name) not 'ok' was: $reply\n"; + } + print $fh $msg; + print STDERR $msg; } - + return; } # @@ -247,13 +291,33 @@ sub update_file { # Validate the filename: - if ($filename eq 'dns_hosts.tab' || $filename eq 'dns_domain.tab') { - my $pushfile = &construct_table_path($filename); - my $specifier = basename($filename, ('.tab')); - my @hosts = (&get_dns_hosts()); - return &push_file($specifier, $pushfile, \@hosts); + if (($filename eq 'dns_hosts.tab') || ($filename eq 'dns_domain.tab') || + ($filename eq 'hosts.tab') || ($filename eq 'domain.tab') || + ($filename eq 'loncapaCAcrl.pem')) { + my ($result,$fh); + if (!-e $logfile) { + system("touch $logfile"); + system("chown www:www $logfile"); + } + if (open ($fh,'>>',$logfile)) { + print $fh "clusteradmin update started: ".localtime(time)."\n"; + my $pushfile = &construct_table_path($filename); + my @hosts = (&get_dns_hosts()); + my $ext = 'tab'; + if ($filename eq 'loncapaCAcrl.pem') { + $ext = 'pem'; + } + my $specifier = basename($filename, (".$ext")); + my @hosts = (&get_dns_hosts()); + $result = &push_file($specifier, $pushfile, \@hosts, $fh); + print $fh "ended: ".localtime(time)."\n"; + close($fh); + } else { + print STDERR "Could not open $logfile to append. Exiting.\n"; + } + return $result; } else { - print STDERR "Only dns_hosts.tab or dns_domain.tab can be updated\n"; + print STDERR "Only dns_hosts.tab, dns_domain.tab or loncapaCAcrl.pem can be updated\n"; &usage(); return 0; } @@ -300,6 +364,12 @@ sub is_manager { # dispatch to the appropriate command processor. # +if ($< != 0) { # Am I root? + print('You must be root in order to run clusteradmin.'. + "\n"); + exit(-1); +} + my $argc = scalar(@ARGV); if ($argc == 0) { print STDERR "Missing subcommand\n";