Sign up ×
Stack Overflow is a community of 4.7 million programmers, just like you, helping each other. Join them, it only takes a minute:

I have a log file that I am trying parse through but haven't been able to find a solution. I've copied a portion of the log file below. Each group of 3 lines is one error.

csrak17 remove int_rpsmkt
Could not perform the administration request
Error: HPDMG1064E   The group member was not found. (status 0x14c01428)
csrak17 add int_rpsops
Could not perform the administration request
Error: HPDMG1064E   The group member was not found. (status 0x14c01428)
csrak17 remove int_rpssales
Could not perform the administration request
Error: HPDMG1064E   The group member was not found. (status 0x14c01428)
csrak17 remove int_tpd
Could not perform the administration request
Error: HPDMG1064E   The group member was not found. (status 0x14c01428)
csrak17 remove int_trpit
Could not perform the administration request
Error: HPDMG1064E   The group member was not found. (status 0x14c01428)

I am loading the log file into an array and have no problem returning a line with an error code. What I need to do is first find a line with 'Error: HPDMG1064E' and then check the line two rows back to see if it has the word 'add' in it (like the second group example).

Is there a way to return a line in an array based on the value found in another? Of course I will be looping through the file and repeating the process.

Here's what I have so far but it only returns one line to my output file for some reason. Also, as you can see, I don't have any code for trying to find another index based on the current one.

$logs = Get-Content C:\Temp\test\ProdtamResults_HPDMG1064E_errors.doc
$Value = "HPDMG1064E"

foreach($log in $logs) {
    $i = 0
    while ($i -le $logs.length-1) {

        if ($logs[$i] -match $Value)
            {
                return $logs[$i] | out-file C:\Temp\test\results.txt
            }
    $i++
    }
}
share|improve this question

2 Answers 2

up vote 3 down vote accepted

Give this a try

$logs = Get-Content C:\Temp\test\ProdtamResults_HPDMG1064E_errors.doc
$Value = "HPDMG1064E"

gc $logs | select-string -Pattern $value -Context 3 | 
? { $_.context.precontext[1] -match '\sadd\s' } | select linenumber, line

This return a psobject[] with the line number and the line value of your needed match.

share|improve this answer
    
+1. This is very powershell-ish and it works. – Neolisk Sep 18 '13 at 14:33
1  
@Neolisk The magic of MatchInfo type returned by select-string ;). Thanks – CB. Sep 18 '13 at 14:36
    
Thanks C.B.! Nice elegant solution. I actually removed the 'select linenumber..' piece and am able to work with those results. – N1tr0 Sep 18 '13 at 15:38
    
@N1tr0 Glad to help! – CB. Sep 18 '13 at 15:49
    
I didn't know about -context, very useful, here's some more details: blogs.msdn.com/b/powershell/archive/2010/05/07/… – David Martin Sep 19 '13 at 7:11

Here is a reduced test case, it will output i-th line when (i-2)th line contains "add":

$file = @"
csrak17 remove int_rpsmkt
Could not perform the administration request
Error: HPDMG1064E   The group member was not found. (status 0x14c01428)
csrak17 add int_rpsops
Could not perform the administration request
Error: HPDMG1064E   The group member was not found. (status 0x14c01428)
csrak17 remove int_rpssales
Could not perform the administration request
Error: HPDMG1064E   The group member was not found. (status 0x14c01428)
csrak17 remove int_tpd
Could not perform the administration request
Error: HPDMG1064E   The group member was not found. (status 0x14c01428)
csrak17 remove int_trpit
Could not perform the administration request
Error: HPDMG1064E   The group member was not found. (status 0x14c01428)
"@;

$lines = $file -split "`n"

$Value = "HPDMG1064E";
for($i=0; $i -lt $lines.Count; $i++) {
  if($lines[$i] -match "HPDMG1064E") {
    if($lines[$i-2] -match "add") {
      Write-Host $lines[$i]; #or do something else
    }
  }
}

In your code Get-Content will have it already split by newline, so you don't have to do it.

share|improve this answer

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

Not the answer you're looking for? Browse other questions tagged or ask your own question.