예제 #1
0
		/// <summary>
		/// Populates a property in an object with data from the StepValue.
		/// </summary>
		/// <param name="pi">The property of the object which will be populated with the data</param>
		/// <param name="obj">The object which will be populated</param>
		/// <param name="sv">The data to insert into the property</param>
		/// <param name="stepId">The Id of the step data object which provided the data. (required incase of any step referencing)</param>
		private void populateProperty(PropertyInfo pi, ref object obj, StepValue sv, int stepId ){
			if(pi == null)
				throw new ArgumentNullException("pi");
			if(obj == null)
				throw new ArgumentNullException("obj");
			
			//debugging
			logger.Debug("Type of object being populated : " + obj.GetType().FullName);
			logger.Debug("The property being assigned to in the .Net object : "  + pi.Name);
			logger.Debug("The type of values held by that .Net property     : "  + pi.PropertyType);
			logger.Debug("STEP token     : "     + sv.Token);
			logger.Debug("STEP value     : "     + sv.Value);
			logger.Debug("STEP valueType : " + sv.ValueType);
			
			switch(sv.Token){
				case StepToken.StartEntity:
					mapObject(pi, ref obj, sv);
					break;
				case StepToken.String:
					mapString(pi, ref obj, sv);
					break;
				case StepToken.LineReference:
					storeLineReference(pi, ref obj, stepId, sv);
					break;
				case StepToken.StartArray:
					mapArray(pi, ref obj, sv, stepId);
					break;
				case StepToken.Enumeration:
					mapEnumeration(pi, ref obj, sv);
					break;
				case StepToken.Integer:
					mapInteger(pi, ref obj, sv);
					break;
				case StepToken.Float:
					mapFloat(pi, ref obj, sv);
					break;
				case StepToken.Null:
					//do nothing, the property value will already be null or default value (if a value type).
					break;
				case StepToken.Overridden:
					//do nothing
					break;
				default:
					throw new NotImplementedException(String.Format(CultureInfo.InvariantCulture,
					                                                "Failed on attempting to set value of property. This token type is not yet implemented: {0}",
					                                                sv.Token));
			}
		}
예제 #2
0
		public void AssertInteger(int expectedValue, StepValue actual){
			AssertStepValue(StepToken.Integer, typeof(int), expectedValue, actual);
		}
예제 #3
0
 private void SerializeProperty( IStepWriter writer, StepValue sv){
     if(writer == null) throw new ArgumentNullException("writer");
     
     switch(sv.Token){
         case StepToken.StartArray:
             //TODO assert that sv.ValueType.Equals(typeof(IList<StepValue>)
             SerializeArray( writer, sv.Value as List<StepValue> );
             break;
         case StepToken.Overridden:
             writer.WriteOverridden();
             break;
         case StepToken.Enumeration:
             writer.WriteEnum((string)sv.Value);
             break;
         case StepToken.String:
             writer.WriteValue((string)sv.Value);
             break;
         case StepToken.Integer:
             switch(sv.ValueType.ToString()){
                 case "System.Int16":
                     writer.WriteValue((System.Int16)sv.Value);
                     break;
                 case "System.Int32":
                     writer.WriteValue((System.Int32)sv.Value);
                     break;
                 case "System.Int64":
                     writer.WriteValue((System.Int64)sv.Value);
                     break;
                 default:
                     throw new StepSerializerException("SerializeProperty(StepWriter, StepValue) has a StepValue of token type Integer, but the ValueType is not an integer");
             }
             break;
         case StepToken.Float:
             writer.WriteValue((double)sv.Value);
             break;
         case StepToken.Boolean:
             writer.WriteBool((bool)sv.Value);
             break;
         case StepToken.Date:
             writer.WriteValue(((DateTime)sv.Value).ToString("yyyy-MM-ddTHH:mm:ss", CultureInfo.InvariantCulture));
             break;
         case StepToken.Null:
             writer.WriteNull();
             break;
         case StepToken.LineReference:
             writer.WriteLineReference( (int)sv.Value );
             break;
         case StepToken.StartEntity:
             logger.Debug("StartEntity : " + ((StepDataObject)sv.Value).ObjectName);
             SerializeObject(writer, (StepDataObject)sv.Value);
             break;
         default:
             throw new NotImplementedException(String.Format(CultureInfo.InvariantCulture,
                                                             "SerializeProperty(StepValue) cannot, yet, handle token {0}",
                                                             sv.Token.ToString()));
     }
 }
예제 #4
0
		private void storeLineReference(PropertyInfo pi, ref Object obj, int stepId, StepValue sp, int index){
			this._objectLinks.Add(new StepEntityReference(stepId, pi, (int)sp.Value, index));
		}
