1
//-----------------------------------------------------------------------
2 // <copyright file="ProtocolException.cs" company="Andrew Arnott">
3 // Copyright (c) Andrew Arnott. All rights reserved.
5 //-----------------------------------------------------------------------
7 namespace DotNetOpenAuth
.Messaging
{
9 using System
.Collections
.Generic
;
10 using System
.Security
.Permissions
;
13 /// An exception to represent errors in the local or remote implementation of the protocol.
16 public class ProtocolException
: Exception
, IDirectedProtocolMessage
{
18 /// The request message being processed when this exception was generated, if any.
20 private IProtocolMessage inResponseTo
;
23 /// The indirect message receiver this exception should be delivered to, if any.
25 private Uri recipient
;
28 /// A cache for extra name/value pairs tacked on as data when this exception is sent as a message.
30 private Dictionary
<string, string> extraData
= new Dictionary
<string, string>();
33 /// Initializes a new instance of the <see cref="ProtocolException"/> class.
35 public ProtocolException() { }
38 /// Initializes a new instance of the <see cref="ProtocolException"/> class.
40 /// <param name="message">A message describing the specific error the occurred or was detected.</param>
41 public ProtocolException(string message
) : base(message
) { }
44 /// Initializes a new instance of the <see cref="ProtocolException"/> class.
46 /// <param name="message">A message describing the specific error the occurred or was detected.</param>
47 /// <param name="inner">The inner exception to include.</param>
48 public ProtocolException(string message
, Exception inner
) : base(message
, inner
) { }
51 /// Initializes a new instance of the <see cref="ProtocolException"/> class
52 /// such that it can be sent as a protocol message response to a remote caller.
54 /// <param name="message">The human-readable exception message.</param>
55 /// <param name="faultedMessage">The message that was the cause of the exception. May not be null.</param>
56 internal ProtocolException(string message
, IProtocolMessage faultedMessage
)
58 if (faultedMessage
== null) {
59 throw new ArgumentNullException("faultedMessage");
62 this.FaultedMessage
= faultedMessage
;
66 /// Initializes a new instance of the <see cref="ProtocolException"/> class
67 /// such that it can be sent as a protocol message response to a remote caller.
69 /// <param name="message">The human-readable exception message.</param>
70 /// <param name="inResponseTo">
71 /// If <paramref name="message"/> is a response to an incoming message, this is the incoming message.
72 /// This is useful for error scenarios in deciding just how to send the response message.
75 /// <param name="remoteIndirectReceiver">
76 /// In the case of exceptions that will be sent as indirect messages to the original calling
77 /// remote party, this is the URI of that remote site's receiver.
78 /// May be null only if the <paramref name="inResponseTo"/> message is a direct request.
80 internal ProtocolException(string message
, IProtocolMessage inResponseTo
, Uri remoteIndirectReceiver
)
82 if (inResponseTo
== null) {
83 throw new ArgumentNullException("inResponseTo");
85 this.inResponseTo
= inResponseTo
;
86 this.FaultedMessage
= inResponseTo
;
88 if (remoteIndirectReceiver
== null && inResponseTo
.Transport
!= MessageTransport
.Direct
) {
89 // throw an exception, with ourselves as the inner exception (as fully initialized as we can be).
90 throw new ArgumentNullException("remoteIndirectReceiver");
92 this.recipient
= remoteIndirectReceiver
;
96 /// Initializes a new instance of the <see cref="ProtocolException"/> class.
98 /// <param name="info">The <see cref="System.Runtime.Serialization.SerializationInfo"/>
99 /// that holds the serialized object data about the exception being thrown.</param>
100 /// <param name="context">The System.Runtime.Serialization.StreamingContext
101 /// that contains contextual information about the source or destination.</param>
102 protected ProtocolException(
103 System
.Runtime
.Serialization
.SerializationInfo info
,
104 System
.Runtime
.Serialization
.StreamingContext context
)
105 : base(info
, context
) {
106 throw new NotImplementedException();
109 #region IProtocolMessage Properties
112 /// Gets the version of the protocol this message is prepared to implement.
114 Version IMessage
.Version
{
115 get { return this.Version; }
119 /// Gets the level of protection this exception requires when transmitted as a message.
121 MessageProtections IProtocolMessage
.RequiredProtection
{
122 get { return RequiredProtection; }
126 /// Gets whether this is a direct or indirect message.
128 MessageTransport IProtocolMessage
.Transport
{
129 get { return this.Transport; }
134 #region IDirectedProtocolMessage Members
137 /// Gets the preferred method of transport for the message.
140 /// This exception may be delivered as an indirect message or a direct response. This property
141 /// only applies to the former. The latter will never query this property.
143 HttpDeliveryMethods IDirectedProtocolMessage
.HttpMethods
{
144 get { return HttpDeliveryMethods.GetRequest | HttpDeliveryMethods.PostRequest; }
148 /// Gets the URL of the intended receiver of this message.
151 /// This property should only be called when the error is being sent as an indirect response.
153 Uri IDirectedProtocolMessage
.Recipient
{
154 get { return this.Recipient; }
160 /// Gets the dictionary of additional name/value fields tacked on to this message.
162 IDictionary
<string, string> IMessage
.ExtraData
{
163 get { return this.ExtraData; }
167 /// Gets the message that caused the exception.
169 internal IProtocolMessage FaultedMessage
{
175 /// Gets the level of protection this exception requires when transmitted as a message.
177 protected static MessageProtections RequiredProtection
{
178 get { return MessageProtections.None; }
182 /// Gets the preferred method of transport for the message.
184 protected HttpDeliveryMethods HttpMethods
{
185 get { return ((IDirectedProtocolMessage)this).HttpMethods; }
189 /// Gets the URL of the intended receiver of this message.
192 /// This property should only be called when the error is being sent as an indirect response.
194 protected Uri Recipient
{
196 if (this.inResponseTo
== null) {
197 throw new InvalidOperationException(MessagingStrings
.ExceptionNotConstructedForTransit
);
199 return this.recipient
;
204 /// Gets the version of the protocol this message is prepared to implement.
206 protected Version Version
{
208 if (this.inResponseTo
== null) {
209 throw new InvalidOperationException(MessagingStrings
.ExceptionNotConstructedForTransit
);
211 return this.inResponseTo
.Version
;
216 /// Gets whether this is a direct or indirect message.
218 protected MessageTransport Transport
{
220 if (this.inResponseTo
== null) {
221 throw new InvalidOperationException(MessagingStrings
.ExceptionNotConstructedForTransit
);
223 return this.inResponseTo
.Transport
;
228 /// Gets the dictionary of additional name/value fields tacked on to this message.
230 protected IDictionary
<string, string> ExtraData
{
231 get { return this.extraData; }
235 /// When overridden in a derived class, sets the <see cref="T:System.Runtime.Serialization.SerializationInfo"/> with information about the exception.
237 /// <param name="info">The <see cref="T:System.Runtime.Serialization.SerializationInfo"/> that holds the serialized object data about the exception being thrown.</param>
238 /// <param name="context">The <see cref="T:System.Runtime.Serialization.StreamingContext"/> that contains contextual information about the source or destination.</param>
239 /// <exception cref="T:System.ArgumentNullException">
240 /// The <paramref name="info"/> parameter is a null reference (Nothing in Visual Basic).
243 /// <IPermission class="System.Security.Permissions.FileIOPermission, mscorlib, Version=2.0.3600.0, Culture=neutral, PublicKeyToken=b77a5c561934e089" version="1" Read="*AllFiles*" PathDiscovery="*AllFiles*"/>
244 /// <IPermission class="System.Security.Permissions.SecurityPermission, mscorlib, Version=2.0.3600.0, Culture=neutral, PublicKeyToken=b77a5c561934e089" version="1" Flags="SerializationFormatter"/>
246 [SecurityPermission(SecurityAction
.LinkDemand
, Flags
= SecurityPermissionFlag
.SerializationFormatter
)]
247 public override void GetObjectData(System
.Runtime
.Serialization
.SerializationInfo info
, System
.Runtime
.Serialization
.StreamingContext context
) {
248 base.GetObjectData(info
, context
);
249 throw new NotImplementedException();
252 #region IProtocolMessage Methods
255 /// See <see cref="IMessage.EnsureValidMessage"/>.
257 void IMessage
.EnsureValidMessage() {
258 this.EnsureValidMessage();
262 /// See <see cref="IMessage.EnsureValidMessage"/>.
264 protected virtual void EnsureValidMessage() {
265 if (this.inResponseTo
== null) {
266 throw new InvalidOperationException(MessagingStrings
.ExceptionNotConstructedForTransit
);