Write-Eventlog pipe issue - powershell

Task:
Writing piped data from object to eventlog:
RecId|Date/Time|Sev|Src|EvtType|Sensor|EvtDetail
0001|01/01/1600:00:00|INF|BMC|Eventlog|SELFullness|LogCleared
0002|01/01/1600:00:01|MAJ|BMC|Eventlog|Progress|PostError
0003|01/01/1600:00:02|INF|BMC|PowerUnit|HostPower|PowerOff
0004|01/01/1600:00:03|MAJ|BMC|SystemFirmware|SELFullness|PostError
0005|01/01/1600:00:04|INF|BMC|OsBoot||C:bootcompleted
This little CSV is stored in D:\Powershell\Bmc.log is nearly a parsed output of ipmitool.exe (isel -c) on a server.
$raw = Get-Content .\Bmc.log
$sel = ConvertFrom-CSV -InputObject $raw -Delimiter "|"
$sel | Where-Object {$_.Sev -eq "INF"} | Out-GridView
This works well, I can use $sel as object, can list its members etc.
Now I want to dump all records to eventlog, but it does not work.
My Approach:
New-Eventlog -LogName HardwareEvents -Source BMC
$sel | Where-Object {$_.Sev -eq "INF"} | Write-Eventlog -LogName HardwareEvents -Source BMC -EventId 999 -Message {$_.EvtDetail} -EntryType INFORMATION
It seems that Write-Eventlog does not accept pipes.
Aim is not to use a loop.

As you suspected and others have pointed out, Write-EventLog doesn't read from the pipeline. Wrap it in a ForEach-Object statement:
$sel | Where-Object {$_.Sev -eq "INF"} | ForEach-Object {
Write-EventLog -LogName HardwareEvents -Source BMC -EventId 999 -Message $_.EvtDetail -EntryType INFORMATION
}
Otherwise you'd need to wrap Write-EventLog in a custom function that does process pipeline input:
function Write-EventLogMessage {
[CmdletBinding()]
Param(
[Parameter(
Mandatory=$true,
Position=0
ValueFromPipeline=$true,
ValueFromPipelineByPropertyName=$true
)]
[string]$Message
)
Process {
Write-EventLog -LogName HardwareEvents -Source BMC -EventId 999 -Message $Message -EntryType INFORMATION
}
}
$sel | Where-Object {$_.Sev -eq "INF"} | Write-EventLogMessage

Related

Powershell script does not continue on write-eventlog

I have the following block in script that checks a log file and if it finds a specific line, should continue.
$keywords=Get-Content "C:\Users\user\desktop\keywords.txt"
Get-Content "C:\Users\user\desktop\some.log" -tail 1 -wait |
ForEach-object {
foreach($word in $keywords) {
if($_ -match "$word") {
Write-EventLog -LogName Application -EventID 2001 -EntryType Information -Source serviceCheck -Message "[SUCCESS] The service has been initialized"
Write-Host "[SUCCESS] The service has been initialized"
}
}
} | Select -First 1
This logs the event but never continues with the rest of the script.
If I put some other command in if($_ -match "$word") {get-date} for example or anything else, it works and continues to the next command.
How should this be made to write in event viewer and continue?
You need to output something for the Select -First 1 statement to react to:
$keywords = Get-Content "C:\Users\user\desktop\keywords.txt"
Get-Content "C:\Users\user\desktop\some.log" -tail 1 -wait |ForEach-object {
foreach ($word in $keywords) {
if ($_ -match "$word") {
Write-EventLog -LogName Application -EventID 2001 -EntryType Information -Source serviceCheck -Message "[SUCCESS] The service has been initialized"
Write-Host "[SUCCESS] The service has been initialized"
"literally any value will do!"
}
}
} | Select -First 1 |Out-Null

Powershell Get-EventLog output issue when logging

