use strict;
use warnings;
use XML::Twig;
use Text::CSV;
use Data::Dump 'pp';
use Data::Dumper;
use REST::Client;
use MIME::Base64;
use Text::Unidecode;
use utf8;
my @header = ();
my @csv_rows = ();
my $order_by = 'u_ci_id';
my %seen = ();
my %arx_data = ();
# parse xml in chunks
my $twig = 'XML::Twig'->new( twig_handlers => { result => \&record });
my $client = REST::Client->new(host => 'https://host.com');
my $encoded_auth = encode_base64("user:password", '');
$client->GET("/api/now/table/cmdb_ci?sysparm_limit=1000",
{'Authorization' => "Basic $encoded_auth",
'Accept' => 'application/xml'});
my $input_xml = $client->responseContent();
$twig->xparse($input_xml);
# data dump
pp \%arx_data;
#pp \@csv_rows;
#pp \@header;
# sort and dump csv
my @sorted = sort { $b->[0] cmp $a->[0] } @csv_rows;
unshift @sorted,[@header]; # add header
my $outfile = 'xmldump.csv';
my $csv = Text::CSV->new ( { binary => 1 } )
or die "Cannot use CSV: ".Text::CSV->error_diag ();
$csv->eol("\n");
if ($outfile){
open my $fh, ">:encoding(utf8)", $outfile or die "$outfile: $!";
for (@sorted){
shift @$_; # remove sort field
$csv->print ($fh, $_);
}
close $fh or die "new.csv: $!";
} else {
for (@sorted){
shift @$_;
$csv->print (\*STDOUT, $_);
}
}
# parse 1 record
sub record {
my ($e,$t) = @_;
# csv records
unless (@header){
my @info_tags = $t->children;
@header = map{ $_->name } @info_tags;
unshift @header,$order_by; # add sort field
}
# extract data in same order as header row
my @data = map{ $t->field($_) } @header;
push @csv_rows, clean(@data); #returns array ref
# build hash structure
my $app = $t->field('u_application_id');
my $u_ci = $t->field('u_ci_id');
my $class = $t->field('sys_class_name');
my $name = $t->field('name');
my $ip = $t->field('ip_address');
my $fqdn = $t->field('fqdn');
my $dns = $t->field('dns_domain');
my $mac = $t->field('mac');
if ( $class eq 'cmdb_ci_appl'){
$arx_data{$u_ci}{'name'} = $name;
} else {
next if $seen{$app}{$ip}++;
push @{$arx_data{$app}{'members'}},$ip;
}
}
sub clean {
my @f = @_;
for (@f){
s/\r|\n//g; # Cleanup Carraige Returns
s/, / /g; # Cleanup Comma Space
s/,/ /g; # Cleanup Comma
s/"//g; # Cleanup Parentheses
s/^\s+|\s+$//g; # Trim spaces
s/([^[:ascii:]]+)/unidecode($1)/ge;
}
return \@f;
}
main::(vance.pl:13): my @header = ();
DB<1> c
Exiting subroutine via next at vance.pl line 91.
at vance.pl line 91.
main::record(XML::Twig=HASH(0x6003eaed0), XML::Twig::Elt=HASH(0x60
+2c20438)) called at /usr/lib/perl5/site_perl/5.22/XML/Twig.pm line 23
+48
|