private static List <Expression> BuildExtractionOfChildModelSetter([NotNull] Type currNodeType, [NotNull] Expression currNodeExpression, [NotNull] Expression valueToSetExpression, [NotNull, ItemNotNull] string[] pathParts) { var statements = new List <Expression>(); for (var partIndex = 0; partIndex < pathParts.Length; ++partIndex) { var name = TemplateDescriptionHelper.GetPathPartName(pathParts[partIndex]); var newNodeType = currNodeType.GetProperty(name)?.PropertyType; currNodeType = newNodeType ?? throw new ObjectPropertyExtractionException($"Type '{currNodeType}' has no property '{name}'"); currNodeExpression = Expression.Property(currNodeExpression, name); if (TemplateDescriptionHelper.IsCollectionAccessPathPart(pathParts[partIndex])) { List <Expression> statementsToAdd; (currNodeExpression, currNodeType, statementsToAdd) = BuildExpandingOfCollectionAccessPart(currNodeExpression, currNodeType, pathParts[partIndex]); statements.AddRange(statementsToAdd); } else if (TemplateDescriptionHelper.IsArrayPathPart(pathParts[partIndex])) { var statementsToAdd = BuildExpandingOfArrayPart(currNodeExpression, currNodeType, valueToSetExpression, pathParts.Skip(partIndex + 1).ToArray()); statements.AddRange(statementsToAdd); return(statements); } else if (!TypeCheckingHelper.IsNullable(currNodeType) && partIndex != pathParts.Length - 1) { statements.Add(ExpressionPrimitives.CreateValueInitStatement(currNodeExpression, currNodeType)); } } statements.Add(ExpressionPrimitives.AssignWithTypeCheckings(currNodeExpression, currNodeType, valueToSetExpression)); return(statements); }
private static T CastWithTypeCheckings <T>([CanBeNull] object from) { if (from is T res) { return(res); } if (from == null && (!typeof(T).IsValueType || TypeCheckingHelper.IsNullable(typeof(T)))) { return(default);