On Tue, May 26, 2009 at 05:03:12PM +0200, Hannes Eder wrote:
> Match the output of `ipvsadm -L -n` against a given ldirectord
> configuration file to produce a verbose status sub-command output, to
> see which virtual and which real servers are up or down, plus some
> additional information.
Hi Hannes,
sorry for taking an extra long time to notice this one.
The change seems reasonable to me, and I'm happy to commit it
(assuming that it still applies). But I am wondering if
it would be better to add this to ipvsadm. What do you think?
> ---
>
> The output mimics format of NetScaler "show" commands.
>
> Comments?
>
> Best,
> Hannes
>
> diff -r 15160b7b2a93 ldirectord/ldirectord.in
> --- a/ldirectord/ldirectord.in Tue May 26 13:55:29 2009 +0200
> +++ b/ldirectord/ldirectord.in Tue May 26 15:57:00 2009 +0200
> @@ -999,6 +999,8 @@
> print STDERR "ldirectord for $CONFIG is running with
> pid: $oldpid\n";
> ld_cmd_children("status", %LD_INSTANCE);
> ld_log("ldirectord for $CONFIG is running with pid:
> $oldpid");
> + ld_setup();
> + ld_show_status();
> ld_log("Exiting from ldirectord $CMD");
> ld_exit(0, "Exiting from ldirectord $CMD");
> }
> @@ -1019,6 +1021,8 @@
> $status = 3;
> }
> print "ldirectord is stopped for $CONFIG\n";
> + ld_setup();
> + ld_show_status();
> ld_exit($status, "Exiting from ldirectord $CMD");
> } else {
> ld_log("ldirectord is stopped for $CONFIG");
> @@ -4966,3 +4970,138 @@
> {
> return ld_find_cmd_path($_[0], $ENV{'PATH'}, $_[1]);
> }
> +
> +# mode_disp_str
> +# helper for ld_show_status
> +sub mode_disp_str
> +{
> + my ($mode) = (@_);
> + my %map = (
> + gate => "DSR",
> + masq => "NAT",
> + ipip => "TUN"
> + );
> + return exists($map{$mode}) ? "$map{$mode} ($mode)" : "? ($mode)";
> +}
> +
> +# scheduler_disp_str
> +# helper for ld_show_status
> +sub scheduler_disp_str
> +{
> + my ($scheduler) = (@_);
> +
> + # stolen from the ipvsadm-1.2.0 manpage
> + my %scheduler_disp_strs = (
> + rr => "Robin Robin",
> + wrr => "Weighted Round Robin",
> + lc => "Least-Connection",
> + wlc => "Weighted Least-Connection",
> + lblc => "Locality-Based Least-Connection",
> + lblcr => "Locality-Based Least-Connection with Replication",
> + dh => "Destination Hashing",
> + sh => "Source Hashing",
> + sed => "Shortest Expected Delay",
> + nq => "Never Queue"
> + );
> +
> + my $scheduler_name = $scheduler_disp_strs{$scheduler};
> + $scheduler_name = "?" if (!defined($scheduler_name));
> + $scheduler_name =~ tr/ -//d;
> + return uc($scheduler_name) . " ($scheduler)";
> +}
> +
> +# ld_show_status
> +# Write a verbose status to STDOUT. It does so by matching the output of
> +# ipvsadm against the given config file. No IPC to the running ldirectord
> +# daemon is performed.
> +#
> +# pre: read_config() and ld_setup() have been called.
> +# return: none
> +sub ld_show_status
> +{
> + # read and parse `ipvsadm -L -n`
> + my $ipvs = &ld_read_ipvsadm();
> +
> + print "\n";
> +
> + foreach my $cv (@VIRTUAL) {
> + my $real_service = &get_virtual($cv) . " " . $cv->{protocol};
> + my $crs = $cv->{real};
> + my $irs = $ipvs->{$real_service}->{real};
> + my $fb = fallback_find($cv);
> + my $real_str;
> + my $r;
> +
> + my $state = exists($ipvs->{$real_service}) ? "UP" : "DOWN";
> + print "\t", get_virtual($cv), " - ", uc($$cv{protocol}), "\n";
> + print "\tState: ", $state, "\n";
> +
> + my $eff_state = "DOWN";
> + for $r (values %$irs) {
> + if ($$r{weight} > 0) {
> + $eff_state = "UP";
> + last;
> + }
> + }
> +
> + if ($eff_state eq "DOWN" and defined($fb)) {
> + $real_str = "$$fb{server}:$$fb{port}";
> + if (defined($$irs{$real_str})
> + and $$irs{$real_str}->{weight} > 0) {
> + $eff_state = "FALLBACK";
> + }
> + }
> +
> + print "\tEffective State: ", $eff_state, "\n";
> + print "\tMethod: ", scheduler_disp_str($$cv{scheduler}), "\n";
> + print "\tConfig Options:\n";
> + for my $key (sort keys %$cv) {
> + next if ($key =~
> m/^(server|port|protocol|real|flags|proto|fallback|scheduler)$/m);
> + my $value = $$cv{$key};
> + next if (!defined($value) or $value eq "");
> + print "\t\t$key: $value\n";
> + }
> + print "\n";
> +
> + my $r_nr = 1;
> +
> + # list fallback
> + if (defined($fb)) {
> + $state = "FALLBACK";
> + print $r_nr, ")\t", $$fb{server}, ":", $$fb{port},
> + " - ", uc($$cv{protocol}),
> + " Mode: ", mode_disp_str($$fb{forward}),
> + " State: ", $state,
> + "\tWeight: ", $$fb{weight}, "\n";
> + $r_nr++;
> + delete($$irs{"$$fb{server}:$$fb{port}"});
> + }
> +
> + # list real servers which are in the config (up or down)
> + for $r (@$crs) {
> + $real_str = "$$r{server}:$$r{port}";
> + $state = (!defined($$irs{$real_str})
> + or $$irs{$real_str}->{weight} == 0) ? "DOWN"
> : "UP";
> + print $r_nr, ")\t", $$r{server}, ":" , $$r{port},
> + " - ", uc($$cv{protocol}),
> + " Mode: ", mode_disp_str($$r{forward}),
> + " State: ", $state,
> + "\tWeight: ", $$r{weight}, "\n";
> + $r_nr++;
> + delete($$irs{$real_str});
> + }
> +
> + # list real servers which are up but NOT in the config
> + $state = "UP (NOT IN CFG)";
> + while (($real_str, $r) = each %$irs) {
> + print $r_nr, ")\t", $real_str,
> + " - ", uc($$cv{protocol}),
> + " Mode: ", mode_disp_str($$r{forward}),
> + " State: ", $state,
> + "\tWeight: ", $$r{weight}, "\n";
> + $r_nr++;
> + }
> +
> + print "\n";
> + }
> +}
> _______________________________________________________
> Linux-HA-Dev: [email protected]
> http://lists.linux-ha.org/mailman/listinfo/linux-ha-dev
> Home Page: http://linux-ha.org/
_______________________________________________________
Linux-HA-Dev: [email protected]
http://lists.linux-ha.org/mailman/listinfo/linux-ha-dev
Home Page: http://linux-ha.org/