示例#1
0
 /// <summary>
 /// Default constructor
 /// </summary>
 /// <param name="table">The main table</param>
 /// <param name="principleKeyColumn">The principle key column of the <see cref="Table"/></param>
 /// <param name="referencedTable">The referenced table</param>
 /// <param name="foreignKeyColumn">The foreign key column of the <see cref="ReferencedTable"/></param>
 /// <param name="index">
 /// The index level of the join.
 /// NOTE: If the index is set to zero, then the <see cref="Table"/> is the root table!
 /// </param>
 /// <param name="isRightJoin">
 /// A flag indicating whether we have a foreign key to primary key join (right join) or not.
 /// NOTE: When this is set to <see cref="false"/> a left join is applied (the navigation property of the root type is an <see cref="IEnumerable{T}"/>)!
 /// NOTE: When this is set to <see cref="true"/> a right join is applied (the navigation property of the root type is an object)!
 /// </param>
 public JoinMap(IDbProviderTable table, IDbProviderColumn principleKeyColumn, IDbProviderTable referencedTable, IDbProviderColumn foreignKeyColumn, int index, bool isRightJoin) : base()
 {
     Table = table ?? throw new ArgumentNullException(nameof(table));
     PrincipleKeyColumn = principleKeyColumn ?? throw new ArgumentNullException(nameof(principleKeyColumn));
     ReferencedTable    = referencedTable ?? throw new ArgumentNullException(nameof(referencedTable));
     ForeignKeyColumn   = foreignKeyColumn ?? throw new ArgumentNullException(nameof(foreignKeyColumn));
     Index       = index;
     IsRightJoin = isRightJoin;
 }
        /// <summary>
        /// Performs the required includes on the specified <paramref name="queryable"/>
        /// </summary>
        /// <param name="queryable">The queryable</param>
        /// <param name="initialTable">The initial table</param>
        /// <returns></returns>
        private IQueryable PerformIncludes(IQueryable queryable, IDbProviderTable initialTable)
        {
            // For every join...
            foreach (var join in Joins)
            {
                var joinsPath = ComputePath(join);

                // For every related join...
                foreach (var j in joinsPath)
                {
                    // Get the type of the model
                    var modelType = queryable.GetType().GetGenericArguments()[0];

                    // If it's the first join...
                    if (joinsPath.ElementAt(0) == j)
                    {
                        // Get the navigation property name
                        var navigationPropertyName = CeidDiplomatikiHelpers.GetPluralForm(j.ReferencedTable.TableName);

                        // Get the navigation property
                        var navigationProperty = modelType.GetProperty(navigationPropertyName);

                        // Create the expression
                        var expression = ExpressionHelpers.CreatePropertySelectorExpression(modelType, navigationProperty);

                        // Get the Include<TEntity, TProperty> method
                        var includeMethod = typeof(EntityFrameworkQueryableExtensions).GetMethods().First(x => x.Name == nameof(EntityFrameworkQueryableExtensions.Include) && x.GetParameters()[1].ParameterType != typeof(string));

                        // Set the generic arguments (TEntity and TProperty)
                        includeMethod = includeMethod.MakeGenericMethod(modelType, navigationProperty.PropertyType);

                        // Call the Include method
                        queryable = (IQueryable)includeMethod.Invoke(null, new object[] { queryable, expression });

                        // Continue
                        continue;
                    }

                    queryable = PerformThenInclude(queryable, j);
                }
            }

            // Return the queryable
            return(queryable);
        }