in reply to 3par data acquistion

Why not use something like IO::Pipe and get rid of awk completely. I suspect that the code below is 'not ideal' for example you very likely don't want/need a sub call to run_command I pass in system, protocol (rsh|ssh) and command in my case so it ate the sub call for some flexibility

#!/usr/bin/perl use strict; use warnings; use IO::Pipe; my @systems = ('3par-S400','3par-E200'); my $system = undef; my $output = undef; my $command = undef; foreach $system (@systems) { $output = run_command($system); while (<$output>) { next if (m/^$/); last if (m/^Press.*/) #grab bits here instead of using awk } close($output); } sub run_command { my $system = shift; my $protocol = 'ssh'; my $command = "statvv -ni"; my $space = " "; #The following is bad but it works for now.. my $do_command = $protocol . $space . $system . $space . $command; my $cmd = new IO::Pipe; $cmd->reader($do_command); return $cmd; }

Replies are listed 'Best First'.
Re^2: 3par data acquistion
by bluethundr (Pilgrim) on Aug 17, 2010 at 16:03 UTC
    Thanks! This is a very elegant solution and gets me closer to my goal of parsing the output of the 3par commands.

    Just to give you a more complete idea of what I'm dealing with, here is a sample of the output of the statvv -ni commamd :

    $:ssh -l gmon 3par-S400 statvv -ni 11:48:42 08/17/10 r/w I/O per second KBytes per sec Sv +t ms IOSz KB VVname Cur Avg Max Cur Avg Max Cur + Avg Cur Avg Qlen mgmain_data t 412 412 412 17794 17794 17794 5.9 + 5.9 43.2 43.2 3 mgnote01_redo1 t 2 2 2 21 21 21 0.9 + 0.9 9.2 9.2 0 mgnote01_redo2 t 2 2 2 21 21 21 1.4 + 1.4 9.2 9.2 0 mg_date_oraarch t 0 0 0 2 2 2 1.8 + 1.8 4.1 4.1 0 mgtool02_oraarch t 1 1 1 4 4 4 0.3 + 0.3 4.1 4.1 0 mgtool02_data_110G t 238 238 238 1987 1987 1987 20.0 +20.0 8.3 8.3 6 mgtool02_redo1_3G t 9 9 9 40 40 40 0.7 + 0.7 4.6 4.6 0 mgtool02_redo2_3G t 9 9 9 40 40 40 0.3 + 0.3 4.6 4.6 0 mgnote01_data_85G t 3 3 3 45 45 45 4.6 + 4.6 16.4 16.4 0 rcat11_data t 2 2 2 30 30 30 0.2 + 0.2 16.4 16.4 0 racprod_redo1a_tpvv t 189 189 189 33379 33379 33379 11.8 +11.8 176.4 176.4 6
    Ideally what I would like to do is grab each discrete piece of info and stock that in it's own variable so that I can graph trends in each one. As much as I love perl, I'm a little too novice to do this just yet, tho I strive to be able to do things like this!

    As it stands now there is no output from the script. If I take the $output variable and print it, this is what I see:

    [gmon@cc126-200:~] $:./3par-disk-stats.pl IO::Pipe::End=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0xe0e9410)IO::Pipe::En +d=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0xe0 +e9410)IO::Pipe::End=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0xe0e9410)IO::P +ipe::End=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0xe0e9410)IO::Pipe::End=GL +OB(0xe0e9410)IO::Pipe::End=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0xe0e941 +0)IO::Pipe::End=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0xe0e9410)IO::Pipe: +:End=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0 +xe0e9410)IO::Pipe::End=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0xe0e9410)IO +::Pipe::End=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0xe0e9410)IO::Pipe::End +=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0xe0e +9410)IO::Pipe::End=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0xe0e9410)IO::Pi +pe::End=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0xe0e9410)IO::Pipe::End=GLO +B(0xe0e9410)IO::Pipe::End=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0xe0e9410 +)IO::Pipe::End=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0xe0e9410)IO::Pipe:: +End=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0x +e0e9410)IO::Pipe::End=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0xe0e9410)IO: +:Pipe::End=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0xe0e9410)IO::Pipe::End= +GLOB(0xe0e9410)IO::Pipe::End=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0xe0e9 +410)IO::Pipe::End=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0xe0e9410)IO::Pip +e::End=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0xe0e9410)IO::Pipe::End=GLOB +(0xe0e9410)IO::Pipe::End=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0xe0e9410) +IO::Pipe::End=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0xe0e9410)IO::Pipe::E +nd=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0xe +0e9410)IO::Pipe::End=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0xe0e9410)IO:: +Pipe::End=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0xe0e9410)IO::Pipe::End=G +LOB(0xe0e9410)IO::Pipe::End=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0xe0e94 +10)IO::Pipe::End=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0xe0e9410)IO::Pipe +::End=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0xe0e9410)IO::Pipe::End=GLOB( +0xe0e9410)IO::Pipe::End=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0xe0e9410)I +O::Pipe::End=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0xe0e9410)IO::Pipe::En +d=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0xe0 +e9410)IO::Pipe::End=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0xe0e9410)IO::P +ipe::End=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0xe0e9410)IO::Pipe::End=GL +OB(0xe0e9410)IO::Pipe::End=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0xe0e941 +0)IO::Pipe::End=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0xe0e9410)IO::Pipe: +:End=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0 +xe0e9410)IO::Pipe::End=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0xe0e9410)IO +::Pipe::End=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0xe0e9410)IO::Pipe::End +=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0xe0e +9410)IO::Pipe::End=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0xe0e9410)IO::Pi +pe::End=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0xe0e9410)IO::Pipe::End=GLO +B(0xe0e9410)IO::Pipe::End=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0xe0e9410 +)IO::Pipe::End=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0xe0e9410)IO::Pipe:: +End=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0x +e0e9410)IO::Pipe::End=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0xe0e9410)IO: +:Pipe::End=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0xe0e9410)IO::Pipe::End= +GLOB(0xe0e9410)IO::Pipe::End=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0xe0e9 +410)IO::Pipe::End=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0xe0e9410)IO::Pip +e::End=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0xe0e9410)IO::Pipe::End=GLOB +(0xe0e9410)IO::Pipe::End=GLOB(0xe0e9410)IO::Pipe::End=GLOB(0xe1c9ca0) +IO::Pipe::End=GLOB(0xe1c9ca0)IO::Pipe::End=GLOB(0xe1c9ca0)IO::Pipe::E +nd=GLOB(0xe1c9ca0)IO::Pipe::End=GLOB(0xe1c9ca0)IO::Pipe::End=GLOB(0xe +1c9ca0)IO::Pipe::End=GLOB(0xe1c9ca0)IO::Pipe::End=GLOB(0xe1c9ca0)IO:: +Pipe::End=GLOB(0xe1c9ca0)IO::Pipe::End=GLOB(0xe1c9ca0)IO::Pipe::End=G +LOB(0xe1c9ca0)IO::Pipe::End=GLOB(0xe1c9ca0)IO::Pipe::End=GLOB(0xe1c9c +a0)IO::Pipe::End=GLOB(0xe1c9ca0)IO::Pipe::End=GLOB(0xe1c9ca0)IO::Pipe +::End=GLOB(0xe1c9ca0)IO::Pipe::End=GLOB(0xe1c9ca0)IO::Pipe::End=GLOB( +0xe1c9ca0)IO::Pipe::End=GLOB(0xe1c9ca0)IO::Pipe::End=GLOB(0xe1c9ca0)I +O::Pipe::End=GLOB(0xe1c9ca0)IO::Pipe::End=GLOB(0xe1c9ca0)IO::Pipe::En +d=GLOB(0xe1c9ca0)IO::Pipe::End=GLOB(0xe1c9ca0)IO::Pipe::End=GLOB(0xe1 +c9ca0)IO::Pipe::End=GLOB(0xe1c9ca0)IO::Pipe::End=GLOB(0xe1c9ca0]
    So I'm really unsure at this point how I can get at the data that I want. But it looks like you've dealt well with the end of the output with this chunk of code!
    while (<$output>) { next if (m/^$/); last if (m/^Press.*/) #grab bits here instead of using awk }
    Without access to awk, however, I am really unsure as to how I can grab the data I want and throw that into some variables I can use. Thanks

      Use the "$_" scalar to work with individual lines inside the while loop. You can do something like this until you get comfortable with "$_"

      next if (m/^$/); last if (m/^Press.*/) my $line = $_; #grab bits here instead of using awk
      I'd also suggest looking at split to put the data into variables:
      ($rw,$io_s_cur,$io_s_avg,$io_s_max,$kb_s_cur,$kb_s_avg,$kb_s_max,$svt_ +ms_cur,$svt_ms_avg,$iosz_cur,$iosz_avg,$qlen) = split(/\s+/, $line, 1 +3);

      The last bit is the first 3 lines in this output; unless you need them for something I'd use the "last if" in the first code block above as a starting point; change last to next and modify the match m//

        I for some reason am getting the following error from my perl program I am trying to use to gather info from our 3par units.

        "my" variable %parvalues masks earlier declaration in same scope at ./ +3par-test2.pl line 23. "my" variable $parkeys masks earlier declaration in same statement at +./3par-test2.pl line 24. "my" variable %parvalues masks earlier declaration in same statement a +t ./3par-test2.pl line 24. "my" variable $parkeys masks earlier declaration in same statement at +./3par-test2.pl line 24. syntax error at ./3par-test2.pl line 22, near "$parvalues{" Global symbol "$parelement" requires explicit package name at ./3par-t +est2.pl line 22. Execution of ./3par-test2.pl aborted due to compilation errors.


        Could someone please explain why these "my" variable are not correctly declared?

        #!/usr/bin/perl use strict; use warnings; use IO::Pipe; my @systems = ('3par-S400','3par-E200'); my $system = undef; my $output = undef; my $command = undef; foreach $system (@systems) { $output = run_command($system); while (<$output>) { next if (m/^$/); last if (m/^Press.*/); #print $_ . "\n"; my $parvalues{$parelement} = ($_ .=~/(.*?)\t+/g) { foreach my $parkeys (sort keys %parvalues){ print $parkeys, "\t", $parvalues{$parkeys}, "\n"; } } } close($output); } sub run_command { my $system = shift; my $protocol = 'ssh'; my $command = "statvv -ni"; my $space = " "; #The following is bad but it works for now.. my $do_command = $protocol . $space . $system . $space . $command; my $cmd = new IO::Pipe; $cmd->reader($do_command); return $cmd; }


        thank you monks for all your help so far!