On Wednesday, September 24, 2003, at 06:42 PM, Perl wrote:

I want to parse a web log file that starts with the following lines:

#Software: Microsoft Internet Information Services 6.0
#Version: 1.0
#Date: 2001-12-07 21:36:29
#Fields: date time s-ip cs-method cs-uri-stem cs-uri-query s-port
cs-username c-ip cs(User-Agent) sc-status
2001-12-07 21:36:29 192.168.73.168 GET /scripts/root.exe /c+dir 80 -
192.168.212.230 - 302
2001-12-07 21:36:29 192.168.73.168 GET /MSADC/root.exe /c+dir 80 -
192.168.212.230 - 302

I want to read the #Fields line and read the fields after that into a
list. Here is what I have and it's not working:

Could you be more specific about what exactly isn't working and how?


#construct the monthly summary

use strict; use warnings;

It helps you and it helps us help you, win win situation.

opendir (DIR, "$iislogs") || die "Unable to open $iislogs because:\n$!\n";
@dirs = readdir(DIR);
foreach $dir (@dirs) {

if ($dir =~/ex(.*)\.log/i) {
open (LOGFILE, "$iislogs\\$dir") || die "unable to open $dir
because:\n$!\n";

}

Okay, this is a problem. You open the log files, but you go on no matter what, even if you didn't open anything.


while ( <LOGFILE> ) {

my $record = <LOGFILE>;

This reads a second line. You already read one into $_ with the while loop.


        chomp $record;
        if ( /Fields/ ) {
        @fields = split / /, $record;

}




}


        
        
        
        }
        
I also want to read future lines and fill in the fields column in a
report style format that is more organized than the log file itself.

Any help is appreciated.

Here's something to read them into a big array with each entry being a hash. (untested code warning)


#!/usr/bin/perl

use strict;
use warnings;

opendir LOGS, "path/to/log/dir" or die "Directory error:  $!\n";
my @files = grep /\.log$/, readdir LOGS;
closedir LOGS;

my @log_entries; # our primary data structure

for my $log (@files) {
        open LOG, $llog or die "File error:  $!\n";
        my @field_names;
        while (<LOG>) {
                if (/^#Fields: (.+)$/) { @field_names = split ' ', $1; }
                elsif (/^#/ || /^\s*$/) { next; }
                else {
                        my @fields = split;
                        my %entry = map { ($field_names[$_], $fields[$_]) } 
0..$#field_names;
                        push @log_entries, \%entry;
                }
        }
        close LOG;
}

# Do something with @log_entries here.  I'll print it:
use Data::Dumper;
print Dumper([EMAIL PROTECTED]);

__END__

I hope that helps. Good luck.

James


-- To unsubscribe, e-mail: [EMAIL PROTECTED] For additional commands, e-mail: [EMAIL PROTECTED]



Reply via email to