예제 #5
0
		public void AssertStepValue(StepToken expectedToken, Type expectedValueType, object expectedValue, StepValue actual){
			Assert.IsNotNull(actual);
			Assert.AreEqual(expectedToken, actual.Token);
			Assert.AreEqual(expectedValueType, actual.ValueType);
			Assert.AreEqual(expectedValue, actual.Value);
		}
예제 #6
0
		/// <summary>
		/// Maps a STEP enumeration to a .Net enum
		/// </summary>
		/// <param name="pi"></param>
		/// <param name="obj"></param>
		/// <param name="sv"></param>
		private void mapEnumeration(PropertyInfo pi, ref Object obj, StepValue sv){
			if(pi == null)
				throw new ArgumentNullException("pi");
			if(obj == null)
				throw new ArgumentNullException("obj");
			if(sv.Value == null)
				throw new ArgumentNullException("sv.Value");
			if(!(sv.Value is string))
				throw new ArgumentException("sv.Value should be a type of string");
			string spv = sv.Value as string;
			if(string.IsNullOrEmpty(spv))
				throw new ArgumentException("sv.Value should not be null or empty");
			spv = spv.ToLower();
			Object val;
			
			//STEP treats boolean values as enumerations
			if(pi.PropertyType == typeof(System.Boolean)){
				if(spv.Equals("t") || spv.Equals("f"))
					val = spv.Equals("t");
				else
					throw new FormatException(String.Format(CultureInfo.InvariantCulture,
					                                        "mapEnumeration found a boolean to parse, but the value was neither 't' nor 'f'.  The value was instead {0}",
					                                        spv));
			}else{
				//pi.Property type may be Nullable<theTypeWeNeed>
				Type enumType = Nullable.GetUnderlyingType( pi.PropertyType );
				if(enumType == null)
					enumType = pi.PropertyType;
				val = Enum.Parse(enumType, spv);//HACK the ToLower may not work in all cases
			}
			
			if(val == null)
				throw new FormatException(String.Format(CultureInfo.InvariantCulture,
				                                        "Could not find a suitable value for {0} in Enum type {1}",
				                                        spv.ToLower(),
				                                        pi.PropertyType.Name));
			pi.SetValue(obj, val, null);
		}
예제 #7
0
		/// <summary>
		/// Maps a STEP float to .Net System.Double
		/// </summary>
		/// <param name="pi"></param>
		/// <param name="obj"></param>
		/// <param name="sv"></param>
		private void mapFloat(PropertyInfo pi, ref Object obj, StepValue sv){
			if(pi == null)
				throw new ArgumentNullException("pi");
			if(obj == null)
				throw new ArgumentNullException("obj");
			if(!(sv.Value is double))
				throw new ArgumentException("sv.Value cannot be cast to a double");
			pi.SetValue(obj, (double)sv.Value, null);
		}
예제 #8
0
		public void AssertNestedObject(string expectedName, int expectedNumberOfProperties, StepValue actual){
			Assert.IsNotNull(actual);
			Assert.IsNotNull(actual.Value);
			Assert.AreEqual(StepToken.StartEntity, actual.Token);
			Assert.AreEqual(typeof(StepDataObject), actual.ValueType);
			
			StepDataObject sdo = actual.Value as StepDataObject;
			Assert.IsNotNull(sdo);
			AssertObject(expectedName, expectedNumberOfProperties, sdo);
		}
예제 #9
0
		public void AssertNull(StepValue actual){
			AssertStepValue(StepToken.Null, null, null, actual);
		}
예제 #10
0
		public void AssertArray(int expectedCount, StepValue actual){
			AssertArray(actual);
			List<StepValue> array = actual.Value as List<StepValue>;
			Assert.IsNotNull(array);
			Assert.AreEqual(expectedCount, array.Count);
		}
예제 #11
0
		public void AssertLineReference(int expectedLineReference, StepValue actual){
			AssertStepValue(StepToken.LineReference, typeof(int), expectedLineReference, actual);
		}
예제 #12
0
		/// <summary>
		/// Asserts a StepValue is an array and is not null, but does not assert anything of the array contents
		/// </summary>
		/// <param name="actual"></param>
		public void AssertArray(StepValue actual){
			Assert.IsNotNull(actual);
			Assert.AreEqual(StepToken.StartArray, actual.Token);
			Assert.AreEqual(typeof(List<StepValue>), actual.ValueType);
			Assert.IsNotNull(actual.Value);
		}
예제 #13
0
		public void AssertDate(string expectedDate, StepValue actual){
			AssertStepValue(StepToken.Date, typeof(DateTime), DateTime.Parse(expectedDate), actual);
		}
