Назад | Перейти на главную страницу

Выявление поврежденных почтовых ящиков Exchange 2013

Мы готовимся избавиться от локального Exchange и переходим с внешнего хостинг-провайдера на Office 365. Мы используем полностью исправленную версию Exchange 2013 поверх Server 2012, которая также полностью исправлена.

Во время миграции тестовых почтовых ящиков мы обнаружили, что многие почтовые ящики в нескольких базах данных повреждены. Более подробную информацию о причине можно найти ВОТ. По сути: SAN, в которой хранится наша виртуальная машина Exchange, переподписана и обычно имеет ожидание ввода-вывода более 5 секунд, а устойчивая скорость чтения редко превышает 500 Кбит / с.

Низких скоростей было бы достаточно, чтобы вызвать значительную потерю времени во время миграции, но когда обнаруживаются поврежденные почтовые ящики, миграция 1 ГБ данных переходит из 2-3 часов в 10-20 часов. Каждый из почтовых ящиков, у которых есть проблемы (которые я обнаружил до сих пор), выдает сообщения, подобные приведенным ниже, при проверке по статистике get-mailboxstatistics:

WARNING: The object <GUID> has been corrupted, and it's in an inconsistent state. The following validation errors happened:
WARNING: Cannot extract the property value of 'DeletedItemCount'. Source: PropTag(DeletedMsgCount), PropType(Int), RawValue(-2), RawValueType(System.Int32). Target:
Type(System.Nullable`1[System.UInt32]), IsMultiValued(False). Error Details: <n/a>

Запуск New-MailboxRepairRequest для всех баз данных выявил некоторые повреждения и исправил их, но не все. Кажется, я не могу найти способ заставить Get-MailboxStatistics регистрировать тот факт, что в каждом из этих почтовых ящиков что-то сломано, хотя я уверен, что он есть. Перенос почтовых ящиков из одной базы данных в другую, похоже, решает проблему. У нас есть ~ 50 БД и около 50 пользователей на БД, так что вручную не перебирать.

Я хочу сделать через PowerShell (извините, пожалуйста, ленивый псевдокод):

foreach ($mailbox in $database){
    if get-mailboxstatisics -eq $corrupted {
        move $mailbox to $otherdb
        wait
        move $mailbox back to $database}
    }

Однако я не могу понять, как отловить текст «Предупреждение: это не работает» из Get-MailboxStatistics, а в возвращенном результирующем объекте нет ничего, что указывало бы на его поломку.

Мне просто нужно поймать предупреждение и предположить, что все, что жалуется на несоответствия, можно исправить таким образом, затем вернуться и проверить список почтовых ящиков, у которых действительно возникла проблема после того, как они были перемещены и обратно, чтобы увидеть, все ли в порядке сломан? Есть ли лучший способ сделать то, что мне нужно?

Замена SAN выходит за рамки возможностей, как и устранение других основных причин.

Чтобы изолировать сообщения от существующих командлетов PowerShell, вы можете использовать

Предупреждающая переменная. Большинство командлетов по умолчанию имеют -WarningVariable параметр доступен, вы можете комбинировать его с -WarningAction SilentlyContinue для подавления предупреждения и сохранения его вывода в переменной, которой затем можно управлять или отображать, как вам нравится. Итак, вы можете запустить это

$mailbox | Get-MailboxStatistics -WarningAction SilentlyContinue -WarningVariable MyWarning;
if($MyWarning -like '*corrupted*'){
  Write-Host "possible corruption";
}

Я попытался воспроизвести предупреждающее событие, чтобы дважды проверить вышеуказанное, но не смог выполнить командлет MailboxStats. Вышеупомянутое должно работать - но в данном контексте оно не проверено.