Public/05_AD_User_Health/Get-VBInactiveComputers.ps1
|
# ============================================================ # FUNCTION : Get-VBInactiveComputers # VERSION : 1.0.2 # CHANGED : 10-04-2026 -- Initial VB-compliant release # AUTHOR : Vibhu Bhatnagar # PURPOSE : Get Active Directory computers inactive for 90+ days # ENCODING : UTF-8 with BOM # ============================================================ <# .SYNOPSIS Get Active Directory computers inactive for 90 days or more. .DESCRIPTION Queries Active Directory for enabled computers whose lastLogonTimestamp is older than 90 days. Returns computer details including DNS hostname, last logon date, and resolved IP address (if available). .PARAMETER ComputerName Domain Controller to query. Defaults to local machine. Accepts pipeline input. .PARAMETER Credential Alternate credentials for the AD query. .EXAMPLE Get-VBInactiveComputers .EXAMPLE Get-VBInactiveComputers -ComputerName DC01 .EXAMPLE 'DC01' | Get-VBInactiveComputers -Credential (Get-Credential) .OUTPUTS [PSCustomObject]: ComputerName, Name, DNSHostName, LastLogonDate, IPAddress, Status, CollectionTime .NOTES Version : 1.0.2 Author : Vibhu Bhatnagar Modified : 10-04-2026 Category : AD User Health #> function Get-VBInactiveComputers { [CmdletBinding()] param( [Parameter(ValueFromPipeline = $true, ValueFromPipelineByPropertyName = $true)] [Alias('Name', 'Server', 'Host')] [string[]]$ComputerName = $env:COMPUTERNAME, [PSCredential]$Credential ) begin { Import-Module ActiveDirectory -ErrorAction Stop } process { foreach ($computer in $ComputerName) { try { # Step 1 -- Define the inactivity threshold (90 days ago) $thresholdDate = (Get-Date).AddDays(-90) # Step 2 -- Build AD query parameters $AdParams = @{ Filter = "enabled -eq `$true -and lastLogonTimestamp -lt `$($thresholdDate.FileTime)" Properties = 'lastLogonTimestamp', 'DNSHostName' } if ($computer -ne $env:COMPUTERNAME) { $AdParams['Server'] = $computer } if ($Credential) { $AdParams['Credential'] = $Credential } # Step 3 -- Get inactive computers $inactiveComputers = Get-ADComputer @AdParams # Step 4 -- Emit results foreach ($comp in $inactiveComputers) { $lastLogonDate = if ($comp.lastLogonTimestamp) { [DateTime]::FromFileTime($comp.lastLogonTimestamp) } else { $null } # Step 5 -- Resolve IP address if DNS hostname exists $ipAddress = 'Unresolved' if ($comp.DNSHostName) { try { $dnsRecord = Resolve-DnsName -Name $comp.DNSHostName -ErrorAction Stop | Where-Object { $_.Type -eq 'A' } if ($dnsRecord) { $ipAddress = $dnsRecord[0].IPAddress } } catch { $ipAddress = 'Unresolved' } } else { $ipAddress = 'No DNSHostName' } [PSCustomObject]@{ ComputerName = $computer Name = $comp.Name DNSHostName = $comp.DNSHostName LastLogonDate = $lastLogonDate IPAddress = $ipAddress Status = 'Success' CollectionTime = (Get-Date).ToString('dd-MM-yyyy HH:mm:ss') } } } catch { [PSCustomObject]@{ ComputerName = $computer Name = $null DNSHostName = $null LastLogonDate = $null IPAddress = $null Error = $_.Exception.Message Status = 'Failed' CollectionTime = (Get-Date).ToString('dd-MM-yyyy HH:mm:ss') } } } } } |