Question

I have multiple log files that looks like dmesg output. I need to parse and store certain result from all these files into one single output file. Ex Input file1:

 .....
 Started 1399343129
 KbPerSec  1222
 KiloBytes 9302938
 Status 83
 StorageUNit unitname
 Ended 1399473434
 .......

Output file:

  1399343129  1222  9302938 83 unitname 1399473434
  <input file2 numbers>
  <input file3 numbers>
  .....

So, I use grep, and split the grep result to get the number I want. Here is what my code looks like. <TRY> is my file handle.

my (@grepres, @splitres);
my ($size, $start, $bw);

if(@grepres=grep{/KbPerSec/} <TRY>){
  @splitres=split(' ',$grepres[0]);
  $bw=$splitres[1];
  print "1. $bw\n";
}

if(@grepres=grep{/Started/} <TRY>){
  @splitres=split(' ',$grepres[0]);
  $start=$splitres[1];
  print "$start\n";
}

...
  1. But my code only executes the first if, and then stops. Why does it not execute the other if statements?
  2. This doesnt seem like an efficient way to do this. How can I do better?
Was it helpful?

Solution

  1. Because <TRY> in list context consumes all the data in the TRY filehandle, making subsequent calls to <TRY> return empty. If you want to reuse the data in the filestream, either

a. save the stream to a variable

 my @try = <TRY>;
 if ( grep ..., @try ) {
    ...
 }
 if ( grep ..., @try ) { 
    ...
 }

b. reopen the file or seek back to the beginning

 open TRY, '<', $try_file
 ...
 if (grep ..., <TRY>) {
    ...
 }
 close TRY;
 open TRY, '<', $try_file
 if (grep ..., <TRY>) {
    ...
 }

 open TRY, '<', $try_file
 ...
 if (grep ..., <TRY>) {
    ...
 }

 seek TRY, 0, 0;  # reset cursor position to start of file

 if (grep ..., <TRY>) {
    ...
 }

OTHER TIPS

Here is a possible approach that depends on the fields being in the same order from record to record.

Update: Changed the end condition match.

#!/usr/bin/perl
use strict;
use warnings;

my @data;
while (<DATA>) {
    if (/^Started/ .. /^Ended/) {
        push @data, /^\S+ (.+)$/;
        print join(" ", splice @data), "\n" if /^Ended/;    
    }
}

__DATA__
.....
Started 1399343129
KbPerSec  1222
KiloBytes 9302938
Status 83
StorageUNit unitname
Ended 1399473434
.......

Prints

1399343129  1222 9302938 83 unitname 1399473434
Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top