I am having an issue with the writing of a get-eventlog function when I'm writing to a TXT file.
This is my LogWrite function:
#Log Function
$Logfile = "..\Logs\$(gc env:computername)_Outlook.log"
$Stamp = (Get-Date).toString("yyyy/MM/dd HH:mm:ss")
Function LogWrite
{
Param ([string]$logstring)
Add-content $Logfile -value $Stamp": "$logstring -Force
}
This is my LogWrite code in part of my script.
$OutlookHangDetailed = Get-EventLog -Log "Application" -Source "Application Hang" -Message "*OUTLOOK.EXE*" -After (Get-Date).AddHours(-12) -ErrorAction SilentlyContinue
LogWrite $OutlookHangDetailed | Format-List
The issue I am having is its coming out like this in the txt file:
Microsoft.PowerShell.Commands.GenericMeasureInfo
But if I simply echo it, it comes out like this (This is an example):
Index : 2568
EntryType : Information
InstanceId : 15
Message : Updated Symantec Endpoint Protection status successfully to SECURITY_PRODUCT_STATE_ON.
Category : (0)
CategoryNumber : 0
ReplacementStrings : {Symantec Endpoint Protection, SECURITY_PRODUCT_STATE_ON}
Source : SecurityCenter
TimeGenerated : 3/15/2017 7:46:02 AM
TimeWritten : 3/15/2017 7:46:02 AM
How can I get this to write to the log this way?
There is no output from your log function. You are not piping anything into Format-List
$OutlookHangDetailed is going to be an array of objects of [System.Diagnostics.EventLogEntry]. You can turn it into a string with $logstring | fl | out-string. Casting directly to a string isn't going to give you the output you are looking for.
$Logfile = "..\Logs\$(gc env:computername)_Outlook.log"
$Stamp = (Get-Date).toString("yyyy/MM/dd HH:mm:ss")
Function LogWrite {
Param (
[System.Diagnostics.EventLogEntry[]]$logstring,
[string]$Logfile,
[string]$Stamp
)
$logentry = "$($Stamp):$($logstring | fl | out-string)"
Add-Content $Logfile -value $logentry -Force
$logentry
}
$OutlookHangDetailed = Get-EventLog -Log "Application" -Source "Application Hang" -Message "*OUTLOOK.EXE*" -After (Get-Date).AddHours(-12) -ErrorAction SilentlyContinue
LogWrite $OutlookHangDetailed $Logfile $Stamp
Get-EventLog -Log "Application" -Source "Application Hang" -Message "*OUTLOOK.EXE*" -After (Get-Date).AddHours(-12) -ErrorAction SilentlyContinue >> "..\Logs\$(gc env:computername)_Outlook.log"
This will work as expected
Maybe like this:
Function LogWrite
{
param (
$logstring
)
$Stamp | Out-File -Encoding UTF8 -FilePath $Logfile -Append -Force
($logstring | Format-List) | Out-File -Encoding UTF8 -FilePath $Logfile -Width 1024 -Append -Force
}
And call your function with:
LogWrite $OutlookHangDetailed

Powershell script design write message body to log

I'm trying to parse through my Outlook inbox and match certain messages and then, for each of those matches, write the email message body to my Application log. My code so far is below but I'm finding that the script is writing the same message for each match. Meaning, the last message body that the script stores, gets written X number of times for each of the matches that the filter catches.
Add-type -assembly "Microsoft.Office.Interop.Outlook" | out-null
$olFolders = "Microsoft.Office.Interop.Outlook.olDefaultFolders" -as [type]
$outlook = new-object -comobject outlook.application
$namespace = $outlook.GetNameSpace("MAPI")
$inbox = $namespace.getDefaultFolder($olFolders::olFolderInBox)
$filter = (%{$inbox.items | Where {$_.SenderName -match ‘TestUser’ -and $_.UnRead -eq $true}})
$filter.count
foreach ($msg in $filter)
{
$MsgBody = $filter | select-object Body | format-table -HideTableHeaders -Wrap | Out-String
}
for ($i = $filter.count; $i -gt 0 ; $i --) {
Write-eventlog -logname Application -source "TestAlerts" -eventID 100 -entrytype Information -message "$MsgBody"
#$($msg)[$i].UnRead -eq $false - this still isn't working either.
}
Try this:
for ($i = $filter.count; $i -gt 0 ; $i --) {
$msg = $filter[$i]
$MsgBody = $msg | select-object Body | format-table -HideTableHeaders -Wrap | Out-String
Write-eventlog -logname Application -source "TestAlerts" -eventID 100 -entrytype Information -message "$MsgBody"
}

