Utöka kontrollen över felhantering och rapportering
ErrorHandling-exemplet visar hur du utökar kontrollen över felhantering och felrapportering i en WCF-tjänst (Windows Communication Foundation) med hjälp av IErrorHandler gränssnittet. Exemplet baseras på Komma igång med ytterligare kod som lagts till i tjänsten för att hantera fel. Klienten tvingar fram flera feltillstånd. Tjänsten fångar upp felen och loggar dem i en fil.
Kommentar
Installationsproceduren och bygginstruktionerna för det här exemplet finns i slutet av det här avsnittet.
Tjänster kan fånga upp fel, utföra bearbetning och påverka hur fel rapporteras med hjälp av IErrorHandler gränssnittet. Gränssnittet har två metoder som kan implementeras: ProvideFault(Exception, MessageVersion, Message) och HandleError. Med ProvideFault(Exception, MessageVersion, Message) metoden kan du lägga till, ändra eller ignorera ett felmeddelande som genereras som svar på ett undantag. Metoden HandleError tillåter att felbearbetning sker i händelse av ett fel och styr om ytterligare felhantering kan köras.
I det här exemplet CalculatorErrorHandler
implementerar IErrorHandler typen gränssnittet. I
HandleErrorCalculatorErrorHandler
-metoden skriver en logg över felet till en Error.txt textfil i c:\logs. Observera att exemplet loggar felet och inte undertrycker det, så att det kan rapporteras tillbaka till klienten.
public class CalculatorErrorHandler : IErrorHandler
{
// Provide a fault. The Message fault parameter can be replaced, or set to
// null to suppress reporting a fault.
public void ProvideFault(Exception error, MessageVersion version, ref Message fault)
{
}
// HandleError. Log an error, then allow the error to be handled as usual.
// Return true if the error is considered as already handled
public bool HandleError(Exception error)
{
using (TextWriter tw = File.AppendText(@"c:\logs\error.txt"))
{
if (error != null)
{
tw.WriteLine("Exception: " + error.GetType().Name + " - " + error.Message);
}
tw.Close();
}
return true;
}
}
ErrorBehaviorAttribute
Finns som en mekanism för att registrera en felhanterare med en tjänst. Det här attributet tar en parameter av en enda typ. Den typen bör implementera IErrorHandler gränssnittet och ha en offentlig, tom konstruktor. Attributet instansierar sedan en instans av den felhanterartypen och installerar den i tjänsten. Det gör det genom att implementera IServiceBehavior gränssnittet och sedan använda ApplyDispatchBehavior metoden för att lägga till instanser av felhanteraren i tjänsten.
// This attribute can be used to install a custom error handler for a service.
public class ErrorBehaviorAttribute : Attribute, IServiceBehavior
{
Type errorHandlerType;
public ErrorBehaviorAttribute(Type errorHandlerType)
{
this.errorHandlerType = errorHandlerType;
}
void IServiceBehavior.Validate(ServiceDescription description, ServiceHostBase serviceHostBase)
{
}
void IServiceBehavior.AddBindingParameters(ServiceDescription description, ServiceHostBase serviceHostBase, System.Collections.ObjectModel.Collection<ServiceEndpoint> endpoints, BindingParameterCollection parameters)
{
}
void IServiceBehavior.ApplyDispatchBehavior(ServiceDescription description, ServiceHostBase serviceHostBase)
{
IErrorHandler errorHandler;
try
{
errorHandler = (IErrorHandler)Activator.CreateInstance(errorHandlerType);
}
catch (MissingMethodException e)
{
throw new ArgumentException("The errorHandlerType specified in the ErrorBehaviorAttribute constructor must have a public empty constructor.", e);
}
catch (InvalidCastException e)
{
throw new ArgumentException("The errorHandlerType specified in the ErrorBehaviorAttribute constructor must implement System.ServiceModel.Dispatcher.IErrorHandler.", e);
}
foreach (ChannelDispatcherBase channelDispatcherBase in serviceHostBase.ChannelDispatchers)
{
ChannelDispatcher channelDispatcher = channelDispatcherBase as ChannelDispatcher;
channelDispatcher.ErrorHandlers.Add(errorHandler);
}
}
}
Exemplet implementerar en kalkylatortjänst. Klienten orsakar avsiktligt två fel i tjänsten genom att ange parametrar med ogiltiga värden. CalculatorErrorHandler
Använder IErrorHandler gränssnittet för att logga felen till en lokal fil och tillåter sedan att de rapporteras tillbaka till klienten. Klienten tvingar fram en uppdelning med noll och ett argument-out-of-range-villkor.
try
{
Console.WriteLine("Forcing an error in Divide");
// Call the Divide service operation - trigger a divide by 0 error.
value1 = 22;
value2 = 0;
result = proxy.Divide(value1, value2);
Console.WriteLine("Divide({0},{1}) = {2}", value1, value2, result);
}
catch (FaultException e)
{
Console.WriteLine("FaultException: " + e.GetType().Name + " - " + e.Message);
}
catch (Exception e)
{
Console.WriteLine("Exception: " + e.GetType().Name + " - " + e.Message);
}
När du kör exemplet visas åtgärdsbegäranden och svar i klientkonsolfönstret. Du ser divisionen med noll och de argument-out-of-range-villkor som rapporteras som fel. Tryck på RETUR i klientfönstret för att stänga av klienten.
Add(15,3) = 18
Subtract(145,76) = 69
Multiply(9,81) = 729
Forcing an error in Divide
FaultException: FaultException - Invalid Argument: The second argument must not be zero.
Forcing an error in Factorial
FaultException: FaultException - Invalid Argument: The argument must be greater than zero.
Press <ENTER> to terminate client.
Filen c:\logs\errors.txt innehåller den information som loggas om felen i tjänsten. Observera att för att tjänsten ska kunna skriva till katalogen måste du se till att processen som tjänsten körs under (vanligtvis ASP.NET eller Nätverkstjänst) har behörighet att skriva till katalogen.
Fault: Reason = Invalid Argument: The second argument must not be zero.
Fault: Reason = Invalid Argument: The argument must be greater than zero.
Så här konfigurerar du, skapar och kör exemplet
Kontrollera att du har utfört engångsinstallationsproceduren för Windows Communication Foundation-exempel.
Skapa lösningen genom att följa anvisningarna i Skapa Windows Communication Foundation-exempel.
Kontrollera att du har skapat katalogen c:\logs för error.txt-filen. Eller ändra filnamnet som används i
CalculatorErrorHandler.HandleError
.Om du vill köra exemplet i en konfiguration med en eller flera datorer följer du anvisningarna i Köra Windows Communication Foundation-exempel.