ScopedMessagePartSpecification.cs 7.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209
  1. //------------------------------------------------------------
  2. // Copyright (c) Microsoft Corporation. All rights reserved.
  3. //------------------------------------------------------------
  4. namespace System.ServiceModel.Security
  5. {
  6. using System.Collections.Generic;
  7. using System.ServiceModel.Channels;
  8. using System.ServiceModel;
  9. using System.Runtime.Serialization;
  10. using System.ServiceModel.Security;
  11. using System.Xml;
  12. public class ScopedMessagePartSpecification
  13. {
  14. MessagePartSpecification channelParts;
  15. Dictionary<string, MessagePartSpecification> actionParts;
  16. Dictionary<string, MessagePartSpecification> readOnlyNormalizedActionParts;
  17. bool isReadOnly;
  18. public ScopedMessagePartSpecification()
  19. {
  20. this.channelParts = new MessagePartSpecification();
  21. this.actionParts = new Dictionary<string, MessagePartSpecification>();
  22. }
  23. public ICollection<string> Actions
  24. {
  25. get
  26. {
  27. return this.actionParts.Keys;
  28. }
  29. }
  30. public MessagePartSpecification ChannelParts
  31. {
  32. get
  33. {
  34. return this.channelParts;
  35. }
  36. }
  37. public bool IsReadOnly
  38. {
  39. get
  40. {
  41. return this.isReadOnly;
  42. }
  43. }
  44. public ScopedMessagePartSpecification(ScopedMessagePartSpecification other)
  45. : this()
  46. {
  47. if (other == null)
  48. throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new ArgumentNullException("other"));
  49. this.channelParts.Union(other.channelParts);
  50. if (other.actionParts != null)
  51. {
  52. foreach (string action in other.actionParts.Keys)
  53. {
  54. MessagePartSpecification p = new MessagePartSpecification();
  55. p.Union(other.actionParts[action]);
  56. this.actionParts[action] = p;
  57. }
  58. }
  59. }
  60. internal ScopedMessagePartSpecification(ScopedMessagePartSpecification other, bool newIncludeBody)
  61. : this(other)
  62. {
  63. this.channelParts.IsBodyIncluded = newIncludeBody;
  64. foreach (string action in this.actionParts.Keys)
  65. this.actionParts[action].IsBodyIncluded = newIncludeBody;
  66. }
  67. public void AddParts(MessagePartSpecification parts)
  68. {
  69. if (parts == null)
  70. throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new ArgumentNullException("parts"));
  71. ThrowIfReadOnly();
  72. this.channelParts.Union(parts);
  73. }
  74. public void AddParts(MessagePartSpecification parts, string action)
  75. {
  76. if (action == null)
  77. throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new ArgumentNullException("action"));
  78. if (parts == null)
  79. throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new ArgumentNullException("parts"));
  80. ThrowIfReadOnly();
  81. if (!this.actionParts.ContainsKey(action))
  82. this.actionParts[action] = new MessagePartSpecification();
  83. this.actionParts[action].Union(parts);
  84. }
  85. internal void AddParts(MessagePartSpecification parts, XmlDictionaryString action)
  86. {
  87. if (action == null)
  88. throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new ArgumentNullException("action"));
  89. AddParts(parts, action.Value);
  90. }
  91. internal bool IsEmpty()
  92. {
  93. bool result;
  94. if (!channelParts.IsEmpty())
  95. {
  96. result = false;
  97. }
  98. else
  99. {
  100. result = true;
  101. foreach (string action in this.Actions)
  102. {
  103. MessagePartSpecification parts;
  104. if (TryGetParts(action, true, out parts))
  105. {
  106. if (!parts.IsEmpty())
  107. {
  108. result = false;
  109. break;
  110. }
  111. }
  112. }
  113. }
  114. return result;
  115. }
  116. public bool TryGetParts(string action, bool excludeChannelScope, out MessagePartSpecification parts)
  117. {
  118. if (action == null)
  119. action = MessageHeaders.WildcardAction;
  120. parts = null;
  121. if (this.isReadOnly)
  122. {
  123. if (this.readOnlyNormalizedActionParts.ContainsKey(action))
  124. if (excludeChannelScope)
  125. parts = this.actionParts[action];
  126. else
  127. parts = this.readOnlyNormalizedActionParts[action];
  128. }
  129. else if (this.actionParts.ContainsKey(action))
  130. {
  131. MessagePartSpecification p = new MessagePartSpecification();
  132. p.Union(this.actionParts[action]);
  133. if (!excludeChannelScope)
  134. p.Union(this.channelParts);
  135. parts = p;
  136. }
  137. return parts != null;
  138. }
  139. internal void CopyTo(ScopedMessagePartSpecification target)
  140. {
  141. if (target == null)
  142. {
  143. throw DiagnosticUtility.ExceptionUtility.ThrowHelperArgumentNull("target");
  144. }
  145. target.ChannelParts.IsBodyIncluded = this.ChannelParts.IsBodyIncluded;
  146. foreach (XmlQualifiedName headerType in ChannelParts.HeaderTypes)
  147. {
  148. if (!target.channelParts.IsHeaderIncluded(headerType.Name, headerType.Namespace))
  149. {
  150. target.ChannelParts.HeaderTypes.Add(headerType);
  151. }
  152. }
  153. foreach (string action in this.actionParts.Keys)
  154. {
  155. target.AddParts(this.actionParts[action], action);
  156. }
  157. }
  158. public bool TryGetParts(string action, out MessagePartSpecification parts)
  159. {
  160. return this.TryGetParts(action, false, out parts);
  161. }
  162. public void MakeReadOnly()
  163. {
  164. if (!this.isReadOnly)
  165. {
  166. this.readOnlyNormalizedActionParts = new Dictionary<string, MessagePartSpecification>();
  167. foreach (string action in this.actionParts.Keys)
  168. {
  169. MessagePartSpecification p = new MessagePartSpecification();
  170. p.Union(this.actionParts[action]);
  171. p.Union(this.channelParts);
  172. p.MakeReadOnly();
  173. this.readOnlyNormalizedActionParts[action] = p;
  174. }
  175. this.isReadOnly = true;
  176. }
  177. }
  178. void ThrowIfReadOnly()
  179. {
  180. if (this.isReadOnly)
  181. throw DiagnosticUtility.ExceptionUtility.ThrowHelperError(new InvalidOperationException(SR.GetString(SR.ObjectIsReadOnly)));
  182. }
  183. }
  184. }