Итак, вот что я сделал. У нас есть несколько пользовательских исключений в нашем приложении, таких как BusinessRuleException и ProcessException, WCF поддерживает как FaultException, так и FaultException<T>
.
Общая практика, как представляется, заключается в том, что вы всегда выдаваете FaultException клиенту в случае общей ошибки или ошибки, которую вы не хотите отображать точно, что произошло. В других случаях вы можете передать FaultException<T>
, где T - класс с информацией о конкретном исключении.
Я создал эту концепцию Violations в приложении, что в основном означало, что любое пользовательское исключение имеет свойство, содержащее соответствующий экземпляр Violation. Затем этот экземпляр был передан клиенту, что позволило клиенту распознать, когда возникла исправимая ошибка.
Это решило часть проблемы, но я все еще хотел получить общий улов, который позволил бы мне централизовать ведение журнала. Я нашел это, используя интерфейс IErrorHandle и добавив свой собственный обработчик ошибок в WCF. Вот код:
public class ServiceHostGeneralErrorHandler : IErrorHandler
{
public void ProvideFault(Exception ex, MessageVersion version, ref Message fault)
{
if (ex is FaultException)
return;
// a general message to the client
var faultException = new FaultException("A General Error Occured");
MessageFault messageFault = faultException.CreateMessageFault();
fault = Message.CreateMessage(version, messageFault, null);
}
public bool HandleError(Exception ex)
{
// log the exception
// mark as handled
return true;
}
}
Используя этот метод, я могу преобразовать исключение из того, чем оно является, во что-то, что может быть легко отображено на клиенте, и в то же время записать реальное исключение, которое увидит ИТ-персонал. Пока что этот подход работает достаточно хорошо и имеет ту же структуру, что и другие модули приложения.