예제 #14
0
		public void AssertString(string expectedValue, StepValue actual){
			AssertStepValue(StepToken.String, typeof(string), expectedValue, actual);
		}
예제 #15
0
		/// <summary>
		/// Maps a STEP entity to a .Net object
		/// </summary>
		/// <param name="pi"></param>
		/// <param name="obj"></param>
		/// <param name="sv"></param>
		private void mapObject(PropertyInfo pi, ref Object obj, StepValue sv){
			if(pi == null)
				throw new ArgumentNullException("pi");
			if(obj == null)
				throw new ArgumentNullException("obj");
			if(sv.Value == null)
				throw new ArgumentNullException("sv.Value");
			StepDataObject sdo = sv.Value as StepDataObject;
			if(sdo == null)
				throw new ArgumentException("sv.Value is not of type StepDataObject");
			Object nestedObj = bindObject(-1, sdo);
			
			//as a quirk of the automatically generated schema
			//nested properties are wrapped in an intermediate class.
			Object wrappingObj = Activator.CreateInstance(pi.PropertyType);
			logger.Debug("Attempting to find \"Item\" property for type of " + pi.PropertyType);
			PropertyInfo wrappingProp = pi.PropertyType.GetProperty("Item", BindingFlags.DeclaredOnly | 
                                                  BindingFlags.Public |
                                                  BindingFlags.Instance);
			if(wrappingProp == null)
				throw new StepBindingException("Could not find a suitable property in the wrapping class around a nested object");
			wrappingProp.SetValue(wrappingObj, nestedObj, null);
			
			//now insert the wrapping object
			pi.SetValue(obj, wrappingObj, null);
		}
예제 #16
0
		public void AssertFloat(double expectedValue, StepValue actual){
			AssertStepValue(StepToken.Float, typeof(double), expectedValue, actual);
		}
예제 #17
0
		/// <summary>
		/// Maps a STEP string to a .Net System.String
		/// </summary>
		/// <param name="pi"></param>
		/// <param name="obj"></param>
		/// <param name="sv"></param>
		private void mapString(PropertyInfo pi, ref Object obj, StepValue sv){
			if(pi == null)
				throw new ArgumentNullException("pi");
			if(obj == null)
				throw new ArgumentNullException("obj");
			if(sv.Value == null)
				throw new ArgumentNullException("sv.Value");
			if(!(sv.Value is string))
				throw new ArgumentException("sv.Value is not of type String");
			pi.SetValue(obj, (string)sv.Value, null);
		}
예제 #18
0
		public void AssertEnum(string expectedValue, StepValue actual){
			AssertStepValue(StepToken.Enumeration, typeof(string), expectedValue, actual);
		}
예제 #19
0
		/// <summary>
		/// Maps a STEP integer to a .Net System.Int32
		/// </summary>
		/// <param name="pi"></param>
		/// <param name="obj"></param>
		/// <param name="sv"></param>
		private void mapInteger(PropertyInfo pi, ref Object obj, StepValue sv){
			if(pi == null)
				throw new ArgumentNullException("pi");
			if(obj == null)
				throw new ArgumentNullException("obj");
			if(!(sv.Value is int))
				throw new ArgumentException("sv.Value cannot be cast to an int");
			pi.SetValue(obj, (int)sv.Value, null);
		}
예제 #20
0
		public void AssertBoolean(bool expectedValue, StepValue actual){
			AssertStepValue(StepToken.Boolean, typeof(bool), expectedValue, actual);
		}
