Windows Server 2008 R2

I'm trying to use PowerShell to get me a list of users who have logged into Remote Desktop Services (formerly known as Terminal Services) during the past day. With little understanding and much copy and pasting, I have this little script:

$a = (Get-Date).AddDays(-1)
Get-EventLog -LogName Security -after $a | Where-Object {($_.EventID -eq '4624') -and  $_.EntryType -eq 'SuccessAudit') -and ($_.Message | Select-String "Logon Type:\t\t\t10")}

The default output tells me things have happened and when they happened which is a good start. What I'd really like is to also display the User. Darned if I can figure out how to get the User and/or how to display it.

And that's my question: How can I add the username associated with that Event ID 4624 / Logon Type 10 event? Ideally I'd just like to show the login time and user name.

  • Good question +1 – Chadddada Sep 27 '11 at 20:47

First I would suggest using the Get-WinEvent and passing a hash to do as much filtering as possible there (and thus avoid creating lots of objects Where-Object will throw away):

Get-WinEvent -filterHashtable @{LogName='Security'; StartTime=$a; Id=4624; Level=0}

Level 0 is success audit. This can be performed remotely with the -computer parameter. Then filter the results to get the login type:

... | Where-Object { $_.Message -match 'Logon Type:\s+10'}

Using a regex to avoid hardcoding the whitespace.

To extract the user and domain from the message would be a little awkward as there are two "Account Name' values: one for the computer and one for the user. But all the replaceable values inserting into the (localisable) message text are in the event's Properties property, so a little checking to see the indexes with a sample1

... | Select-Object *, @{l='LogonAccount';e={$_.Properties[6].Value + "\" + $_.Properties[5].Value }}

Clearly capturing other details (eg. SID, client IP) follows the same pattern.


Get-WinEvent -filterHashtable @{LogName='Security'; StartTime=$a; Id=4624; Level=0} |
  Where-Object { $_.Properties[8].Value -eq 10} |
  Select-Object *, @{l='LogonAccount';e={$_.Properties[6].Value + "\" + $_.Properties[5].Value }}

1 With a single event in $ev I used:

0..($ev.Properties.Count-1) | Select @{l='Idx';e={$_}},@{l='Property';e={$ev.Properties[$_].Value}} |
  ft -auto

to give (with a little censorship, and noting a better way to get the logon type at index #8):

Idx Property
--- --------
  0 S-1-5-18
  1 *Computer's account*
  2 *Computer's Domain*
  3 999
  4 *User's SID*
  5 *User's user name*
  6 *User's Domain*
  7 151556
  8 10
  9 User32
 10 Negotiate
 11 *Computer's Name*
 12 00000000-0000-0000-0000-000000000000
 13 -
 14 -
 15 0
 16 2964
 17 C:\Windows\System32\winlogon.exe
 18 *Client IP*
 19 15532
  • A minor variation of your "Hence" example works delightfully. Thanks! – Chris_K Sep 22 '11 at 17:24

I'd do it as follows -

$filter = "<QueryList>" + `
               "<Query Id=`"0`" Path=`"Security`">" + `
                    "<Select Path=`"Security`">" + `
                        "*[System[(EventID=4624) and " + `
                        "TimeCreated[@SystemTime&gt;='2011-09-21T06:00:00Z' and @SystemTime&lt;'2011-09-22T06:00:00Z']]] and " + `
                        "*[EventData[Data[@Name=`'LogonType`']=10]]" + `
                    "</Select>" + `
                    "<Suppress Path=`"Security`">" + `
                        "*[EventData[Data[@Name=`'LogonGuid`']=`'{00000000-0000-0000-0000-000000000000}`']]" + `
                    "</Suppress>" + `
               "</Query>" + `

Get-WinEvent -FilterXML $filter | 
%{ [xml]$xml = $_.ToXml()
   $xml.getElementsByTagName("Data") | where{$_.name -eq "TargetUserName"} | 
   select '#text'

EDIT: This now returns the names of the individuals. You can play around with what exactly you'd like to extract from that XML document.

Note: You'll need to putz around with the TimeCreated values (probably generate them on the fly). I included these so you could see the format they required.

Get-WinEvent will be much faster than Get-EventLog since the filtering will be done server-side instead of in the pipeline. You can also get a bit more specific on your queries by using the FilterXML parameter. The usernames associated with the logon events are in the Message property of the returned EventLogRecord.

  • A thing of beauty! However, it gives me the exact same output as what I currently have :-( How do I get the username in the output? – Chris_K Sep 22 '11 at 15:01
  • Updated to extract just the names. I don't know exactly what you want to see on the output, so I'll let you sort that bit out. If you need help, ask. – pk. Sep 22 '11 at 15:39

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

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