/Source/FIMPSResource.cs
C# | 252 lines | 174 code | 33 blank | 45 comment | 17 complexity | c72133ead2d614a8570ef5f06bdd3e50 MD5 | raw file
1using System; 2using System.Collections.Generic; 3using System.Linq; 4using System.Text; 5using System.Collections.ObjectModel; 6using Microsoft.ResourceManagement.ObjectModel; 7 8namespace Quest.FIMPowerShellSnapin 9{ 10 /// <summary> 11 /// The FIMPSCmdletResource class represents a FIM resource object as a PowerShell object. It contains a reference to the RmResource object 12 /// as well as a reference to the FIMPSCmdletSession that the RmResource object is associate with. 13 /// </summary> 14 public class FIMPSResource 15 { 16 private readonly RmResource _resource; 17 private readonly FIMPSSession _session; 18 private RmResourceChanges _changes; 19 20 public FIMPSResource(FIMPSSession session) 21 : this(new RmResource(), session) 22 { 23 } 24 25 internal FIMPSResource(RmResource obj, FIMPSSession session) 26 { 27 if (session == null) 28 { 29 throw new ArgumentNullException(); 30 } 31 32 _resource = obj; 33 _session = session; 34 _changes = new RmResourceChanges(_resource); 35 36 _changes.BeginChanges(); // Copies current attribute values so we can calculate changeset later 37 } 38 39 /// <summary> 40 /// Determines if two FIM PS cmdlet resource objects are equal. To be equal, they must be from the same FIM server, the 41 /// credentials used to obtain the object must be the same, and the property values must all be the same. 42 /// </summary> 43 /// <param name="obj">The PS object to compare</param> 44 /// <returns>true if the two objects are equal, false if they are not equal</returns> 45 public override bool Equals(object obj) 46 { 47 if (obj == this) 48 { 49 return true; 50 } 51 52 FIMPSResource other = obj as FIMPSResource; 53 if (other == null) 54 { 55 return false; 56 } 57 58 if (Session.Server.ToLowerInvariant() != other.Session.Server.ToLowerInvariant()) 59 { 60 return false; 61 } 62 63 if (Session.Credential.UserName.Trim().ToLowerInvariant() != other.Session.Credential.UserName.Trim().ToLowerInvariant()) 64 { 65 return false; 66 } 67 68 return Resource.Equals(other.Resource); 69 } 70 71 public override int GetHashCode() 72 { 73 return _resource.GetHashCode(); 74 } 75 76 77 public RmResource Resource 78 { 79 get 80 { 81 return _resource; 82 } 83 } 84 85 public FIMPSSession Session 86 { 87 get 88 { 89 return _session; 90 } 91 } 92 93 /// <summary> 94 /// Indexer. Allows PoSh to retrieve attributes from the object using indexed array notation. Attribute values are 95 /// returned as strings, except for attributes defined in the schema as dates, which are returned as DateTime. 96 /// Multi-valued attributes are returned as a List of either strings or DateTimes. 97 /// </summary> 98 /// <param name="attributeName">The name of the attribute to retrieve.</param> 99 /// <returns></returns> 100 public object this[string attributeName] 101 { 102 get 103 { 104 object pSValue; 105 106 try // or else PoSh suppresses exceptions 107 { 108 RmAttributeName resourceAttributeName = new RmAttributeName(attributeName); 109 RmAttributeValue resourceValue = _resource[resourceAttributeName]; 110 111 bool isDateTime = (_session.Client.Schema.GetAttributeType(attributeName) == SchemaCache.AttributeType.DateTime); 112 113 if (_session.Client.Schema.IsMultiValued(resourceAttributeName)) 114 { 115 List<object> listOfValues = new List<object>(resourceValue.Values.Count); 116 foreach (RmAttributeValue rmValue in resourceValue.Values) 117 { 118 listOfValues.Add(isDateTime ? ConvertValueToDateTime(rmValue) : rmValue); 119 } 120 pSValue = new ReadOnlyCollection<object>(listOfValues); 121 } 122 else 123 { 124 pSValue = isDateTime ? ConvertValueToDateTime(resourceValue) : resourceValue; 125 } 126 } 127 catch 128 { 129 throw; 130 } 131 return pSValue; 132 } 133 } 134 135 private object ConvertValueToDateTime(RmAttributeValue rmValue) 136 { 137 if (rmValue.IsNullValue()) 138 { 139 return new DateTime(); 140 } 141 else 142 { 143 return DateTime.Parse(rmValue.ToString()); 144 } 145 } 146 147#if false 148 public ICollection<ILMAttributeInfo> Attributes 149 { 150 get 151 { 152 List<retList = new List<ILMAttributeInfo>(); 153 154 foreach (String key in RmObject.AttributeNames) 155 { 156 retList.Add(new ILMAttributeInfo(RmObject[key])); 157 } 158 159 return new ReadOnlyCollection<ILMAttributeInfo>(retList); 160 } 161 } 162#endif 163 /// <summary> 164 /// Adds a value to the specified attribute. If the attribute doesn't exist, it will be created. If the 165 /// attribute is single-valued, it throws an exception. If the attribute is multi-valued the specified value 166 /// will be added to the attribute. Note that this code does not check for the prior existence of the 167 /// value, so it will be possible to create a multi-valued attribute with multiple identical values, which 168 /// would be rejected by the FIM service. 169 /// </summary> 170 /// <param name="attributeName">The name of the attribute to modify</param> 171 /// <param name="attributeValue">The value to set or add to the attribute</param> 172 public void AddValue(string attributeName, IComparable attributeValue) 173 { 174 RmAttributeName rmAttrName = new RmAttributeName(attributeName); 175 176 bool isMultivalued = _session.Client.Schema.IsMultiValued(rmAttrName); 177 if(!isMultivalued) 178 { 179 throw new ArgumentException(string.Format(Constants.Messages.Error_IllegalOpForSVA, attributeName)); 180 } 181 182 RmAttributeValue rmAttrValue = null; 183 if(_resource.TryGetValue(rmAttrName, out rmAttrValue)) 184 { 185 rmAttrValue.Values.Add(attributeValue); 186 } 187 else 188 { 189 rmAttrValue.Value = attributeValue; 190 } 191 _resource[rmAttrName] = rmAttrValue; 192 } 193 194 /// <summary> 195 /// Removes a value from the specified multi-valued attribute. If the attribute does not exist, or if the 196 /// attribute is defined as single-valued, or if the value does not exist in the multi-value, throws an exception. 197 /// </summary> 198 /// <param name="attributeName">The name of the attribute to remove or modify</param> 199 /// <param name="attributeValue">The value to remove from the attribute</param> 200 public void RemoveValue(string attributeName, IComparable attributeValue) 201 { 202 RmAttributeName rmAttrName = new RmAttributeName(attributeName); 203 204 bool isMultivalued = _session.Client.Schema.IsMultiValued(rmAttrName); 205 if(!isMultivalued) 206 { 207 throw new ArgumentException(string.Format(Constants.Messages.Error_IllegalOpForSVA, attributeName)); 208 } 209 210 //!! Debateable as to whether this should throw an exception if the attr doesn't exist. Could just ignore it. 211 RmAttributeValue rmAttrValue = null; 212 if(!_resource.TryGetValue(rmAttrName, out rmAttrValue)) 213 { 214 throw new ArgumentException(string.Format(Constants.Messages.Error_AttributeMissing, attributeName)); 215 } 216 217 rmAttrValue.Values.Remove(attributeValue); 218 _resource[rmAttrName] = rmAttrValue; 219 } 220 221 /// <summary> 222 /// Sets the value of the specified attribute to the specified value. If the attribute value does not exist, it 223 /// will be added. If the attribute is single valued, any existing value will be replaced. If the attribute 224 /// is multi-valued, the value will be replaced with the specified value. Null is a valid value. 225 /// </summary> 226 /// <param name="attributeName">The name of the attribute to remove or modify</param> 227 /// <param name="attributeValue">The value to remove from the attribute</param> 228 public void SetValue(string attributeName, object attributeValue) 229 { 230 231 RmAttributeName rmAttrName = new RmAttributeName(attributeName); 232 RmAttributeValue rmAttrValue = new RmAttributeValue(attributeValue as IComparable); 233 234 _resource[rmAttrName] = rmAttrValue; 235 } 236 237 /// <summary> 238 /// Retrieves the RmResourceChanges object associated with this object. The RmResourceChanges object contains 239 /// the original value of the objects attributes so that a delta can be computed to update the FIM web service. 240 /// </summary> 241 /// <returns></returns> 242 public RmResourceChanges GetTransactionChanges() 243 { 244 return _changes; 245 } 246 247 public void AcceptChanges() 248 { 249 _changes.AcceptChanges(); 250 } 251 } 252}