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

After reading in a text file, I get a hash reference in my text file (HASH(0x223bb84)) if the field is blank. If the is not blank, it works fine. I am taking multiple fields from multiple text files and putting them into a comma delimited text file. Also, I would appreciate any ones comments to improve the script.
#!/usr/bin/perl -w use strict; use File::Glob; use XML::Simple; open DIPFILE, ">> C:/director/DIPFILE.TXT"; open LOGFILE, ">> C:/director/DIPLOG.LOG"; #Pull in all the xml files for each report. my @dipfile = glob('C:/director/*.xml'); foreach my $x (@dipfile) { my $ref = XML::Simple::XMLin($x); print '"' . $x . '","' . $ref->{defaultName} . '","' . $ref->{defa +ultDescription} . '","' . $ref->{reportExecutionTime} . '"' . "\n"; printf DIPFILE '"' . $x . '","' . $ref->{defaultName} . '","' . $r +ef->{defaultDescription} . '","' . $ref->{reportExecutionTime} . '"' +. "\n"; printf LOGFILE '"' . $x . '","' . $ref->{defaultName} . '","' . $r +ef->{defaultDescription} . '","' . $ref->{reportExecutionTime} . '"' +. "\n"; }
Thanks, Dave

Replies are listed 'Best First'.
Re: Reading XML File Hash in text
by Your Mother (Archbishop) on May 22, 2009 at 22:33 UTC

    Semi-tested (I don't know Text::CSV so I might not be using it as well as possible). You'll be much happier if you use some more robust approaches to XML (XML::LibXML), CSV, and file handling. This might not be final but it's worth playing around with the pieces and approach.

    use strict; use warnings; use XML::LibXML; use Text::CSV; open my $dip_file, ">>", "C:/director/DIPFILE.TXT" or die "Couldn't open DIP file for appending: $!"; open my $dip_log, ">>", "C:/director/DIPLOG.TXT" or die "Couldn't open DIP log for appending: $!"; my $csv = Text::CSV->new; # glob is a built-in, you don't need to "use File::Glob." my @dipfile = glob('C:/director/*.xml'); my $parser = XML::LibXML->new(); # set options for $parser here if needed, like $parser->recover(1) for # messed up XML. for my $xml_file ( @dipfile ) { my $doc = $parser->parse_file($xml_file); my ( $default_name ) = $doc->findnodes("//defaultName"); my ( $default_description ) = $doc->findnodes("//defaultDescriptio +n"); my ( $report_execution_time ) = $doc->findnodes("//reportExecution +Time"); $csv->combine( $xml_file, $default_name ? $default_name->textContent : "", $default_description ? $default_description->textCo +ntent : "", $report_execution_time ? $report_execution_time->te +xtContent : "", ); # Update: print $csv->string, "\n"; # To see it in the terminal. $dip_file->print( $csv->string, "\n" ); $dip_log->print( $csv->string, "\n" ); }
      I'll take a look at it. Thanks, Dave
Re: Reading XML File Hash in text
by juster (Friar) on May 23, 2009 at 05:13 UTC

    I think you want the SupressEmpty option. Copy/pasted from the XML::Simple CPAN page:

    SuppressEmpty => 1 | '' | undef # in+out - handy

    This option controls what XMLin() should do with empty elements (no attributes and no content). The default behaviour is to represent them as empty hashes. Setting this option to a true value (eg: 1) will cause empty elements to be skipped altogether. Setting the option to 'undef' or the empty string will cause empty elements to be represented as the undefined value or the empty string respectively. The latter two alternatives are a little easier to test for in your code than a hash with no keys.

      Yes, that worked perfectly.
Re: Reading XML File Hash in text
by Anonymous Monk on May 22, 2009 at 23:00 UTC
    You might want to try using the ForceArray => 1 option in XML::Simple. That solved my problem when I was sometimes getting a hash reference but sometimes not. (I'm not sure entirely how it handles blank fields, however.)