<# .SYNOPSIS This script will determine activesync device partnerships that are older than x number of days and remove them from organization accordingly. .DESCRIPTION MANDATORY REQUIREMENT: This script can run with Exchange Management Shell or in Shell window with Exchange module loaded. MANDATORY PARAMETERS: NumberofDays,HTMLFile This script will find all activesync device partnerships for particular mailbox or set of mailboxes using csv/Organizational Unit/Database/Server or all mailboxes that are older than x number of days. It can then either generate report only using -ReportOnly parameter OR remove them from organization along with report accordingly. As it does either of those, it will write the data into a HTML file which can then be sent via email to intended recipients of the report. The report contains following details 1. Display Name or Identity of mailbox 2. Email address for user or mailbox 3. Device ID 4. Device Model 5. Status of Device 6. Device Access State 7. First Synchronization Time 8. Last successful Synchronization Time IMPORTANT NOTE: 1. If no parameter is provided beside -NumberofDays and -HTMLFIle, the script will run for all mailboxes/device relationships in environment and remove them accordingly. 2. If you use single mailbox/csvfile/database/mailbox server as input, the script will NOT determine orphan device partnerships i.e. one which do not have any mailbox associated with them. Use OrganizationalUnit/All device method for same. .PARAMETER NumberofDays Provide cound/number of days to determine device partnerships which are older than said cound/number. .PARAMETER HTMLFile Provides location of output HTML file to store results. .PARAMETER ReportOnly Use this switch if you will like script to simply generate HTML report of old devices but NOT remove them. .PARAMETER MailboxName Name or identity of mailbox for which script should run. .PARAMETER MailboxServer Name of te Mailbox server for which script should run. .PARAMETER OrganizationalUnit Organizational Unit for which script should run. .PARAMETER DatabaseName Database for whcih script should run. .PARAMETER FileName Provides location of csv file to impoart data from .PARAMETER SendMail Use this switch if you will like to send output file in email. Make sure to use SMTPServer,Subject,From and To parameters with this switch .PARAMETER SMTPServer IP Address or FQDN of the mail relay server. .PARAMETER Subject Subject line for email to be generated. .PARAMETER From From or ReplyTo address for the email to be generated. .PARAMETER To Recipients who should receive this report. .PARAMETER ScheduleAs Attempt to schedule the command just executed for 10PM nightly. Specify the username here, schtasks (under the hood) will ask for a password later. .EXAMPLE Run script against all devices in environment, storing report in C:\Test.htm and remove partnerships older than 30 days .\Remove-OldActiveSyncDevicePartnerhip.ps1 -HTMLFile C:\Test.htm -NumberofDays 30 .EXAMPLE Run script against single mailbox named TestMailbox to find devices older than 30 days and generrate report only which will be stored in C:\Test.htm .\Remove-OldActiveSyncDevicePartnerhip.ps1 -MailboxName TestMailbox -ReportOnly:$true -HTMLFile C:\Test.htm -NumberofDays 30 .EXAMPLE Run script against single mailbox named TestMailbox to find devices older than 30 days and generrate report only which will be stored in C:\Test.htm & then emailed to administrator@contoso.com via email using relay server 10.0.0.1 .\Remove-OldActiveSyncDevicePartnerhip.ps1 -MailboxName TestMailbox -ReportOnly:$true -HTMLFile C:\Test.htm -NumberofDays 30 -SendMail:$true -SMTPServer 10.0.0.1 -Subject "Active Sync Report" -To Administrator@contoso.com -From Reporting@contoso.com .EXAMPLE Run script against single mailbox named TestMailbox to find device older than 30 days and remove them accordingly. Report saved in C:\Test.htm. .\Remove-OldActiveSyncDevicePartnerhip.ps1 -MailboxName TestMailbox -HTMLFile C:\Test.htm -NumberofDays 30 #> param( [parameter(Position=1,Mandatory=$true,ValueFromPipeline=$false,HelpMessage="Find device partnerships older than Number of Days")][int]$NumberofDays, [parameter(Position=2,Mandatory=$true,ValueFromPipeline=$false,HelpMessage="Path or Location for HTML file to store")][string]$HTMLFile, [parameter(Position=3,Mandatory=$false,ValueFromPipeline=$false,HelpMessage="Use this switch if you will like to run script in report only mode")][boolean]$ReportOnly, [parameter(Position=4,Mandatory=$false,ValueFromPipeline=$true,HelpMessage="Provide name or Identity of mailbox")][string]$MailboxName, [parameter(Position=5,Mandatory=$false,ValueFromPipeline=$true,HelpMessage="Provide location of csv file")][string]$FileName, [parameter(Position=6,Mandatory=$false,ValueFromPipeline=$true,HelpMessage="Provide Name of mailbox datbase")][string]$DatabaseName, [parameter(Position=7,Mandatory=$false,ValueFromPipeline=$true,HelpMessage="Provide name of the mailbox server")][string]$MailboxServer, [parameter(Position=8,Mandatory=$false,ValueFromPipeline=$true,HelpMessage="Provide name of Organizational Unit")][string]$OrganizationalUnit, [parameter(Position=9,Mandatory=$false,ValueFromPipeline=$false,HelpMessage="Use this switch if you will like to send email")][boolean]$SendMail, [parameter(Position=10,Mandatory=$false,ValueFromPipeline=$false,HelpMessage="Use this switch if you will like to send email")][string]$SMTPServer, [parameter(Position=11,Mandatory=$false,ValueFromPipeline=$false,HelpMessage="Use this switch if you will like to send email")][string]$Subject, [parameter(Position=12,Mandatory=$false,ValueFromPipeline=$false,HelpMessage="Use this switch if you will like to send email")]$From, [parameter(Position=13,Mandatory=$false,ValueFromPipeline=$false,HelpMessage="Use this switch if you will like to send email")]$To, [parameter(Position=14,Mandatory=$false,ValueFromPipeline=$false,HelpMessage="Use this switch if you will like to send email")][String]$Scheduleas ) Add-PSSnapin Microsoft.Exchange.Management.PowerShell.E2010 Set-Adserversettings -ViewEntireForest $true Set-ExecutionPolicy -ExecutionPolicy RemoteSigned Clear-Content $HTMLFile Function writeHtmlHeader { param($HTMLFile) $date = ( Get-Date ).ToString('yyyy/MM/dd - hh:mm') Add-Content $HTMLFile "" Add-Content $HTMLFile "" Add-Content $HTMLFile "" Add-Content $HTMLFile 'Old Active Sync Device Report' Add-Content $HTMLFile '" Add-Content $HTMLFile "" Add-Content $HTMLFile "" Add-Content $HTMLFile "" Add-Content $HTMLFile "" Add-Content $HTMLFile "" Add-Content $HTMLFile "" Add-Content $HTMLFile "
" Add-Content $HTMLFile "Old Active Sync Device Report - $date" Add-Content $HTMLFile "
" } # Function to write the HTML Header to the file Function writeTableHeader { param($HTMLFile) Add-Content $HTMLFile "" Add-Content $HTMLFile "" Add-Content $HTMLFile "" Add-Content $HTMLFile "" Add-Content $HTMLFile "" Add-Content $HTMLFile "" Add-Content $HTMLFile "" Add-Content $HTMLFile "" Add-Content $HTMLFile "" Add-Content $HTMLFile "" Add-Content $HTMLFile "" } Function writeHtmlFooter { param($HTMLFile) Add-Content $HTMLFile "
Display NameEmail AddressDevice IDDevice ModelStatusDevice Access StateFirst Sync TimeLast Success Sync
" Add-Content $HTMLFile "" Add-Content $HTMLFile "" } Function Remove-OldActiveSyncDevicePartnerhip ($DeviceInfo,$ReportOnly) { $currentdate = Get-Date foreach($device in $DeviceInfo) { $stats = Get-ActiveSyncDeviceStatistics $device $isdeviceold = ($currentDate - $stats.LastSuccessSync).Days if ($isdeviceold -ge $NumberofDays -or $stats.LastSuccessSync -eq $null -and $stats.FirstSyncTime -ne $null) { $mbx = Get-Mailbox $device.UserDisplayName if ($mbx -eq $null) { $username = $device.UserDisplayName $emailadd = $null} Else { $username = $mbx.DisplayName $emailadd = $mbx.WindowsEmailAddress} $devicet = $stats.DeviceID $devicem = $stats.DeviceModel $devices = $stats.Status $deviceas = $stats.DeviceAccessState $firstsync = $stats.FirstSyncTime $lastsync = $stats.LastSuccessSync writedata $username $emailadd $devicet $devicem $devices $deviceas $firstsync $lastsync If (!($ReportOnly)) { Write-Host "Removing device partnerhip from environment" Remove-ActiveSyncDevice $device -confirm:$false } } } } Function WriteData { param($username,$emailadd,$devicet,$devicem,$devices,$deviceas,$firstsync,$lastsync) $tableEntry = "$username$emailadd$devicet$devicem$devices$deviceas$firstsync$lastsync" Add-Content $HTMLFile $tableEntry Write-Host $tableEntry } Function sendEmail { param($from,$to,$subject,$smtphost,$htmlFileName) $body = Get-Content $htmlFileName $smtp= New-Object System.Net.Mail.SmtpClient $smtphost $msg = New-Object System.Net.Mail.MailMessage $from, $to, $subject, $body $msg.isBodyhtml = $true $smtp.send($msg) } if ($MailboxName) { $DeviceInfo = Get-ActiveSyncDevice -Mailbox $MailboxName } if ($filename) { $DeviceInfo = Import-Csv $filename| ForEach-Object {Get-ActiveSyncDevice -Mailbox $_.Identity} } if ($DatabaseName){ $Mailboxes = Get-Mailbox -ResultSize Unlimited -Database $DatabaseName $DeviceInfo = foreach($mailbox in $mailboxes) {Get-ActiveSyncDevice -Mailbox $mailbox} } if ($MailboxServer){ $Mailboxes = Get-Mailbox -ResultSize Unlimited -Server $MailboxServer $DeviceInfo = foreach($mailbox in $mailboxes) {Get-ActiveSyncDevice -Mailbox $mailbox} } if ($OrganizationalUnit){ $DeviceInfo = Get-ActiveSyncDevice -ResultSize Unlimited -OrganizationalUnit $OrganizationalUnit } if (!($MailboxName) -and !($MailboxServer) -and !($FileName) -and !($DatabaseName) -and !($OrganizationalUnit)) { Write-Host "Runing Script against all devices in environment" $DeviceInfo = Get-ActiveSyncDevice -ResultSize Unlimited } writehtmlheader $HTMLFile writetableheader $HTMLFile Remove-OldActiveSyncDevicePartnerhip $DeviceInfo $ReportOnly -Verbose writehtmlfooter $HTMLFile $date = ( Get-Date ).ToString('yyyy/MM/dd - hh:mm') if ($SendMail){ sendEmail $From $To $Subject $SMTPServer $HTMLFile} if ($ScheduleAs) { $dir=(split-path -parent $myinvocation.mycommand.definition) $params = "-HTMLFile $HTMLFile -NumberofDays $NumberofDays" if ($SendMail) { $params += ' -SendMail:$true' $params +=" -From:$from -To:$to -SMTPServer:$SMTPServer -Subject:$Subject" } $task = "powershell -c \""pushd $dir; $($myinvocation.mycommand.definition) $params\""" Write-Output "Attempting to schedule task as $($ScheduleAs)..." Write-Output "Task to schedule: $($task)" schtasks /Create /RU $ScheduleAs /RP /SC DAILY /ST 22:00 /TN EER /TR $task }