Updated DRBD->get_devices() and Server->parse_definition() to take 'anvil_uuid' so that server data can be parsed from anywhere.

Created, but not finished, tools/anvil-report-usage that will print a report of server resource allocation and Anvil! resource availability.

Signed-off-by: Digimer <digimer@alteeve.ca>
main
Digimer 3 years ago
parent 3ad1793c23
commit 4751c6e747
  1. 108
      Anvil/Tools/DRBD.pm
  2. 11
      Anvil/Tools/Server.pm
  3. 3
      share/words.xml
  4. 141
      tools/anvil-report-usage

@ -1045,6 +1045,10 @@ This finds all of the configured '/dev/drbdX' devices and maps them to their res
Parameters; Parameters;
=head3 anvil_uuid (optional)
If set, the C<< drbdadm dump-xml >> is not called, instead the most recent version as recorded in C<< scan_drbd -> scan_drbd_common_xml >> is loaded from one of the hosts.
=head3 password (optional) =head3 password (optional)
This is the password to use when connecting to a remote machine. If not set, but C<< target >> is, an attempt to connect without a password will be made. This is the password to use when connecting to a remote machine. If not set, but C<< target >> is, an attempt to connect without a password will be made.
@ -1070,48 +1074,102 @@ sub get_devices
my $debug = defined $parameter->{debug} ? $parameter->{debug} : 3; my $debug = defined $parameter->{debug} ? $parameter->{debug} : 3;
$anvil->Log->entry({source => $THIS_FILE, line => __LINE__, level => $debug, key => "log_0125", variables => { method => "DRBD->get_devices()" }}); $anvil->Log->entry({source => $THIS_FILE, line => __LINE__, level => $debug, key => "log_0125", variables => { method => "DRBD->get_devices()" }});
my $anvil_uuid = defined $parameter->{anvil_uuid} ? $parameter->{anvil_uuid} : "";
my $password = defined $parameter->{password} ? $parameter->{password} : ""; my $password = defined $parameter->{password} ? $parameter->{password} : "";
my $port = defined $parameter->{port} ? $parameter->{port} : ""; my $port = defined $parameter->{port} ? $parameter->{port} : "";
my $remote_user = defined $parameter->{remote_user} ? $parameter->{remote_user} : "root"; my $remote_user = defined $parameter->{remote_user} ? $parameter->{remote_user} : "root";
my $target = defined $parameter->{target} ? $parameter->{target} : ""; my $target = defined $parameter->{target} ? $parameter->{target} : "";
$anvil->Log->variables({source => $THIS_FILE, line => __LINE__, level => $debug, list => { $anvil->Log->variables({source => $THIS_FILE, line => __LINE__, level => $debug, list => {
anvil_uuid => $anvil_uuid,
password => $anvil->Log->is_secure($password), password => $anvil->Log->is_secure($password),
port => $port, port => $port,
remote_user => $remote_user, remote_user => $remote_user,
target => $target, target => $target,
}}); }});
# Is this a local call or a remote call? # If we've got an anvil_uuid, search for the drbd common XML from the database.
my $host = $anvil->Get->short_host_name; my $host = $anvil->Get->short_host_name;
my $shell_call = $anvil->data->{path}{exe}{drbdadm}." dump-xml"; my $output = "";
my $output = ""; if ($anvil_uuid)
if ($anvil->Network->is_local({host => $target}))
{ {
# Local. if (not exists $anvil->data->{anvils}{anvil_uuid}{$anvil_uuid})
($output, $anvil->data->{drbd}{'drbdadm-xml'}{return_code}) = $anvil->System->call({shell_call => $shell_call}); {
$anvil->Database->get_anvils({debug => $debug});
if (not exists $anvil->data->{anvils}{anvil_uuid}{$anvil_uuid})
{
# Failed to find the Anvil! data.
$anvil->Log->entry({source => $THIS_FILE, line => __LINE__, level => 0, priority => "err", key => "error_0360", variables => { anvil_uuid => $anvil_uuid }});
return("!!error!!");
}
}
my $node1_host_uuid = $anvil->data->{anvils}{anvil_uuid}{$anvil_uuid}{anvil_node1_host_uuid};
my $node2_host_uuid = $anvil->data->{anvils}{anvil_uuid}{$anvil_uuid}{anvil_node2_host_uuid};
$anvil->Log->variables({source => $THIS_FILE, line => __LINE__, level => $debug, list => { $anvil->Log->variables({source => $THIS_FILE, line => __LINE__, level => $debug, list => {
output => $output, node1_host_uuid => $node1_host_uuid,
"drbd::drbdadm-xml::return_code" => $anvil->data->{drbd}{'drbdadm-xml'}{return_code}, node2_host_uuid => $node2_host_uuid,
}}); }});
my $query = "
SELECT
scan_drbd_common_xml
FROM
scan_drbd
WHERE
scan_drbd_host_uuid = '618e8007-3a0b-4bbf-a616-a64fd7d2dc30'
OR
scan_drbd_host_uuid = '75070e21-a0e3-4ba5-b4f7-476bf5d08107'
ORDER BY modified_date DESC
LIMIT 1
;";
$anvil->Log->variables({source => $THIS_FILE, line => __LINE__, level => $debug, list => { query => $query }});
my $results = $anvil->Database->query({query => $query, source => $THIS_FILE, line => __LINE__});
my $count = @{$results};
$anvil->Log->variables({source => $THIS_FILE, line => __LINE__, level => $debug, list => {
results => $results,
count => $count,
}});
if (not $count)
{
# Nothing found
$anvil->Log->entry({source => $THIS_FILE, line => __LINE__, level => 0, priority => "err", key => "error_0361", variables => { anvil_uuid => $anvil_uuid }});
return("!!error!!");
}
$output = $results->[0]->[0];
$anvil->Log->variables({source => $THIS_FILE, line => __LINE__, level => $debug, list => { output => $output }});
} }
else else
{ {
# Remote call. # Is this a local call or a remote call?
($output, my $error, $anvil->data->{drbd}{'drbdadm-xml'}{return_code}) = $anvil->Remote->call({ my $shell_call = $anvil->data->{path}{exe}{drbdadm}." dump-xml";
debug => $debug, if ($anvil->Network->is_local({host => $target}))
shell_call => $shell_call, {
target => $target, # Local.
port => $port, ($output, $anvil->data->{drbd}{'drbdadm-xml'}{return_code}) = $anvil->System->call({shell_call => $shell_call});
password => $password, $anvil->Log->variables({source => $THIS_FILE, line => __LINE__, level => $debug, list => {
remote_user => $remote_user, output => $output,
}); "drbd::drbdadm-xml::return_code" => $anvil->data->{drbd}{'drbdadm-xml'}{return_code},
$host = $target; }});
$anvil->Log->variables({source => $THIS_FILE, line => __LINE__, level => $debug, list => { }
host => $host, else
error => $error, {
output => $output, # Remote call.
"drbd::drbdadm-xml::return_code" => $anvil->data->{drbd}{'drbdadm-xml'}{return_code}, ($output, my $error, $anvil->data->{drbd}{'drbdadm-xml'}{return_code}) = $anvil->Remote->call({
}}); debug => $debug,
shell_call => $shell_call,
target => $target,
port => $port,
password => $password,
remote_user => $remote_user,
});
$host = $target;
$anvil->Log->variables({source => $THIS_FILE, line => __LINE__, level => $debug, list => {
host => $host,
error => $error,
output => $output,
"drbd::drbdadm-xml::return_code" => $anvil->data->{drbd}{'drbdadm-xml'}{return_code},
}});
}
} }
# Clear the hash where we'll store the data. # Clear the hash where we'll store the data.

