Extracting a multiple level XML using Perl
I'm trying to extract data from an XML file.
The format of the XML is as follows:
<notifications>
<notification name="ccmSmtp" oid="1.3.6.1" status="current">
<objects>
<object module="callhome" name="ccmSmtp"/>
</objects>
<description>
This is a d开发者_如何学Goescription
</description>
</notification>
<notification name="ccmAlertGroup" oid="1.3.6.1" status="current">
<objects>
<object module="callhome" name="callHome"/>
</objects>
<description>
This is a description
</description>
</notification>
<notification name="ccmAlert" oid="1.3.6.1" status="current">
<objects>
<object module="callhome" name="callHome"/>
</objects>
<description>
This is a description
</description>
</notification>
<notification name="ccmSmtp" oid="1.3.6.1" status="current">
<objects>
</objects>
<description>
This is a description
</description>
</notification>
</notifications>
I have written the following code to extract the notifications node from example.xml file.
#!/usr/bin/perl
use XML::Simple;
use Data::Dumper;
$xml = new XML::Simple;
$data = $xml->XMLin("example.xml",KeyAttr => {
notifications => notification => 'name'
});
$notification = $data->{notifications};
print Dumper($notification);
When I run the above Perl file I get the following output:
$VAR1 = {
'notification' => [
{
'objects' => {
'object' => {
'name' => 'ccmSmtp',
'module' => 'callhome'
}
},
'status' => 'current',
'oid' => '1.3.6.',
'name' => 'ccmSmtp',
'description' => ' This is a mib '
},
{
'objects' => {
'object' => {
'name' => 'callHome',
'module' => 'module'
}
},
'status' => 'current',
'oid' => '1.3.6.1.4',
'name' => 'ccmAlert',
'description' => 'This is a description'
},
{
'objects' => {
'object' => {
'name' => 'callHome',
'module' => 'homemib'
}
},
'status' => 'current',
'oid' => '1.3.6.1.4',
'name' => 'ccmAlertf',
'description' => 'This is a description'
},
{
'objects' => {},
'status' => 'current',
'oid' => '1.3.6.1',
'name' => 'ccmSmtp',
'description' => ' This is an example'
}
]
};
My question is, how can I extract the contents of notification node and store the values in separate variables/array ?
Generally for extracting items from XML I would start with XPath. There is an XPath package for Perl, probably even in the XML package you're already using.
$notification
is just a ref to a hash with one key 'notification' that has an array of hashes.
You could loop through it by doing
for my $n ( @{$notification->{notification}} ) {
# ie. to get status out, this is same for description,oid,name
my $status = $n->{status};
# To get the nested 'objects' data object module value (phew)
my $object_module = $n->{status}{object}{module};
}
I am unclear what it is you want. The code you posted did not produce that output as it will not compile, but if you wrote instead
my $data = $xml->XMLin("x.xml", KeyAttr => ['notification']);
print Dumper $data;
then you would get exactly that. Now $data->{notification} is a reference to an array of four hashes (corresponding to the four elements) which can be accessed as
my $note0 = $data->{notification}[0];
etc. Does this answer your question?
I would looped like below :
foreach $NOTIFICATION( @{$data->{'notification}})
{
foreach $OBJECT (@{$NOTIFICATION->{'OBJECT'}})
{
$name=$NOTIFICATION->{'name'}; $module=$OBJECT->{'module'};
Print $name , $module
}
}
精彩评论