During Foreach read another foreach in powershell

Hi all powershell gurus out there.
I have a foreach which opens a URL from URLListl.txt and doing a Measure-command on them. The result from Measure-command writes to event-log.
In another text file i have country list, like:
USA
Canada
Brazil
and so on....
I want in write eventlogs Message to read from this Text file and write it with the Measure-command result in Message part of the eventlog.
The below is my script which works fine but it creates two entries for each URL.
{
$URLListFile = "C:\yourname\URLList.txt"
$URLList = Get-Content $URLListFile -ErrorAction SilentlyContinue
Foreach ($Uri in $URLList)
{
$Time = Measure-Command {
C:\yourname\MainScript.ps1}
$Time.TotalSeconds
$countrycode = (Get-Content c:\yourname\URLListcountry.txt)
foreach ($SiteCode in $CountryCode)
{
$LogFileExist = Get-EventLog -list | Where-Object { $_.LogDisplayName -eq "Scriptcheck" }
if (! $LogFileExist)
{
New-EventLog -LogName "Scriptcheck" -Source "Scripts"
}
if ($Time.Totalseconds -lt 25)
{
Write-EventLog -LogName "Scriptcheck" -Source "Scripts" -EntryType information -EventId 100 -Message " $SiteCode `nTotal Time: $Time"
}
elseif ($Time.Totalseconds -gt 25)
{
Write-EventLog -LogName "Scriptcheck" -Source "Scripts" -EntryType warning -EventId 101 -Message " $SiteCode `nTotal Time: $Time"
}
}
}
}
if (Get-Process -name iexplore -ErrorAction SilentlyContinue)
{
Stop-Process -Name iexplore
}
Measure-Site

Attempting to Write an Event Log on Success if on error write another one saying that it had failed

Import-Module ActiveDirectory
$Content = Get-Content C:\SMS\sms.txt -TotalCount 1
ForEach ($Payroll in ($Content )) {
Get-ADUser -Identity "$Payroll" -Properties LockedOut | Select-Object LockedOut
If ($true) {$true -ne $false}
Unlock-ADAccount $Payroll
If ($true) {$true -ne $false}
Write-EventLog -LogName "ADUnlock" -Source ADUnlock -EntryType Information -Message "AD account Successfully unlocked $Payroll" -Category 1 -EventId "12"
If ($false) {$false -ne $true}
Write-EventLog -LogName "ADUnlock" -Source ADUnlock -EntryType Information -Message "AD account Attempted to unlock but failed $Payroll" -Category 1 -EventId "12"
}
I am attempting to Write to the event log on success and error using the $true and the $false booleans but it is writing the two event logs despite the success or error, I have tried different variations of the code by using $LASTEXITCODE but then realized that it is for Win32 applications not for PowerShell Command lets.
I'm not entirely sure what you're doing with those if statements but I think you might want something like this:
Import-Module ActiveDirectory
$Content = Get-Content C:\SMS\sms.txt -TotalCount 1
ForEach ($Payroll in ($Content )) {
$res = Get-ADUser -Identity "$Payroll" -Properties LockedOut | Select-Object LockedOut
If (!res) {continue}
Unlock-ADAccount $Payroll
if ($?) {
Write-EventLog -LogName "ADUnlock" -Source ADUnlock -EntryType Information -Message "AD account Successfully unlocked $Payroll" -Category 1 -EventId 12
}
else {
Write-EventLog -LogName "ADUnlock" -Source ADUnlock -EntryType Information -Message "AD account Attempted to unlock but failed $Payroll" -Category 1 -EventId 12
}
}
Thing is, I'm not sure what the type of LockedOut is. I'm assuming a Boolean here.