Identifying Bad/Corrupt Calendar Items

I have been seeing more and more issues with bad calendar items causing out of control mailbox database and transaction log growth. What I seen as a good process for attacking these issues is to use the following:

  • Exchange User Monitor (ExMon) which will identify the mailbox that is causing the problem. You will see a single mailbox or just a couple that consumes a huge percentage of resources.
  • Calendar Check (CalCheck) can then be used against the mailboxes to identify calendar items that have been modified way too many times and have become extremely large. It is usually one or more of these items that have become corrupted and are causing this issue.
  • Scot O, one of my favorite bloggers, also has a great blog to help identify issues by viewing the transaction logs and using strings.exe to identify repeating patterns which usually indicate a problem.

Recently, I have been trying to find a more proactive measure to identify these calendar items that tend to break when users just refuse to follow best practices.

I have combined PowerShell and CalCheck to look for bad items. Here is my latest version of the script. Please keep in mind that the formatting of this blog does not always work perfectly for scripts, and many of the lines that appear here are really a single line. You can download the latest version of this script here.

# This script is broken into three steps. In the first step, we identify users that have large calendar folders # In this step, we use get the databases first to try to minimize the memory requirements of processing all mailboxes # as PowerShell fails when you start getting into the tens of thousands of mailboxes.

$Date = Get-Date

Write-Host Start processing script at $Date # I always to keep track of how much time scripts take

$mbdb = Get-MailboxDatabase | Where {$ -ilike ‘*vpc*’} Write-Host $Null | Out-File List.txt foreach ($db in $mbdb){

Write-Host Processing $db

$Mailboxes = Get-Mailbox -database $db

foreach ($i in $Mailboxes){

$CalendarSize = (Get-Mailbox $i | Get-MailboxFolderStatistics -folderscope ‘calendar’).FolderandSubFolderSize

# Write-Host $i – Calendar size is $CalendarSize

$CalSplit = $CalendarSize -split ‘ ‘

$CalSize = $CalSplit[2]

$CalSize = $CalSize -replace “\(|\)|,| bytes”

$CalSize = [int]$CalSize

if ($CalSize -gt 100000000){

Get-Mailbox $i | Select Name,LegacyExchangeDN | FL | Out-File -append list.txt




$Date = Get-Date

Write-Host Completed identification of mailboxes that have large calendar folders at $Date

# In this step, we simply run CalCheck against all of the mailboxes that have calendar folders over 100MB as found in the first step. This requires version 2.0 or higher which supports the -l and –a arguments.

# It is vital that the account running this script have proper access to the individual mailboxes to scan them.

# The output will be a large number of log and csv files. I use the csv files for simpler processing.

# Note: Currently, CalCheck is not able to process more than around 100 mailboxes at a time. YMMV. You should also note that I pause the PowerShell script so that CalCheck can run.

Start-Process -FilePath c:\calcheck\calcheck.exe -ArgumentList “-a -l list.txt”

Write-Host “Once CalCheck has finished running, press any key to continue …”

$x = $host.UI.RawUI.ReadKey(“NoEcho,IncludeKeyDown”)

$Date = Get-Date

Write-Host Completed running CalCheck against mailboxes that have large calendar folders at $Date

# In this step, we create an output file for our results.

Write-Host $Null | Out-File Results.csv

$Header = “Subject,Organizer,Email,Modifications,Size”

$Header | Out-File Results.csv

$UserFiles = Dir C:\calcheck\calcheck_*.csv

foreach ($File in $UserFiles){

Write-Host ” “

Write-Host PROCESSING $file

Write-Host ” “

Copy $File CalItems.csv

(Get-Content calitems.csv) | where {$_ -notmatch ‘Processing*’} | Set-Content calitems.csv

$CalItems = Import-CSV calitems.csv

foreach ($item in $CalItems){

$Subject = $Item.Subject

$Size = $Item.Size

#This section is used to identify the organizer of the meeting and to put their info into first name, middle initial, last name format and also the same for their email address which I can use in other scripts to send automated email if I want. Your email address format may differ.

$Organizer = $Item.”Organizer Name”

$Organizer = $Organizer -split “_ “

$OrganizerFN = $Organizer[1]

$OrganizerLN = $Organizer[0]

$OrganizerFN1 = $OrganizerFN -split ” “

$OrganizerFN2 = $OrganizerFN1[0]

$OrganizerMI = $OrganizerFN1[1]

$Organizer = $OrganizerFN + ” ” + $OrganizerLN

if ($OrganizerMI){

$Email = $OrganizerFN2 + “.” + $OrganizerMI + “.” + $OrganizerLN + “”


if (!$OrganizerMI){

$Email = $OrganizerFN2 + “.” + $OrganizerLN + “”


if ($Modified = !$Null){

[int]$Modified = $Item.”Modified Instances”

if($Modified -ge “20”){

$Result = “$Subject,$Organizer,$Email,$Modified,$Size”

Write-Host $Result

$Result | Out-File -append Results.csv




Del CalItems.csv


$Date = Get-Date

Write-Host Completed script at $Date

What you will end up with is a csv file named results.csv that can then be loaded into Excel and sorted as needed to identify the items that may be causing the most pain.

This entry was posted in Exchange. Bookmark the permalink.

2 Responses to Identifying Bad/Corrupt Calendar Items

  1. Pingback: Identifying Bad/Corrupt Calendar Items | Build Your Business on a Solid Infrastructure « JC’s Blog-O-Gibberish

  2. Pingback: Lync MVP Article Roundup: October 2012 - NextHop - Site Home - TechNet Blogs

Leave a Reply

Fill in your details below or click an icon to log in: Logo

You are commenting using your account. Log Out /  Change )

Google photo

You are commenting using your Google account. Log Out /  Change )

Twitter picture

You are commenting using your Twitter account. Log Out /  Change )

Facebook photo

You are commenting using your Facebook account. Log Out /  Change )

Connecting to %s