Get the most accurate last logon date for a user

Quick question. If you were to automate user administration and wanted to create a script which searches AD for idle users and disable them accordingly, what method would you use?

We started out with LastLogonDate, but as it turned out, this attribute is not very reliable as it is only updated on the DC where the user authenticates.
So I searched the web for another solution and found that there is another attribute called LastLogon (with some kind of hash or numeric value) which is the most accurate if you know how to convert it to a date.

So I changed the script to use that “conversion” ,@{Name=“lastLogon”;Expression={[datetime]::FromFileTime($_.‘lastLogon’)}} which returns 100% accurate if I for instance run it against my own user.

After creating the report and making some sample comtrol, I found that many LastLogons for many users are not accurate at all (in my report).

Using LastLogon with the expression:
Get-ADUser -filter * -Searchbase $_ -Properties Name,SamAccountName,LastLogon,DistinguishedName |
Select-Object Name,SamAccountName,@{Name=“lastLogon”;Expression={[datetime]::FromFileTime($_.‘lastLogon’)}},DistinguishedName

Name SamAccountName lastLogon
XXXXXXXXXXXX YYYYYY 30-08-2021 10:56:26

From console using:
get-aduser -Identity XXXX -Properties LastLogonDate | Select-Object Name,LastLogonDate
Name LastLogonDate


XXXXXXXXXXX 26-11-2021 12:41:53

On the AD object itself not even the LastLogon and the LastLogon timestamp are the same.
image

Any idea what is wrong?
What is the most reliable method to go with? I won’t risk disabling users based on this.

With a little research you will learn that the “LastLogonTimestamp” will be replicated between all DCs but that might take some time. If I remember right the replication starts after 14 days by default. The best approach is to query all DCs for the attribute “LastLogon” and use the most current one.

Hey Olaf.

I find that in regards to LastLogonDate, and swithed to the LastLogon and thought that I was home safe, but apparantly not :slight_smile:

Thank you for the link to the blog, I will try and build something from that.

I wonder how many businesses who rely on LastLogonDate because the web is filled with basic examples and oneliners using this and if these business (that might have only one DC even though that doesn’t make much sense) rely on scripts developed that way, I guess they are up for a rude awakening when some users or computers are automatically disabled based on a script using only LastLogonDate?!

Thank you again for pointing me in the right direction.

Cheers!

@Thomasso
Hello Thomasso,
Our subdomain has 22 GCDC in different countries. so we can’t simply use the LastLogonDate to count the users who have not logged in for long time, we use the LastLogontimestamp.
Usually we count the users who haven’t logged in for more than six months. so we can accept 14days errors.

I published a couple of functions to help getting the most accurate lastlogon not too long ago.

https://www.reddit.com/r/PowerShell/comments/mfvgwn/getlastlogon_get_accurate_last_logon_time_for_user/

I am not trying to sound rude, however any IT person who has AD experience, especially those “responsible” for disabling/deleting objects, should absolutely already know about this “problem.” It is discussed and documented all over the web. Furthermore, if anyone takes any script or one liner from the internet and runs it in production, without knowing exactly what it does or doesn’t do, is destined for headaches.

As Chen said, you can shoot for a timeframe that accounts for an up to 14 day discrepancy. This is another viable solution.

Hopefully one or both of these will help.

1 Like

Reading the TechNet article above I gather I would not be crazy in saying that the LastLogonDate is good enough to determine who I can disable going by the year and it is not necessary to get all fancy with the query.

A quick question to the team here, does this have the same issues?

Search-AdAccount -AccountInactive -UsersOnly -TimeSpan "$($daysInactive):00:00:00"

Thanks in advance. I use this to find users that have not logged in for a specific period defined in $daysInactive

I realize this thread is a bit old and the question/issue is well documented in terms of the last logon AD attributes. However, as long as there is some new activity, thought I would throw out another approach as food for thought.

Password last change dates.

For example, if your password policy is to change it every 90 days and “today’s date” is 75 days since the last password change, who cares if they are logging in regularly or not. But if "today’s date is 105 since last password change… disabling is probably a good idea.

If an AD account is set to change password at next logon, that does wipe out the password last change date, but there are still ways to calculate how long an account has been in that state. I would have to check my notes at work if you are interested to refresh myself how I calculate that + x days = no one is working with that account, and then disable it.

A key reason I stopped trying to use last logon dates is I was finding AD accounts that were used daily to authenticate to something non MS based, and because the end user wasn’t doing so from Windows their AD accounts were coming up false positive for not being used… ever. If I had relied on last logon, I would have created a some very vocal and unhappy users.

Current guidance is that regular, mandatory password changes should not be enforced on non-priviliged accounts. So in a lot organisations the date the password was last changed could be a long time ago.

I suspect the number of organizations that have switched to up-to-date password guidelines is significantly smaller than those that have.

Speaking for myself, I have known for more than a decade that regular password changes do not actually enhance security. BUT regularly expiring passwords were pounded into people’s heads for years as the best practice. It was how you protected your network. Switching gears will not be easy or quick for many, many companies.

It doesn’t matter how long NIST has been saying otherwise or how confident Microsoft is in the new practices, at each company someone has to be in the hot seat for making the change and prepared to defend that change if they are ever breached. It is kind of like that old saying, no ever got fired for buying IBM. No one will ever get fired for having regularly changed passwords, even if it truly isn’t a best practice. Times are changing, MFA is helping. As are old farts retiring. But I seriously doubt we are at a tipping point yet where we can confidently say “most companies” are not doing regular changing of passwords.

If “you” work in a company that is up to date, then no, my suggestion likely will not be of any use. But if “you” work for a company that still clings to regular password changes, then it gives you something a bit more solid than last logon, particularly if you are using AD to authenticate to other things than Microsoft Windows that might not register a last logon activity at all.

One environment I work in is still using expiring passwords, another is not so I knew when I posted the suggestion would not help everyone.