EWS Script: Recover Email Items out of the Purges and Deletions based on a timeframe for when the email items were deleted.

Scenario:  You want to recover email items that were deleted from the mailbox and were moved into the backend Purges and Deletions Recoverable folders. You want to recover only items that were deleted  between a timeframe. You also want to place these deleted items into a single folder available in the mailbox.

Scriptlets:

Declare your Variables:

#Variables
    $cred = Get-credential  #credentials will fullaccess to access the mailbox
    $mailboxname = "Jane@Domain.Com"  #The Mailbox you wish to perform the query and restore on
    $EWS_DLL = "C:Program FilesMicrosoftExchange ServerV15BinMicrosoft.Exchange.WebServices.dll"
    $EWS_URL = "https://mail.domain.com/ews/exchange.asmx"
    [datetime]$StartDate  = "6/5/2017" #Used for the LastModifiedTime
    [datetime]$EndDate = "6/19/2017" #Used for the LastModifiedTime
    $RestoreFolder = "Recovered Items"  #The folder thats is already created in the mailbox to restore to

Configure the EWS connection properties

#Configure connection to EWS
    Import-Module -Name $EWS_DLL
    $service = new-object Microsoft.Exchange.WebServices.Data.ExchangeService([Microsoft.Exchange.WebServices.Data.Exchangeversion]::exchange2013)
    $service.Url = new-object System.Uri($EWS_URL)
    $service.UseDefaultCredentials = $false
    $service.Credentials = $cred.GetNetworkCredential()

Attach to the following folders:  Purges, Deletions, and Recoverable Items (created in mailbox to restore content to)

#Attach to Purges
    $folderidpurges = new-object Microsoft.Exchange.WebServices.Data.FolderId([Microsoft.Exchange.WebServices.Data.WellKnownFolderName]::RecoverableItemspurges,$MailboxName)
    $purgesFolder = [Microsoft.Exchange.WebServices.Data.Folder]::Bind($service,$folderidpurges)
#Attach to Deletions
    $folderidDeletions = new-object Microsoft.Exchange.WebServices.Data.FolderId([Microsoft.Exchange.WebServices.Data.WellKnownFolderName]::RecoverableItemsDeletions,$MailboxName)
    $DeletionsFolder = [Microsoft.Exchange.WebServices.Data.Folder]::Bind($service,$folderidDeletions)