예제 #21
0
		/// <summary>
		/// Maps a STEP array to a .Net array.
		/// </summary>
		/// <remarks>The .Net schema often wraps arrays in intermediate objects, and this case is dealt with by the function</remarks>
		/// <param name="pi">The property of the entity which holds an array</param>
		/// <param name="obj">The entity as currently constructed</param>
		/// <param name="sv">The value to be entered into the object</param>
		/// <param name="stepId">the number of the object as given in the step format being deserialized</param>
		private void mapArray(PropertyInfo pi, ref Object obj, StepValue sv, int stepId){
			if(pi == null)
				throw new ArgumentNullException("pi");
			if(obj == null)
				throw new ArgumentNullException("obj");
			if(sv.Value == null)
				throw new ArgumentNullException("sv.Value");
			
			IList<StepValue> stepValues = sv.Value as IList<StepValue>;
			if(stepValues == null)
				throw new StepBindingException("sv.Value cannot be converted to List<StepValues>");
			if(stepValues.Count < 1)
				return;
			logger.Debug("Number of items in array : " + stepValues.Count);
			
			
			PropertyInfo arrayProperty = findArrayProperty( pi );
			if(arrayProperty == null)
				throw new StepBindingException(String.Format(CultureInfo.InvariantCulture,
				                                                "Cannot find a suitable property in the array wrapping type {0} which would hold an array",
				                                                pi.PropertyType.Name));
			
			Object arrayWrappingObject;
			//check incase there is an intermediate type
			if(arrayProperty.Equals(pi))
				arrayWrappingObject = obj;
			else
				arrayWrappingObject = System.Activator.CreateInstance(pi.PropertyType);
			
			//get the array, or create it if it doesn't already exist
			Array array = (Array)arrayProperty.GetValue(arrayWrappingObject, null);
			if(array == null)
				array = Array.CreateInstance( arrayProperty.PropertyType.GetElementType(), stepValues.Count );
			if(array.Length != stepValues.Count)
				throw new StepBindingException(String.Format(CultureInfo.InvariantCulture,
				                                                "The array length, {0}, is not long enough to hold all the properties, {1}, being mapped to it",
				                                                array.Length,
				                                                stepValues.Count));
			
			//iterate through each item and add it to the array.
			for(int arrayIndex = 0; arrayIndex < stepValues.Count; arrayIndex++){
				StepValue svInner = stepValues[arrayIndex];
				
				//debugging
				logger.Debug("Mapping property in array. Index : " + arrayIndex);
				logger.Debug("Property being assigned to in the .Net object : "       + arrayProperty.Name);
				logger.Debug("The Type of values held by that .Net property : " + arrayProperty.PropertyType.GetElementType().Name);
				logger.Debug("STEP token     : "     + svInner.Token);
				logger.Debug("STEP value     : "     + svInner.Value);
				logger.Debug("STEP valueType : " + svInner.ValueType);
				
				switch(svInner.Token){
					case StepToken.String:
					case StepToken.Float:
					case StepToken.Integer:
						if(array.GetType().GetElementType().Equals( svInner.ValueType ))
							array.SetValue(svInner.Value, arrayIndex);
						else{
							//we need to convert/cast the type, and need the conversion operator of the target type to assist with this
							MethodInfo mi = array.GetType().GetElementType().GetMethod(
								"op_Implicit",
								(BindingFlags.Public | BindingFlags.Static),
								null,
								new Type[] { svInner.ValueType },
								new ParameterModifier[0]
							);
							if(mi == null)
								throw new NotImplementedException(String.Format(CultureInfo.InvariantCulture,
								                                                "Cannot convert from a {0} to a type of {1}, as there is no static implicit cast method present on the type we're casting to",
								                                                svInner.ValueType.Name,
								                                                array.GetType().GetElementType().Name));
							Object parsedValue = mi.Invoke(null, BindingFlags.InvokeMethod | (BindingFlags.Public | BindingFlags.Static), null, new object[] { svInner.Value }, CultureInfo.InvariantCulture);
							if(parsedValue == null)
								throw new StepBindingException(String.Format(CultureInfo.InvariantCulture,
								                                                "Was unable to invoke the conversion operator to convert the value {0}, a type of {1}, to the type {2}",
								                                                svInner.Value.ToString(),
								                                                svInner.ValueType.Name,
								                                                array.GetType().GetElementType().Name));
							array.SetValue(parsedValue, arrayIndex);
						}
						continue;
					case StepToken.StartEntity:
						Object nestedObj = bindObject(-1, svInner.Value as StepDataObject );
						array.SetValue(nestedObj, arrayIndex);
						continue;
					case StepToken.LineReference:
						storeLineReference(pi, ref obj, stepId, svInner, arrayIndex);
						continue;
					default:
						throw new NotImplementedException(svInner.Token + " is not yet implemented in mapArray");
				}
			}
			
			//now add the array to the array wrapping object
			arrayProperty.SetValue(arrayWrappingObject, array, null);
			
			//if there is a wrapping object, then we need to insert that into the object.
			if(!arrayProperty.Equals(pi)){
				pi.SetValue(obj, arrayWrappingObject, null);
			}
		}
예제 #22
0
		public void AssertOverridden(StepValue actual){
			AssertStepValue(StepToken.Overridden, null, null, actual);
		}
예제 #23
0
        public static StepValue CreateArray(params StepValue[] values)
        {
            IList <StepValue> valueList = new List <StepValue>(values);

            return(StepValue.CreateArray(valueList));
        }
예제 #24
0
		public List<StepValue> getArray(StepValue stepValueContainingArray){
			return stepValueContainingArray.Value as List<StepValue>;
		}