Finding Expired and Unused AD Accounts

Welcome Forums General PowerShell Q&A Finding Expired and Unused AD Accounts

This topic contains 6 replies, has 3 voices, and was last updated by

 
Participant
3 weeks, 6 days ago.

  • Author
    Posts
  • #125862

    Participant
    Points: 23
    Rank: Member

    I am using the following command to find any expired account or accounts that have not logged in within 45 days. Do you have any suggestions for improving the script? Is there anything I am missing when checking for expired or unused accounts?

    get-aduser -filter * -SearchBase $varOUPath -Properties PasswordExpired,Enabled,LastLogonDate,Created,lastLogonTimestamp,

    AccountExpirationDate |

    Where-Object {($_.PasswordExpired -eq $True) -or ($_.Enabled -eq $False) -or
    (($_.LastLogonDate -lt $varInactiveDate) -and ($_.LastLogonDate -ne $NULL)) -or (($_.created -lt $varInactiveDate) -and ($_.LastLogonDate -eq $NULL)) -or (($_.AccountExpirationDate -le (get-date)) -and ($_.AccountExpirationDate -ne $null))}|

    Select-Object Name,SamAccountname,PasswordExpired,Enabled,Created,Lastlogondate,@{n='LogonTimeStamp(Replicated)'; e={[datetime]::FromFileTime($_.LastlogonTimestamp).ToString('g')}},AccountExpirationDate

  • #125877

    Participant
    Points: 66
    Rank: Member

    So that is going to take a lot longer to run. Check out the filter parameter as your using an * to basically say All vs filtering just on what you want.

     

    $Date = Get-Date

    $45DaysAgo = $Date.AddDays(-45)

    #Grab Users who haven't logged into the system in over 45 days.

    Get-ADUser -Filter {LastLogonDate -lt $45DaysAgo} -Properties LastLogonDate | Select-Object -Property SamAccountName,Lastlogondate

    Find Expired acccounts/disable ones.

    Search-ADAccount -AccountExpired

    Search-ADAccount -AccountDisabled

     

    get-aduser -filter {LastLogonDate -LT $90Daysgo} -SearchBase $varOUPath -Properties PasswordExpired,Enabled,LastLogonDate,Created,lastLogonTimestamp,

  • #125882

    Participant
    Points: 355
    Helping Hand
    Rank: Contributor

    To be clear, you should do all of your filtering (if possible) here:

    Get-ADUser -Filter {(LastLogonDate -lt $45DaysAgo) -and (PasswordExpired -eq $True) -and (Enabled -eq $False)}
    
  • #125883

    Participant
    Points: 23
    Rank: Member

    Thanks for the updates! I will try and add the expression in the filter section of get-aduser.

  • #126035

    Participant
    Points: 23
    Rank: Member

    I am wondering if there is a limitation to how many expressions you can put in the filter? After adding 3 expressions I get a parsing error. I did run the command with everything in the where statement and 3 expressions moved to the filter. (Gained about 12 milliseconds, see below)

    Error:

    get-aduser : Error parsing query: '(PasswordExpired -eq $True) -or (Enabled -eq $False) -or ((LastLogonDate -lt $varInactiveDate) -and (LastLogonDate -like "*")) -or ((AccountExpirationDate -le (get-date)) -and (AccountExpirationDate -like "*"))' Error
    Message: 'syntax error' at position: '160'.
    At line:1 char:1
    + get-aduser -SearchBase $varOUPath -Properties PasswordExpired,Enabled ...
    + ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
    + CategoryInfo : ParserError: (:) [Get-ADUser], ADFilterParsingException
    + FullyQualifiedErrorId : Error parsing query: '(PasswordExpired -eq $True) -or (Enabled -eq $False) -or ((LastLogonDate -lt $varInactiveDate) -and (LastLogonDate -like "*")) -or ((AccountExpirationDate -le (get-date)) -and (AccountExpirationDate -like
    "*"))' Error Message: 'syntax error' at position: '160'.,Microsoft.ActiveDirectory.Management.Commands.GetADUser

    < # with where statements only 24855 User Objects Days : 0 Hours : 0 Minutes : 0 Seconds : 17 Milliseconds : 950 Ticks : 179504590 #>

    < # added 3 expressions to the filter 24855 User Objects Days : 0 Hours : 0 Minutes : 0 Seconds : 5 Milliseconds : 666 Ticks : 56664759 #>

  • #126044

    Participant
    Points: 355
    Helping Hand
    Rank: Contributor

    What exactly are you looking for? If you are doing a comparison on a date, then there should be no need to see if is not null (e.g. -like '*'). The biggest issue is you are looking for people that are already disabled. You can try a filter something like this:

    (Enabled -eq $True) -and #Account still enabled
    (PasswordExpired -eq $True) -or  #Account password expired
    (LastLogonDate -lt (Get-Date).AddDays(-45)) -or #Account Last Logon is beyond 45 days
    (AccountExpirationDate -gt (get-date)) #Account has expired
    

    Rather than trying to jam all of stuff you want into the filter, I would start with the first 2 and try it. Then add the third and try it. Another option is Search-ADAccount:

    Search-ADAccount -AccountDisabled
    Search-ADAccount -AccountExpired
    Search-ADAccount -AccountExpiring
    Search-ADAccount -AccountInactive
    
  • #126083

    Participant
    Points: 23
    Rank: Member

    I still need to do some more testing but seems to have an error after a 4th entry is added.

    The following works but if I add another entry it displays the error listed. I might be doing something wrong but was wondering what the limitations are when using the filter if any?

    (PasswordExpired -eq $True) -or (Enabled -eq $False) -or ((LastLogonDate -lt $varInactiveDate) -and (LastLogonDate -like "*"))

     

You must be logged in to reply to this topic.