//-----------------------------------------------------------------------
//
// Copyright (c) Outercurve Foundation. All rights reserved.
//
//-----------------------------------------------------------------------
namespace DotNetOpenAuth.Messaging {
using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.Diagnostics.Contracts;
using System.Globalization;
using System.Web;
using DotNetOpenAuth.Logging;
using Validation;
///
/// A collection of error checking and reporting methods.
///
[Pure]
internal static class ErrorUtilities {
///
/// Wraps an exception in a new .
///
/// The inner exception to wrap.
/// The error message for the outer exception.
/// The string formatting arguments, if any.
/// The newly constructed (unthrown) exception.
[Pure]
internal static Exception Wrap(Exception inner, string errorMessage, params object[] args) {
Requires.NotNull(args, "args");
Assumes.True(errorMessage != null);
return new ProtocolException(string.Format(CultureInfo.CurrentCulture, errorMessage, args), inner);
}
///
/// Throws an internal error exception.
///
/// The error message.
/// Nothing. But included here so callers can "throw" this method for C# safety.
/// Always thrown.
[Pure]
internal static Exception ThrowInternal(string errorMessage) {
// Since internal errors are really bad, take this chance to
// help the developer find the cause by breaking into the
// debugger if one is attached.
if (Debugger.IsAttached) {
Debugger.Break();
}
throw new InternalErrorException(errorMessage);
}
///
/// Checks a condition and throws an internal error exception if it evaluates to false.
///
/// The condition to check.
/// The message to include in the exception, if created.
/// Thrown if evaluates to false.
[Pure]
internal static void VerifyInternal(bool condition, string errorMessage) {
if (!condition) {
ThrowInternal(errorMessage);
}
}
///
/// Checks a condition and throws an internal error exception if it evaluates to false.
///
/// The condition to check.
/// The message to include in the exception, if created.
/// The formatting arguments.
/// Thrown if evaluates to false.
[Pure]
internal static void VerifyInternal(bool condition, string errorMessage, params object[] args) {
Requires.NotNull(args, "args");
Assumes.True(errorMessage != null);
if (!condition) {
errorMessage = string.Format(CultureInfo.CurrentCulture, errorMessage, args);
throw new InternalErrorException(errorMessage);
}
}
///
/// Checks a condition and throws an if it evaluates to false.
///
/// The condition to check.
/// The message to include in the exception, if created.
/// Thrown if evaluates to false.
[Pure]
internal static void VerifyOperation(bool condition, string errorMessage) {
if (!condition) {
throw new InvalidOperationException(errorMessage);
}
}
///
/// Checks a condition and throws a if it evaluates to false.
///
/// The condition to check.
/// The message to include in the exception, if created.
/// Thrown if evaluates to false.
[Pure]
internal static void VerifySupported(bool condition, string errorMessage) {
if (!condition) {
throw new NotSupportedException(errorMessage);
}
}
///
/// Checks a condition and throws a if it evaluates to false.
///
/// The condition to check.
/// The message to include in the exception, if created.
/// The string formatting arguments for .
/// Thrown if evaluates to false.
[Pure]
internal static void VerifySupported(bool condition, string errorMessage, params object[] args) {
Requires.NotNull(args, "args");
Assumes.True(errorMessage != null);
if (!condition) {
throw new NotSupportedException(string.Format(CultureInfo.CurrentCulture, errorMessage, args));
}
}
///
/// Checks a condition and throws an if it evaluates to false.
///
/// The condition to check.
/// The message to include in the exception, if created.
/// The formatting arguments.
/// Thrown if evaluates to false.
[Pure]
internal static void VerifyOperation(bool condition, string errorMessage, params object[] args) {
Requires.NotNull(args, "args");
Assumes.True(errorMessage != null);
if (!condition) {
errorMessage = string.Format(CultureInfo.CurrentCulture, errorMessage, args);
throw new InvalidOperationException(errorMessage);
}
}
///
/// Throws a if some evaluates to false.
///
/// True to do nothing; false to throw the exception.
/// The error message for the exception.
/// The string formatting arguments, if any.
/// Thrown if evaluates to false.
[Pure]
internal static void VerifyHost(bool condition, string errorMessage, params object[] args) {
Requires.NotNull(args, "args");
Assumes.True(errorMessage != null);
if (!condition) {
throw new HostErrorException(string.Format(CultureInfo.CurrentCulture, errorMessage, args));
}
}
///
/// Throws a if some evaluates to false.
///
/// True to do nothing; false to throw the exception.
/// The message being processed that would be responsible for the exception if thrown.
/// The error message for the exception.
/// The string formatting arguments, if any.
/// Thrown if evaluates to false.
[Pure]
internal static void VerifyProtocol(bool condition, IProtocolMessage faultedMessage, string errorMessage, params object[] args) {
Requires.NotNull(args, "args");
Requires.NotNull(faultedMessage, "faultedMessage");
Assumes.True(errorMessage != null);
if (!condition) {
throw new ProtocolException(string.Format(CultureInfo.CurrentCulture, errorMessage, args), faultedMessage);
}
}
///
/// Throws a if some evaluates to false.
///
/// True to do nothing; false to throw the exception.
/// The error message for the exception.
/// The string formatting arguments, if any.
/// Thrown if evaluates to false.
[Pure]
internal static void VerifyProtocol(bool condition, string unformattedMessage, params object[] args) {
Requires.NotNull(args, "args");
Assumes.True(unformattedMessage != null);
if (!condition) {
var exception = new ProtocolException(string.Format(CultureInfo.CurrentCulture, unformattedMessage, args));
if (Logger.Messaging.IsErrorEnabled()) {
Logger.Messaging.Error(
string.Format(
CultureInfo.CurrentCulture,
"Protocol error: {0}{1}{2}",
exception.Message,
Environment.NewLine,
new StackTrace()));
}
throw exception;
}
}
///
/// Throws a .
///
/// The message to set in the exception.
/// The formatting arguments of the message.
///
/// An InternalErrorException, which may be "thrown" by the caller in order
/// to satisfy C# rules to show that code will never be reached, but no value
/// actually is ever returned because this method guarantees to throw.
///
/// Always thrown.
[Pure]
internal static Exception ThrowProtocol(string unformattedMessage, params object[] args) {
Requires.NotNull(args, "args");
Assumes.True(unformattedMessage != null);
VerifyProtocol(false, unformattedMessage, args);
// we never reach here, but this allows callers to "throw" this method.
return new InternalErrorException();
}
///
/// Throws a .
///
/// The message for the exception.
/// The string formatting arguments for .
/// Nothing. It's just here so the caller can throw this method for C# compilation check.
[Pure]
internal static Exception ThrowFormat(string message, params object[] args) {
Requires.NotNull(args, "args");
Assumes.True(message != null);
throw new FormatException(string.Format(CultureInfo.CurrentCulture, message, args));
}
///
/// Throws a if some condition is false.
///
/// The expression to evaluate. A value of false will cause the exception to be thrown.
/// The message for the exception.
/// The string formatting arguments for .
/// Thrown when is false.
[Pure]
internal static void VerifyFormat(bool condition, string message, params object[] args) {
Requires.NotNull(args, "args");
Assumes.True(message != null);
if (!condition) {
throw ThrowFormat(message, args);
}
}
///
/// Verifies something about the argument supplied to a method.
///
/// The condition that must evaluate to true to avoid an exception.
/// The message to use in the exception if the condition is false.
/// The string formatting arguments, if any.
/// Thrown if evaluates to false.
[Pure]
internal static void VerifyArgument(bool condition, string message, params object[] args) {
Requires.NotNull(args, "args");
Assumes.True(message != null);
if (!condition) {
throw new ArgumentException(string.Format(CultureInfo.CurrentCulture, message, args));
}
}
///
/// Throws an .
///
/// Name of the parameter.
/// The message to use in the exception if the condition is false.
/// The string formatting arguments, if any.
/// Never returns anything. It always throws.
[Pure]
internal static Exception ThrowArgumentNamed(string parameterName, string message, params object[] args) {
Requires.NotNull(args, "args");
Assumes.True(message != null);
throw new ArgumentException(string.Format(CultureInfo.CurrentCulture, message, args), parameterName);
}
///
/// Verifies something about the argument supplied to a method.
///
/// The condition that must evaluate to true to avoid an exception.
/// Name of the parameter.
/// The message to use in the exception if the condition is false.
/// The string formatting arguments, if any.
/// Thrown if evaluates to false.
[Pure]
internal static void VerifyArgumentNamed(bool condition, string parameterName, string message, params object[] args) {
Requires.NotNull(args, "args");
Assumes.True(message != null);
if (!condition) {
throw new ArgumentException(string.Format(CultureInfo.CurrentCulture, message, args), parameterName);
}
}
///
/// Verifies that some given value is not null.
///
/// The value to check.
/// Name of the parameter, which will be used in the , if thrown.
/// Thrown if is null.
[Pure]
internal static void VerifyArgumentNotNull(object value, string paramName) {
if (value == null) {
throw new ArgumentNullException(paramName);
}
}
///
/// Verifies that some string is not null and has non-zero length.
///
/// The value to check.
/// Name of the parameter, which will be used in the , if thrown.
/// Thrown if is null.
/// Thrown if has zero length.
[Pure]
internal static void VerifyNonZeroLength(string value, string paramName) {
VerifyArgumentNotNull(value, paramName);
if (value.Length == 0) {
throw new ArgumentException(MessagingStrings.UnexpectedEmptyString, paramName);
}
}
///
/// Verifies that != null.
///
/// Thrown if == null
[Pure]
internal static void VerifyHttpContext() {
ErrorUtilities.VerifyOperation(HttpContext.Current != null && HttpContext.Current.Request != null, MessagingStrings.HttpContextRequired);
}
///
/// Obtains a value from the dictionary if possible, or throws a if it's missing.
///
/// The type of key in the dictionary.
/// The type of value in the dictionary.
/// The dictionary.
/// The key to use to look up the value.
/// The message to claim is invalid if the key cannot be found.
/// The value for the given key.
[Pure]
internal static TValue GetValueOrThrow(this IDictionary dictionary, TKey key, IMessage message) {
Requires.NotNull(dictionary, "dictionary");
Requires.NotNull(message, "message");
TValue value;
VerifyProtocol(dictionary.TryGetValue(key, out value), MessagingStrings.ExpectedParameterWasMissing, key, message.GetType().Name);
return value;
}
}
}