/// <summary> /// Evaluates canonical function. /// </summary> /// <param name="resultType">The function result type.</param> /// <param name="classType">Type of the class.</param> /// <param name="methodName">Name of the method.</param> /// <param name="arguments">The arguments for the function call.</param> /// <returns> /// Query value which is the result of the function evaluation. /// </returns> private QueryValue EvaluateMethod(QueryScalarType resultType, Type classType, string methodName, params QueryScalarValue[] arguments) { var argsTypes = arguments.Select(a => ((IQueryClrType)a.Type).ClrType).ToArray(); var method = classType.GetMethod(methodName, argsTypes); if (method == null) { argsTypes = argsTypes.Skip(1).ToArray(); method = classType.GetMethod(methodName, argsTypes, true, false); } ExceptionUtilities.CheckObjectNotNull(method, "Could not find instance or static method '{0}' on type '{1}'", methodName, classType.FullName); object[] argsValues = arguments.Select(a => a.Value).ToArray(); object value = null; if (method.IsStatic) { value = method.Invoke(null, argsValues); } else if (argsValues[0] != null) { // null needs to be propagated for instance methods, otherwise this will fail value = method.Invoke(argsValues[0], argsValues.Skip(1).ToArray()); } return(resultType.CreateValue(value)); }
private QueryValue BuildCollectionQueryValue(string propertyPath, QueryCollectionType queryCollectionType, EntitySetDataRow row) { QueryScalarType scalarElementDataType = queryCollectionType.ElementType as QueryScalarType; QueryComplexType complexTypeElementDataType = queryCollectionType.ElementType as QueryComplexType; List <QueryValue> queryValues = new List <QueryValue>(); if (scalarElementDataType != null) { int i = 0; while (row.PropertyPaths.Any(pp => pp == propertyPath + i)) { var value = row[propertyPath + i]; queryValues.Add(scalarElementDataType.CreateValue(value)); i++; } } else { ExceptionUtilities.CheckObjectNotNull(complexTypeElementDataType, "PropertyPath '{0}' is an invalid type '{1}'", propertyPath, queryCollectionType.ElementType); int i = 0; while (row.PropertyPaths.Where(pp => pp.StartsWith(propertyPath + i, StringComparison.Ordinal)).Count() > 0) { QueryStructuralValue complexChildInstance = complexTypeElementDataType.CreateNewInstance(); this.BuildStructuralPropertiesQueryValue(complexChildInstance, propertyPath + i + ".", complexTypeElementDataType.ComplexType.Properties, complexTypeElementDataType.Properties, row); queryValues.Add(complexChildInstance); i++; } } return(queryCollectionType.CreateCollectionWithValues(queryValues.ToArray())); }
/// <summary> /// Compares the given values of the given type, and throws a DataComparisonException or AssertionFailedException if values don't match /// </summary> /// <param name="type">The expected type</param> /// <param name="expected">The expected value</param> /// <param name="actual">The actual value</param> /// <param name="assert">The assertion handler to use</param> protected virtual void Compare(QueryScalarType type, object expected, object actual, AssertionHandler assert) { ExceptionUtilities.CheckArgumentNotNull(type, "type"); ExceptionUtilities.CheckArgumentNotNull(assert, "assert"); if (expected == type.NullValue.Value) { assert.IsNull(actual, "Primitive value unexpectedly non-null"); } else { assert.IsNotNull(actual, "Primitive value unexpectedly null"); assert.AreEqual(expected.GetType(), actual.GetType(), EqualityComparer <Type> .Default, "Types did not match"); var comparer = new DelegateBasedEqualityComparer <QueryScalarValue>((v1, v2) => v1.Type.EvaluationStrategy.Compare(v1, v2) == 0); assert.AreEqual(type.CreateValue(expected), type.CreateValue(actual), comparer, "Primitive value did not match"); } }
/// <summary> /// Factory method to create the <see cref="QueryConstantExpression"/>. /// </summary> /// <param name="value">Value of the expression.</param> /// <param name="valueType">Type of the expression.</param> /// <returns>The <see cref="QueryConstantExpression"/> with the provided arguments.</returns> public static QueryConstantExpression Constant(object value, QueryScalarType valueType) { ExceptionUtilities.CheckArgumentNotNull(valueType, "valueType"); if (value == null) { ExceptionUtilities.Assert(!valueType.IsUnresolved, "When value is null type cannot be unresolved."); } return(Constant(valueType.CreateValue(value))); }
/// <summary> /// Evaluates the property. /// </summary> /// <param name="resultType">Type of the result.</param> /// <param name="propertyName">Name of the property.</param> /// <param name="instance">The instance.</param> /// <returns> /// Query value which is the result of the function evaluation. /// </returns> private QueryValue EvaluateProperty(QueryScalarType resultType, string propertyName, QueryScalarValue instance) { if (instance.Value == null) { // TODO: evaluation error? return(resultType.NullValue); } var type = instance.Value.GetType(); var propertyInfo = type.GetProperty(propertyName); ExceptionUtilities.CheckObjectNotNull(propertyInfo, "Could not find property named '{0}' on '{1}'", propertyName, instance.Value); var value = propertyInfo.GetValue(instance.Value, null); return(resultType.CreateValue(value)); }
private void BuildStructuralPropertiesQueryValue(QueryStructuralValue instance, string propertyPath, IList <MemberProperty> properties, IList <QueryProperty> queryProperties, EntitySetDataRow row) { ExceptionUtilities.Assert(properties.Count == queryProperties.Count, "QueryProperties '{0}' and MemberProperties '{1}' are not the same number!", CreateQueryPropertyList(queryProperties), CreateMemberPropertyList(properties)); // TODO: Some Taupo framework pieces skip over StreamDataType properties foreach (MemberProperty childProperty in properties.Where(p => !(p.PropertyType is StreamDataType))) { string childPropertyPath = propertyPath + childProperty.Name; List <QueryProperty> childQueryProperties = queryProperties.Where(p => p.Name == childProperty.Name).ToList(); ExceptionUtilities.Assert(childQueryProperties.Count == 1, "Could not find query property based on MemberProperty Name '{0}' in list of query properties '{1}'", childProperty.Name, CreateQueryPropertyList(childQueryProperties)); QueryProperty childQueryProperty = childQueryProperties.First(); QueryCollectionType childCollectionDataType = childQueryProperty.PropertyType as QueryCollectionType; QueryScalarType childScalarType = childQueryProperty.PropertyType as QueryScalarType; QueryComplexType childComplexType = childQueryProperty.PropertyType as QueryComplexType; if (childCollectionDataType != null) { instance.SetValue(childProperty.Name, this.BuildCollectionQueryValue(childPropertyPath + ".", childCollectionDataType, row)); } else if (childScalarType != null) { var value = row[childPropertyPath]; var queryValue = childScalarType.CreateValue(value); instance.SetValue(childQueryProperty.Name, queryValue); } else { ExceptionUtilities.CheckObjectNotNull(childComplexType, "Unknown type '{0}'", childProperty.PropertyType); // If a complex type instance is null in the datarow, we will create a QueryStructuralValue indicating null and set it on the instance. if (row.PropertyPaths.Contains(childPropertyPath) && row[childPropertyPath] == null) { instance.SetValue(childProperty.Name, new QueryStructuralValue(childComplexType, true, null, childComplexType.EvaluationStrategy)); } else { QueryStructuralValue childInstance = childComplexType.CreateNewInstance(); this.BuildStructuralPropertiesQueryValue(childInstance, childPropertyPath + ".", childComplexType.ComplexType.Properties, childComplexType.Properties, row); instance.SetValue(childProperty.Name, childInstance); } } } }
private void UpdateRootScalarBag(QueryCollectionValue instance, IEnumerable <NamedValue> namedValues, QueryScalarType scalarElementDataType) { int i = 0; var scalarCollection = new List <QueryValue>(); List <NamedValue> scalarItemNamedValues = namedValues.Where(pp => pp.Name == i.ToString(CultureInfo.InvariantCulture)).ToList(); while (scalarItemNamedValues.Any()) { ExceptionUtilities.Assert(scalarItemNamedValues.Count() < 2, "Should not get more than one value for a scalar Bag item for path '{0}'", i.ToString(CultureInfo.InvariantCulture)); var value = scalarItemNamedValues.Single(); scalarCollection.Add(scalarElementDataType.CreateValue(value.Value)); this.unusedNamedValuePaths.Remove(value.Name); i++; scalarItemNamedValues = namedValues.Where(pp => pp.Name == i.ToString(CultureInfo.InvariantCulture)).ToList(); } if (scalarCollection.Any()) { this.SetCollectionValue(instance, scalarCollection); } }
private void UpdateScalarBag(QueryStructuralValue instance, QueryProperty memberProperty, string propertyPath, IEnumerable <NamedValue> namedValues, QueryScalarType scalarElementDataType) { int i = 0; var scalarCollection = new List <QueryValue>(); List <NamedValue> scalarItemNamedValues = namedValues.Where(pp => pp.Name == propertyPath + "." + i).ToList(); while (scalarItemNamedValues.Any()) { ExceptionUtilities.Assert(scalarItemNamedValues.Count() < 2, "Should not get more than one value for a scalar Bag item for path '{0}'", propertyPath + "." + i); var value = scalarItemNamedValues.Single(); scalarCollection.Add(scalarElementDataType.CreateValue(value.Value)); this.unusedNamedValuePaths.Remove(value.Name); i++; scalarItemNamedValues = namedValues.Where(pp => pp.Name == propertyPath + "." + i).ToList(); } if (scalarCollection.Any()) { this.SetCollectionProperty(instance, memberProperty, scalarCollection); } }
private QueryValue VisitScalar(QueryScalarType queryScalarType) { var scalarResult = this.ResultFragmentStack.Pop(); return(queryScalarType.CreateValue(scalarResult)); }