Jump to content

Recommended Posts

Posted

Hi All,

I've been trying to get a Power Shell script to gather a particular event log from a list of remote computers, but as yet not had much success.

 

The script should query a list of PCs in c:\Scripts\server.txt and gather the "Operational" event log with ID 100 (i'm trying to get the boot up and login times on remote computers)

 

Script looks like:

 

 

$servers=get-content c:\scripts\servers.txt

$date=(Get-Date).AddDays(-7)

foreach ($server in $servers)

{

if (test-connection $server -quiet)

{

$arr1+=get-eventlog -logname Operational -entryType "Warning" -cn $server -after $date | ?{$_.eventid -eq "100" } | select MachineName,EventID,EntryType,Message

 

}

if ($arr1)

{$arr1 | export-csv c:\scripts\sysoutput.csv -notypeinformation}

else

{"No matching system log events found..."}

}

 

 

But keeps returning the "no event logs found". Can anyone point me in the right direction please?

 

Thanks for any help.

J.

Posted

I prefer to use Get-WinEvent as Get-EventLog is the older cmdlet. To achieve what you want with Get-WinEvent you'd do something like this:

 

Get-WinEvent -FilterHashTable @{logname='Operational';id=100;StartTime=$Date} -ComputerName $server

 

I'd check the name of the log file though, running that myself gets an error about that, if it's nested in other folders you should be able to do "\\Operational" instead.

Posted

Thanks for reply, as you can probably tell i'm no scripting guru.

You were correct that the log i'm trying to query is nested under "Applications and Services Logs\Microsoft\Windows\Diagnostics-Performance\Operational". So i've changed the script with your suggestions, but still bombs out.

Script now looks like:

 

 

 

$servers=get-content c:\scripts\servers.txt

$date=(Get-Date).AddDays(-7)

foreach ($server in $servers)

{

if (test-connection $server -quiet)

{

$arr1+=Get-WinEvent -FilterHashTable @{logname="Applications and Services Logs\Microsoft\Windows\Diagnostics-Performance\Operational" ;id=100;StartTime=$Date} -ComputerName $server

 

}

if ($arr1)

{$arr1 | export-csv c:\scripts\sysoutput.csv -notypeinformation}

else

{"No matching system log events found..."}

}

 

 

The script has been cobbled together from a few i've found so might be things in there i don't need.

Posted

If you go to Event Viewer to the actual log and choose a random event, at the bottom of the screen where it shows the details it also lists the log name. For the one you're looking for it's actually Microsoft-Windows-Diagnostics-Performance/Operational.

 

You also need to run the script as Administrator, it's a permissions thing apparently.

 

Edit: If that still doesn't work then post your error messages and I'll see what I can do to help figure it out.

Posted

Hi, thanks very much for your help. I've got the script to finally work, in that it gives me the data from that event log. Problem is, it doesn't give me the data I really needed which is the "Boot Duration" Arrrg!

 

 

J.

Posted
Hi, thanks very much for your help. I've got the script to finally work, in that it gives me the data from that event log. Problem is, it doesn't give me the data I really needed which is the "Boot Duration" Arrrg!

 

 

J.

 

That's not too difficult to get out of the XML data it stores. I'll play around with it a bit and should have something before the end of the day.

Posted

This should do what you want, replace your current $arr1+=Get-WinEvent with this section:

 

$Events =  Get-WinEvent -FilterHashTable @{logname='Microsoft-Windows-Diagnostics-Performance/Operational';id=100;StartTime=$Date} -ComputerName $Server
Foreach ($Event in $Events)
{
   $SingleEventOutput = New-Object -TypeName PSObject -Property @{'Computer'=$Server;'BootTime'='';'Date'="$($Event.TimeCreated)"}
   write-Verbose "Converting to XML"
   $EventLogXML = [xml]$Event.ToXML()
   Write-Verbose "Parsing XML and finding required entries"
foreach ($Property in $EventLogXML.Event.EventData.Data) 
   {
	if ($Property.Name -eq "BootTime") 
       {
		$SingleEventOutput.BootTime = "$($Property.'#text'/1000)"
           $arr1 += $SingleEventOutput
	}
}
}

 

It takes each event, loops through them to extracts the XML data and then examines each property to find the BootTime, pushes that to an object (converting to seconds from milliseconds) and then adds it to your variable.

  • Thanks 1
Posted

That's fantastic! You're a total genus! :)

it's giving me the info i needed, but only against the first computer in the servers.txt file. I hate to ask, as you've helped me so much, but do you know why it doesn't go through a list of PCs in the servers.txt file?

 

I think i owe you a drink or two mate :)

 

j.

Posted

Two things need to be changed:

 

move the arr1 | export-csv bit to the end, outside the foreach loop so that it runs only once.

 

At the start with the other variables (like $computers = get-content) add in $arr1 =@() to declare it as an empty array. Sometimes it will work fine without it but it's good practice to declare it like that so that it will definitely work.

  • Thanks 1

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now



×
×
  • Create New...