#Attach to Recovered Items Folder
    $PathToSearch = $restorefolder  
    $folderid = new-object Microsoft.Exchange.WebServices.Data.FolderId([Microsoft.Exchange.WebServices.Data.WellKnownFolderName]::MsgFolderRoot,$mailboxname)   
    $tfTargetFolder = [Microsoft.Exchange.WebServices.Data.Folder]::Bind($service,$folderid)  
    $fldArray = $PathToSearch.Split("") 
    for ($lint = 1; $lint -lt $fldArray.Length; $lint++) { 
        $fldArray[$lint] 
        #Perform search based on the displayname of each folder level 
        $fvFolderView = new-object Microsoft.Exchange.WebServices.Data.FolderView(1) 
        $SfSearchFilter = new-object Microsoft.Exchange.WebServices.Data.SearchFilter+IsEqualTo([Microsoft.Exchange.WebServices.Data.FolderSchema]::DisplayName,$fldArray[$lint]) 
        $findFolderResults = $service.FindFolders($tfTargetFolder.Id,$SfSearchFilter,$fvFolderView) 
        if ($findFolderResults.TotalCount -gt 0){ 
            foreach($folder in $findFolderResults.Folders){ 
                $tfTargetFolder = $folder                
            } 
        } 
        else{ 
            "Error Folder Not Found"  
            $tfTargetFolder = $null  
            break  
        }     

Create your Search Filter and perform the search

#Create and Apply an Search Filter
    $sfCollection = new-object Microsoft.Exchange.WebServices.Data.SearchFilter+SearchFilterCollection([Microsoft.Exchange.WebServices.Data.LogicalOperator]::And);
    $Sfgt = new-object Microsoft.Exchange.WebServices.Data.SearchFilter+IsGreaterThan([Microsoft.Exchange.WebServices.Data.ItemSchema]::LastModifiedTime, $StartDate)
    $Sflt = new-object Microsoft.Exchange.WebServices.Data.SearchFilter+IsLessThan([Microsoft.Exchange.WebServices.Data.ItemSchema]::LastModifiedTime, $EndDate)
    $sfCollection.add($Sfgt)
    $sfCollection.add($Sflt)
    $view = new-object Microsoft.Exchange.WebServices.Data.ItemView(2000000)
    $miMailItems = $DeletionsFolder.FindItems($sfCollection,$view)

Lastly,  Move your email Items into the Recovery folder

    ###Moves your Email Items
    $MiMailItems | %{
        "Moving: "+ $_.LastModifiedTime +": " + $_.Subject.ToString()
        [VOID]$_.Move($tftargetfolder.id)
    }

 

 

 

 

 

 

 

 

 

Powershell: List all mailbox folder delegate access for a mailbox

Scenario: You want to determine all mailbox folder delegate access for a mailbox. You wish to not include the anonymous and default permissions.

Script:

$mbx = "steve"
$permissions = @()
$Folders = Get-MailboxFolderStatistics $mbx | % {$_.folderpath} | % {$_.replace(“/”,””)}
$list = ForEach ($F in $Folders)
   {
    $FolderKey = $mbx + ":" + $F
    $Permissions += Get-MailboxFolderPermission -identity $FolderKey -ErrorAction SilentlyContinue | Where-Object {$_.User -notlike “Default” -and $_.User -notlike “Anonymous” -and $_.AccessRights -notlike “None”}
   }
$permissions

Find Exchange Recipients that do not have a specific EmailDomain as an Email Alias/Proxy Address

Scenario:  You want to query all Exchange recipients that do not have a email alias with the @XYZ.com domain.

Script: Use this command to export the recipients to a .csv.

get-recipient * -filter {emailaddresses -notlike ‘*@xyz.com’} -ResultSize unlimited | Export-csv C:tempxyz.csv

Detect Backpressure on your Exchange Servers

Scenario:  Customers are complaining about connectivity issues and degraded performance with their mail clients. You suspect its due to backpressure on a server, but you want to dig a little deeper.

Troubleshooting:

1.Check for Windows Event 2002 “The number of outstanding requests for guard TargetBackend has exceeded the max limit 150. Current request will be rejected” by running this PowerShell command:

Get-WinEvent -computername <remote computer> -FilterHashtable @{logname=’application’;id=2002}

 

2. Check the number of mounted copies of mounted Exchange Databases on each server and manually spread them out:

(get-mailboxdatabasecopystatus -server <remote computer> | Where status -like Mounted).count

3. Check for user counts and compare against each server by running this Powershell Command:

(Get-WmiObject Win32_LoggedOnUser -ComputerName <remote computer>| Select Antecedent -Unique).count

Error “A reboot from a previous installation is pending” during Exchange InstallUninstall

Scenario:  When attempting to install/uninstall Exchange, you receive the following error during readiness checks:

“A reboot from a previous installation is pending”

Even after a reboot, it doesn’t clear this error.

Solution:

  1. Clear values out of the PendingFileRenameOperations key located at: HKLMSYSTEMCurrentControlSetControlSessionManagerPendingFileRenameOperations
  2. You may need to clear out the content of this key as well located at: HKLMSystemControlSet001ControlSessionManager

Determine who has a mailbox and remote mailbox via AD Powershell

Scenario:  You have a list of username’s in a .csv file with a column header labeled: name.  You want to quickly determine which usernames have a Mailbox and RemoteMailbox.

Script:

Import-module ActiveDirectory

$Members = Import-csv C:sharecvusers.csv | Select -ExpandProperty Name

$Members = $Members | Sort

$Members_OnPrem = @()
$Members_o365 = @()

$Members  | %{
    "$_"
    $type = Get-ADUser $_ -properties msExchRecipientTypeDetails | Select -ExpandProperty MSexchRecipientTypeDetails
         If ($type -eq "1"){$Members_OnPrem += $_}
         If ($type -eq "2147483648"){$Members_o365 += $_}
}


Performing a Search-Mailbox with complex search criteria

Scenario: Batman is at it again.  He is now under litigation hold for attacking Superman and you want to search in Superman’s mailbox for any message that was received and sent by Batman, or specific terms were in the Subject, Body, or attachments.  You are only interested for messages sent after 1/1/2012.

Script:

Search-Mailbox Superman -SearchDumpster -SearchQuery "(Received:1/1/2012..5/18/2016) AND (To:Batman@DC.com OR From:Batman@DC.com OR CC:Batman@DC.com OR BCC:Batman@DC.com OR 'Batman' OR 'Bruce' OR 'Wayne')" –targetmailbox BobTheLawyer -loglevel full -targetfolder "Search_Batman"

Test-ActiveSyncConnectivity to verify EAS is working properly

Scenario: You want to test whether ActiveSync (EAS) is working properly.  You can use the following script to determine if EAS is failing on any of your Exchange Client Access Servers:

Script:

#Gather Credentials for the Test User into a variable
$1 = get-credential ("DomainEASTestuser")

#Gather Servers into a variable
$Servers = Get-clientaccessserver 

#Define your collection variable
$EAS = @()

#Loop through each server and test
$Servers | %{$EAS += Test-ActiveSyncConnectivity -AllowUnsecureAccess:$true -ClientAccessServer $_ -MailboxCredential $1 -lightmode}

Mail automatically deletes itself as soon as it enters into the Inbox.

Scenario:  A mailbox was recently created and every time mail is sent to this mailbox, it immediately deletes from the Inbox.

You have already verified that there are no mailbox rules, mobile devices, and applications that are causing this behavior.

Solution:  Check the RecipientType of the mailbox that was created by running the following command:

get-recipient iBroke

We had a mailbox that was incorrectly configured as a Room Mailbox and this mailbox needed to be a normal user mailbox. The automatic calendar processing was immediately deleting this message.  We resolved this issue by running:

Set-Mailbox iBroke -Type Regular

 

 

Determine which groups are distribution of all the groups a AD user is a member of

Scenario:  A user is a member of multiple security and distribution groups and you wish to determine which of these groups are distribution.

Script:

$1 = (Get-ADUser STEVE -Properties Memberof).memberof
$2 = $1 | %{Get-DistributionGroup $_}