У меня есть набор веб-сервисов SOAP, которые обертывают исключения с помощью IErrorHandler, а именно:
public sealed class ErrorHandler : IErrorHandler
{
public bool HandleError(Exception error)
{
return true;
}
public void ProvideFault(Exception error, MessageVersion version, ref Message fault)
{
// don't wrap existing fault exceptions
if ((error is FaultException)) return;
// our basic service fault
var businessFault = new BusinessFault { FaultMessage = error.Message, FaultReference = "Internal" };
// Resource based faultReason
var faultReason = new FaultReason(Properties.Resources.BusinessFaultReason);
var faultcode = FaultCodeFactory.CreateVersionAwareSenderFaultCode(InternalFaultCodes.BusinessFailure.ToString(), Service.Namespace);
var faultException = new FaultException<BusinessFault>(
businessFault,
faultReason,
faultcode);
// Create message fault
var messageFault = faultException.CreateMessageFault();
// Create message using Message Factory method
fault = Message.CreateMessage(version, messageFault, faultException.Action);
}
}
Я добавил дополнительные конечные точки для Json и Pox, которые работают нормально, если не происходит исключение. В случае конечной точки Json FaultException возвращается в виде XML.
Мне известно из других сообщений SO, что в случае REST мне лучше создать исключение WebHttpException:
throw new WebFaultException<BusinessFault>(detail, HttpStatusCode.BadRequest);
Или переопределить свойства ответного сообщения в ProvideFault, например:
var wbf = new WebBodyFormatMessageProperty(WebContentFormat.Json);
fault.Properties.Add(WebBodyFormatMessageProperty.Name, wbf);
var rmp = new HttpResponseMessageProperty
{
StatusCode = System.Net.HttpStatusCode.BadRequest,
StatusDescription = "See fault object for more information."
};
fault.Properties.Add(HttpResponseMessageProperty.Name, rmp);
Однако в MSDN есть несколько интересных замечаний по поводу WebHttpException , а именно:
При использовании конечной точки REST WCF (WebHttpBinding и WebHttpBehavior или
WebScriptEnablingBehavior) устанавливается HTTP-код состояния в ответе
соответственно. Тем не менее, WebFaultException можно использовать с не-REST
конечные точки и ведет себя как обычное исключение FaultException.
При использовании конечной точки REST WCF формат ответа сериализованного
неисправность определяется так же, как реакция без неисправности. Для большего
информацию о форматировании WCF REST см. в разделе Форматирование WCF REST.
Таким образом, можно предположить, что мне нужно преобразовать мой текущий метод ProvideFault, чтобы обеспечить новое WebHttpException (обертывание любых существующих исключений или FaultExceptions), и тогда SOAP все равно будет работать.
Кто-нибудь хотел бы попробовать, как это будет выглядеть (.Net4.0 btw)? Я хочу, чтобы один обработчик ошибок управлял ими всеми!