Networker

Re: [Networker] Need NSRADMIN Output Examples for Script Testing

2004-05-07 16:48:54
Subject: Re: [Networker] Need NSRADMIN Output Examples for Script Testing
From: Byron Servies <bservies AT PACANG DOT COM>
To: NETWORKER AT LISTMAIL.TEMPLE DOT EDU
Date: Fri, 7 May 2004 13:48:44 -0700
On May 07, 2004 at 19:37, Peter L. Buschman wrote:
>
> Thank you very much for the example below.  It is quite helpful.  In my
> case, reading the resource files directly is not an option so I have
> to parse the raw nsradmin output.

Hi,

Several years ago I did a perl module that correctly handles
the different possible cases of nsradmin output.  I am also
including a little script that uses it so you can see how to
parse the output.  This worked on both unix and windows at
the time.

HTH,

Byron

--- cut here sample.pl ---
#!/usr/bin/perl

use Nsradmin;

set_nsradmin("/usr/sbin/nsradmin");

$server = "myserver";
$query  = "type: NSR";
$show   = "";
$options = "";

@reslist = query($server, $query, $show, $options);

#
# A reslist is a list of resources.  Resources are a
# hash of attributes, which have a name and value lists.
#
foreach $res (@reslist) {
        %attrlist = %{$res};
        foreach $attr (sort keys %attrlist) {
                @vallist = @{$attrlist{$attr}};
                printf "%s: ", $attr;
                foreach $val (@vallist) {
                        printf "$val\t";
                }
                printf "\n";
        }
}


--- cut here: Nsradmin.pm ----

package Nsradmin;
require Exporter;
@ISA    = qw(Exporter);
@EXPORT = qw(
        set_nsradmin
        create_tmpfile
        query
        write_lines
        $nsradmin
);

$nsradmin = "nsradmin";

1;

sub set_nsradmin {
        my ($path) = @_;
        $nsradmin = $path;
}

sub query {
        my ($server, $query, $show, $options) = @_;
        my @lines;
        my @reslist;
        my @reslines;
        my %attrlist;
        my $cmd;
        my $append;
        my $append_next;

        # Prep the command to change display options
        $options = "option $options";

        # Prep the command for which attributes to show
        $show = "show $show";

        # Prep the command for the query to perform
        $query = "print $query";

        # Write the query to a temporary file
        $queryfile = &write_lines($options, $show, $query);

        # Determine the command to execute
        $cmd = "$nsradmin -s $server -i $queryfile";

        # Execute the query and parse the results
        $append = 0;
        open CMD, "$cmd |" || die "could not execute \"$cmd\"";
        while (<CMD>) {
                # Skip the option output
                next if (/^Dynamic|Hidden|Resource/o);

                # Skip the list of display options
                if (/^Display options:/) {
                        # Read the next 3 lines
                        $_ = <CMD>;
                        $_ = <CMD>;
                        $_ = <CMD>;
                        next;
                }

                # Skip any show lines
                next if (/^Will show all attributes/);

                if ($append == 0 && /^\s*$/) {
                        #
                        # Blank lines start a new resource, but only if we are 
not
                        # searching for the end of the previous attribute.
                        #
                        if (scalar @lines > 0) {
                                # The lines array represents a resource
                                push @reslines, [ @lines ];
                                @lines = ();
                        }
                        next;
                }

                # Eliminate leading and trailing whitespace only if we are not
                # still searching for the end of an
                s/^\s+// unless ($append);
                s/\s+$// unless ($append);

                if (/\\\s*$/) {
                        # Remove the backslash from the input line if it exists
                        s/\\\s*$//;
                        $append_next = 1;
                }

                # Determine if this line should be added to the previous line 
or not
                if ($append != 0) {
                        # Append this line to the last line in the array
                        $lines[$#lines] .= $_;
                } elsif ($#lines != -1 && $lines[$#lines] !~ /;\s*/) {
                        #
                        # The previous line does not end with a semi-colon.
                        # Add the current line to the previous line
                        #
                        $lines[$#lines] .= $_;
                } else {
                        # Add the ordinary line to the list of lines
                        push @lines, $_;
                }

                if ($lines[$#lines] !~ /;\s*/o) {
                        #
                        # The current line does not end with a semi-colon.  The
                        # next line must be appended until one is found and the
                        # value list is complete.
                        #
                        $append_next = 1;
                }
                $append = $append_next;
                $append_next = 0;
        }

        #
        # Append the most recent set of lines to the results if there was no
        # blank line at the end of the output
        #
        if (scalar @lines > 0) {
                push @reslines, [ @lines ];
                @lines = ();
        }

        # Delete the query file.  The command pipeline closes itself.
        unlink $queryfile;

        #
        # Separete the lines of each resource into a list of hashes.  The hash
        # keys are the attribute names and their values are a list of the
        # attributes values.
        #
        foreach $lines (@reslines) {
                %attrlist = ();

                # The lines are in and compressed.  Now separated them into a 
hash
                foreach $line (@$lines) {
                        if ($line =~ /(^[\w\s]+):(.*)$/ms) {
                                $attrname = $1;
                                $2 =~ /^\s*(.*);$/ms;
                                $value = $1;

                                # The following loop is from the book
                                # "Mastering Regular Expressions", page 205.
                                # Jeffrey Friedl, O'Reilly & Associates, Inc.
                                #
                                # It was modified to use the delimiter
                                # (, ) instead of a simle comma for use
                                # with RAP.
                                #
                                @vallist = ();
                                while ($value =~
m/"([^"\\]*(\\.[^"\\]*)*)"(,\s+)?|([^,]+)(,\s+)?|(,\s+)/g) {
                                        push(@vallist, defined($1) ? $1 : $4);
                                }
                                push(@vallist, undef) if $value =~ m/,$/;


                                #
                                # Make sure the attribute is in the array,
                                # regardless of how many values it may or may
                                # not have.
                                #
                                $attrlist{$attrname} = ();
                                foreach $value (@vallist) {
                                        #
                                        # strip leading and trailing whitespace 
from
                                        # all values
                                        #
                                        $value =~ s/^\s+//;
                                        $value =~ s/\s+$//;

                                        # Skip empty values
                                        next if (length $value == 0);
                                        push @{$attrlist{$attrname}}, $value;
                                }
                        }
                }

                # Add the attrlist hash to the resource list
                push @reslist, { %attrlist };

        }

        return @reslist;
}

sub create_tmpfile {
        my $filename;

        if (defined $ENV{TMPDIR}) {
                $filename = $ENV{TMPDIR} . "/" . "tmp$$";
        } elsif (defined $ENV{TMP}) {
                $filename = $ENV{TMP} . "/" . "tmp$$";
        } else {
                $filename = "/tmp/" . "tmp$$";
        }
}

sub write_lines {
        my @lines = @_;

        $tmpfile = &create_tmpfile;

        open TMPFILE, "> $tmpfile" || die "could open $tmpfile for writting";
        print TMPFILE join "\n", @lines;
        print TMPFILE "\n";
        close TMPFILE;

        return $tmpfile;
}

1;

--
Note: To sign off this list, send a "signoff networker" command via email
to listserv AT listmail.temple DOT edu or visit the list's Web site at
http://listmail.temple.edu/archives/networker.html where you can
also view and post messages to the list.
=*=*=*=*=*=*=*=*=*=*=*=*=*=*=*=*=*=*=*=*=*=*=*=*=*=*=*=*=*=*=*=