Beefy Boxes and Bandwidth Generously Provided by pair Networks
Don't ask to ask, just ask
 
PerlMonks  

Accessing 2nd level elements in XML::Simple and using the data in an SNMP call

by wruehl (Acolyte)
on Jul 31, 2007 at 12:35 UTC ( #629816=perlquestion: print w/replies, xml ) Need Help??

wruehl has asked for the wisdom of the Perl Monks concerning the following question:

For my first Perl project(IE I've never used Perl before) I'm using XML Simple to process the data in a program that will need to store the xml data as variables. I can access the first level code, but don't really know the snyax to access the second level hash. Below is the code followed by the results of a data dump, this should show more closely what I'm trying to do. What I need to be able to do is pull the data from all the tags, and as of right now I can't pull the data from the sub tags of DeviceA and DeviceB. I'm also having issues with getting the SNMP syntax correct, which is why that code is commented out. That code was a result of trying an example that I found online, but like most of the examples of NET::SNMP get that I found, it was not easy to understand, so I just tried to alter it for my purposes, and wasn't successful.

Ideally what I'd like to be able to do is Run the SNMPget command within the foreach loop and report the findings to a seperate file. Eventually this code will be used by NetIQ to run a port monitoring script and will have calls to the their libraries for the reporting.

Also if anyone could give me tips on the proper input to the Net::SNMP snmpget function that would be appreciated, all of the examples I've seen have used some form of variable to extract the target. What I'd like to do is be able to use the IP address and port from the foreach statement in my request, and store the results in variables to either be logged or reported in some way. I already have the OID that I'll need to be accessing, so if possible I'd like to know the syntax for that sort of request.

#!/usr/bin/perl -w #use strict; #modules used use XML::Simple; use Data::Dumper; use Net::SNMP; our ($data, $xml, $e, $Host, $OID, $port, $CMD, $value, $SNMP_TARGET , + $SNMP_GET_CMD); #create object $xml = new XML::Simple; # MIB Hard value taken from parameters of the DC1 fab port pairs scrip +t appended a 1 to test port #1 $OID = ".1.3.6.1.4.1.289.2.1.1.2.3.1.1.152.1"; #checking against PD110 as a test run will probably be read from an XM +L input file in the future $Host = "10.2.125.110"; # read the XML file #$CMD = "snmpget -v1 -c public -Ovq -m "; #chomp($value = '${CMD} ${Host} .1.3.6.1.4.1.289.2.1.1.2.3.1.1.152.1') +; #print $value; $data = $xml->XMLin("FabPortPairs.xml"); #print Dumper($data); foreach $e (@{$data->{PairedDevices}}) #Do actions that require use of XML data in this loop possibly #call SNMP data gathering and reporting { print "Pairname is: " . $e->{PairName} . "\n "; print "Hosted Apps are: " . $e->{HostedApplication} . "\n" ; print "HostOS is: " . $e->{HostOS} . "\n"; }
Data dump output of one iteration of the file:
$VAR1 = { 'PairedDevices' => [ { 'DeviceB' => { 'SNMPCommunity' => 'public +', 'DeviceNickName' => 'SD131 +', 'SNMPPortIndex' => '19', 'IPAddress' => '10.2.125.1 +31', 'PathName' => '01', 'RealPort' => '18' }, 'ExclusionIndicator' => {}, 'PairName' => 'Chestnut', 'MetricSeverity' => '34', 'MinPercent' => '20', 'HostOwningGroup' => 'AIX Team', 'StatusAlertThisPair' => 'Y', 'DeviceA' => { 'SNMPCommunity' => 'public +', 'DeviceNickName' => 'SD130 +', 'SNMPPortIndex' => '19', 'IPAddress' => '10.2.125.1 +30', 'PathName' => '00', 'RealPort' => '18' }, 'StatusSeverity' => '31', 'HostedEnvironment' => 'Test', 'MetricAlertThisPair' => 'Y', 'MaxPercent' => '80', 'HostedApplication' => 'IEOR', 'HostOS' => 'AIX' },
Thanks, Bill

Replies are listed 'Best First'.
Re: Accessing 2nd level elements in XML::Simple and using the data in an SNMP call
by FunkyMonk (Chancellor) on Jul 31, 2007 at 12:58 UTC
    After fixing up your sample data (it's missing a closing bracket & brace) and shortening it, your code runs fine:

    my $data = { 'PairedDevices' => [ { 'PairName' => 'Chestnut', 'MetricSeverity' => '34', 'MinPercent' => '20', 'HostOwningGroup' => 'AIX Team', 'StatusAlertThisPair' => 'Y', 'StatusSeverity' => '31', 'HostedEnvironment' => 'Test', 'MetricAlertThisPair' => 'Y', 'MaxPercent' => '80', 'HostedApplication' => 'IEOR', 'HostOS' => 'AIX' } ] }; foreach my $e (@{$data->{PairedDevices}}) { print "Pairname is: " . $e->{PairName} . "\n "; print "Hosted Apps are: " . $e->{HostedApplication} . "\n" ; print "HostOS is: " . $e->{HostOS} . "\n"; }

    Output:

    Pairname is: Chestnut Hosted Apps are: IEOR HostOS is: AIX

    You don't really want to comment out use strict. Really, you don't. Removing strict doesn't fix problems, it just hides them. The problems lurk, hidden, until the time you least want them to reappear.

      I only commented out the use strict because I was testing random SNMP functions and didn't want to have to go and declare them in each iteration. Once I know what I'm going to be doing(which variable names and the like) I'll put them in the header and uncomment the use strict.

        I don't think strict does what you think it does. There's no need to pre-declare variables or functions (subs) in Perl. However, strict will complain about you using global variables without explicit package names. All you have to do is use lexically-scoped variables. It does this for very good reasons.

        Or, in other words, when you first use a variable, use my:

        my $xml = new XML::Simple;

        When we advocate use strict;, we do so with good reason and as a result of vast experience. Personally -- I've been screwed over a few times because I was too lazy to work with strict in place. And vicariously -- we've all helped folks solve problems that would have been entirely avoided with the use of strict and warnings.

        So please, use strict; use warnings; -- it really will help you learn good Perl more quickly!

        <radiant.matrix>
        Ramblings and references
        The Code that can be seen is not the true Code
        I haven't found a problem yet that can't be solved by a well-placed trebuchet
Re: Accessing 2nd level elements in XML::Simple and using the data in an SNMP call
by oha (Friar) on Jul 31, 2007 at 12:47 UTC
    i'm a bit confused by the lines commented out. btw on the documentation on cpan about XML::Simple at the very beginning (QUICK START) it's explained how to get to the second level and further:
    print $config->{server}->{kalahari}->{address}->[1];
    so in your case, you can do something like
    $data->{PairedDevices}->{DeciveA}->{DeviceNickName}
    will return 'SD130' i have no knowledge about snmp so for that i must pass Oha

Log In?
Username:
Password:

What's my password?
Create A New User
Node Status?
node history
Node Type: perlquestion [id://629816]
Approved by b10m
help
Chatterbox?
and the web crawler heard nothing...

How do I use this? | Other CB clients
Other Users?
Others perusing the Monastery: (5)
As of 2021-06-13 09:07 GMT
Sections?
Information?
Find Nodes?
Leftovers?
    Voting Booth?
    What does the "s" stand for in "perls"? (Whence perls)












    Results (54 votes). Check out past polls.

    Notices?