@ -1259,6 +1259,10 @@ B<< Note >>: This method currently parses out data needed for specific tasks, an
Parameters; Parameters;
=head3 anvil_uuid (optional)
If passed, the C<< anvil_uuid >> will be passed on to C<< DRBD->get_devices >>.
=head3 server (required) =head3 server (required)
This is the name of the server whose XML is being parsed. This is the name of the server whose XML is being parsed.
@ -1297,12 +1301,14 @@ sub parse_definition
$anvil->Log->entry({source => $THIS_FILE, line => __LINE__, level => $debug, key => "log_0125", variables => { method => "Server->parse_definition()" }}); $anvil->Log->entry({source => $THIS_FILE, line => __LINE__, level => $debug, key => "log_0125", variables => { method => "Server->parse_definition()" }});
# Source is required. # Source is required.
my $anvil_uuid = defined $parameter->{anvil_uuid} ? $parameter->{anvil_uuid} : "";
my $server = defined $parameter->{server} ? $parameter->{server} : ""; my $server = defined $parameter->{server} ? $parameter->{server} : "";
my $source = defined $parameter->{source} ? $parameter->{source} : ""; my $source = defined $parameter->{source} ? $parameter->{source} : "";
my $definition = defined $parameter->{definition} ? $parameter->{definition} : ""; my $definition = defined $parameter->{definition} ? $parameter->{definition} : "";
my $host = defined $parameter->{host} ? $parameter->{host} : $anvil->Get->short_host_name; my $host = defined $parameter->{host} ? $parameter->{host} : $anvil->Get->short_host_name;
my $target = $anvil->Get->short_host_name(); my $target = $anvil->Get->short_host_name();
$anvil->Log->variables({source => $THIS_FILE, line => __LINE__, level => $debug, list => { $anvil->Log->variables({source => $THIS_FILE, line => __LINE__, level => $debug, list => {
anvil_uuid => $anvil_uuid,
server => $server, server => $server,
source => $source, source => $source,
definition => $definition, definition => $definition,
@ -1344,7 +1350,10 @@ sub parse_definition
$anvil->data->{server}{$target}{$server}{$source}{parsed} = $server_xml; $anvil->data->{server}{$target}{$server}{$source}{parsed} = $server_xml;
# Get the DRBD data that this server will almost certainly be using. # Get the DRBD data that this server will almost certainly be using.
$anvil->DRBD->get_devices({debug => $debug}); $anvil->DRBD->get_devices({
debug => $debug,
anvil_uuid => $anvil_uuid,
});
# Pull out some basic server info. # Pull out some basic server info.
$anvil->data->{server}{$target}{$server}{$source}{info}{uuid} = $server_xml->{uuid}->[0]; $anvil->data->{server}{$target}{$server}{$source}{info}{uuid} = $server_xml->{uuid}->[0];

@ -504,6 +504,9 @@ The output, if any, was;
<key name="error_0356">Failed to read the kernel release on the host: [#!variable!target!#]. The return code was: [#!variable!return_code!#] (expected '0') and the release output, if any, was: [#!variable!output!#].</key> <key name="error_0356">Failed to read the kernel release on the host: [#!variable!target!#]. The return code was: [#!variable!return_code!#] (expected '0') and the release output, if any, was: [#!variable!output!#].</key>
<key name="error_0357">The program: [#!variable!program!#] is using: [#!variable!ram_used!#] (#!variable!ram_used_bytes!# Bytes). This is probably caused by a memory leak, so we will now exit so that systemctl can restart us. If this is happening repeatedly, please contact support.</key> <key name="error_0357">The program: [#!variable!program!#] is using: [#!variable!ram_used!#] (#!variable!ram_used_bytes!# Bytes). This is probably caused by a memory leak, so we will now exit so that systemctl can restart us. If this is happening repeatedly, please contact support.</key>
<key name="error_0358">This is not a Striker host.</key> <key name="error_0358">This is not a Striker host.</key>
<key name="error_0359">There are no databases available, exiting.</key>
<key name="error_0360">Unable to find the Anvil! information for the Anvil! UUID: [#!variable!anvil_uuid!#].</key>
<key name="error_0361">Unable to find the DRBD config from either node in the Anvil! with the Anvil! UUID: [#!variable!anvil_uuid!#]. Has scan_drbd (as part of scancore) run on either nodes?</key>
<!-- Files templates --> <!-- Files templates -->
<!-- NOTE: Translating these files requires an understanding of which lines are translatable --> <!-- NOTE: Translating these files requires an understanding of which lines are translatable -->

@ -0,0 +1,141 @@
#!/usr/bin/perl
use strict;
use warnings;
use Anvil::Tools;
use Data::Dumper;
use Text::Diff;
$| = 1;
my $THIS_FILE = ($0 =~ /^.*\/(.*)$/)[0];
my $running_directory = ($0 =~ /^(.*?)\/$THIS_FILE$/)[0];
if (($running_directory =~ /^\./) && ($ENV{PWD}))
{
$running_directory =~ s/^\./$ENV{PWD}/;
}
my $anvil = Anvil::Tools->new();
$anvil->data->{switches}{brief} = 0;
$anvil->Get->switches();
$anvil->Log->variables({source => $THIS_FILE, line => __LINE__, level => 2, list => {
"switches::brief" => $anvil->data->{switches}{brief},
}});
$anvil->Database->connect();
$anvil->Log->entry({source => $THIS_FILE, line => __LINE__, level => 1, key => "log_0132"});
if (not $anvil->data->{sys}{database}{connections})
{
# No databases, exit.
$anvil->Log->entry({source => $THIS_FILE, line => __LINE__, level => 0, 'print' => 1, priority => "err", key => "error_0359"});
$anvil->nice_exit({exit_code => 1});
}
gather_data($anvil);
$anvil->nice_exit({exit_code => 0});
#############################################################################################################
# Functions #
#############################################################################################################
sub gather_data
{
my ($anvil) = @_;
collect_anvil_data($anvil);
collect_server_data($anvil);
# collect_cpu_data($conf);
# collect_ram_data($conf);
# collect_storage_data($conf);
# collect_server_data($conf);
# collect_bridges($conf);
return(0);
}
sub collect_server_data
{
my ($anvil) = @_;
$anvil->Database->get_anvils();
$anvil->Database->get_servers();
$anvil->Database->get_server_definitions();
foreach my $server_uuid (sort {$a cmp $b} keys %{$anvil->data->{servers}{server_uuid}})
{
my $server_name = $anvil->data->{servers}{server_uuid}{$server_uuid}{server_name};
my $anvil_uuid = $anvil->data->{servers}{server_uuid}{$server_uuid}{server_anvil_uuid};
my $anvil_name = $anvil->data->{anvils}{anvil_uuid}{$anvil_uuid}{anvil_name};
my $server_definition = $anvil->data->{server_definitions}{server_definition_server_uuid}{$server_uuid}{server_definition_xml};
my $server_ram = $anvil->data->{servers}{server_uuid}{$server_uuid}{server_ram_in_use};
if ($anvil->data->{servers}{server_uuid}{$server_uuid}{server_configured_ram} > $server_ram)
{
$server_ram = $anvil->data->{servers}{server_uuid}{$server_uuid}{server_configured_ram};
}
$anvil->Log->variables({source => $THIS_FILE, line => __LINE__, level => 2, list => {
's1:server_name' => $server_name,
's2:anvil_name' => $anvil_name,
's3:server_ram' => $anvil->Convert->add_commas({number => $server_ram})." (".$anvil->Convert->bytes_to_human_readable({'bytes' => $server_ram}).")",
}});
my $target = $anvil->Get->short_host_name;
my $source = "from_db";
$anvil->Server->parse_definition({
debug => 2,
source => $source,
server => $server_name,
definition => $server_definition,
anvil_uuid => $anvil_uuid,
});
# CPU info
my $total_cores = $anvil->data->{server}{$target}{$server_name}{$source}{cpu}{total_cores};
my $cpu_sockets = $anvil->data->{server}{$target}{$server_name}{$source}{cpu}{sockets};
my $cpu_cores = $anvil->data->{server}{$target}{$server_name}{$source}{cpu}{cores};
my $cpu_threads = $anvil->data->{server}{$target}{$server_name}{$source}{cpu}{threads};
my $cpu_model = $anvil->data->{server}{$target}{$server_name}{$source}{cpu}{model_name};
my $cpu_fallback = $anvil->data->{server}{$target}{$server_name}{$source}{cpu}{model_fallback};
my $cpu_match = $anvil->data->{server}{$target}{$server_name}{$source}{cpu}{match};
my $cpu_vendor = $anvil->data->{server}{$target}{$server_name}{$source}{cpu}{vendor};
my $cpu_mode = $anvil->data->{server}{$target}{$server_name}{$source}{cpu}{mode};
$anvil->Log->variables({source => $THIS_FILE, line => __LINE__, level => 2, list => {
's1:total_cores' => $total_cores,
's2:cpu_sockets' => $cpu_sockets,
's3:cpu_cores' => $cpu_cores,
's4:cpu_threads' => $cpu_threads,
's5:cpu_model' => $cpu_model,
's6:cpu_fallback' => $cpu_fallback,
's7:cpu_match' => $cpu_match,
's8:cpu_vendor' => $cpu_vendor,
's9:cpu_mode' => $cpu_mode,
}});
# Storage info.
}
return(0);
}
sub collect_anvil_data
{
my ($anvil) = @_;
# Get a list of Anvil's and what free RAM and disk space they have available.
$anvil->Database->get_anvils();
foreach my $anvil_name (sort {$a cmp $b} keys %{$anvil->data->{anvils}{anvil_name}})
{
# $anvil->data->{anvils}{anvil_name}{$anvil_name}{anvil_uuid} = $anvil_uuid;
# $anvil->data->{anvils}{anvil_name}{$anvil_name}{anvil_description} = $anvil_description;
# $anvil->data->{anvils}{anvil_name}{$anvil_name}{anvil_node1_host_uuid} = $anvil_node1_host_uuid;
# $anvil->data->{anvils}{anvil_name}{$anvil_name}{anvil_node2_host_uuid} = $anvil_node2_host_uuid;
# $anvil->data->{anvils}{anvil_name}{$anvil_name}{anvil_dr1_host_uuid} = $anvil_dr1_host_uuid;
}
return(0);
}
Loading…
Cancel
Save