示例#1
0
        /// <summary>
        /// Generate a sequence of <c>LEFT OUTER JOIN</c> clauses for the given associations.
        /// </summary>
        protected JoinFragment MergeOuterJoins(IList <OuterJoinableAssociation> associations)
        {
            JoinFragment outerjoin = Dialect.CreateOuterJoinFragment();

            OuterJoinableAssociation last = null;

            foreach (OuterJoinableAssociation oj in associations)
            {
                if (last != null && last.IsManyToManyWith(oj))
                {
                    oj.AddManyToManyJoin(outerjoin, (IQueryableCollection)last.Joinable);
                }
                else
                {
                    oj.AddJoins(outerjoin);
                    // NH Different behavior : NH1179 and NH1293
                    // Apply filters in Many-To-One association
                    if (enabledFiltersForManyToOne.Count > 0)
                    {
                        string manyToOneFilterFragment = oj.Joinable.FilterFragment(oj.RHSAlias, enabledFiltersForManyToOne);
                        bool   joinClauseDoesNotContainsFilterAlready =
                            outerjoin.ToFromFragmentString.IndexOfCaseInsensitive(manyToOneFilterFragment) == -1;
                        if (joinClauseDoesNotContainsFilterAlready)
                        {
                            outerjoin.AddCondition(manyToOneFilterFragment);
                        }
                    }
                }
                last = oj;
            }

            return(outerjoin);
        }
示例#2
0
        /// <summary>
        /// Generate a sequence of <c>LEFT OUTER JOIN</c> clauses for the given associations.
        /// </summary>
        protected JoinFragment MergeOuterJoins(IList <OuterJoinableAssociation> associations)
        {
            JoinFragment outerjoin = Dialect.CreateOuterJoinFragment();

            var sortedAssociations        = GetSortedAssociations(associations);
            OuterJoinableAssociation last = null;

            foreach (OuterJoinableAssociation oj in sortedAssociations)
            {
                if (last != null && last.IsManyToManyWith(oj))
                {
                    oj.AddManyToManyJoin(outerjoin, (IQueryableCollection)last.Joinable);
                }
                else
                {
                    // NH Different behavior : NH1179 and NH1293
                    // Apply filters for entity joins and Many-To-One associations
                    SqlString filter = null;
                    var       enabledFiltersForJoin = oj.ForceFilter ? enabledFilters : enabledFiltersForManyToOne;
                    if (oj.ForceFilter || enabledFiltersForJoin.Count > 0)
                    {
                        string manyToOneFilterFragment = oj.Joinable.FilterFragment(oj.RHSAlias, enabledFiltersForJoin);
                        bool   joinClauseDoesNotContainsFilterAlready =
                            oj.On?.IndexOfCaseInsensitive(manyToOneFilterFragment) == -1;
                        if (joinClauseDoesNotContainsFilterAlready)
                        {
                            filter = new SqlString(manyToOneFilterFragment);
                        }
                    }

                    if (TableGroupJoinHelper.ProcessAsTableGroupJoin(new[] { oj }, new[] { oj.On, filter }, true, outerjoin, alias => true, factory))
                    {
                        continue;
                    }

                    oj.AddJoins(outerjoin);

                    // Ensure that the join condition is added to the join, not the where clause.
                    // Adding the condition to the where clause causes left joins to become inner joins.
                    if (SqlStringHelper.IsNotEmpty(filter))
                    {
                        outerjoin.AddFromFragmentString(filter);
                    }
                }
                last = oj;
            }

            return(outerjoin);
        }
示例#3
0
        /// <summary>
        /// Get the order by string required for collection fetching
        /// </summary>
        protected SqlString OrderBy(IList <OuterJoinableAssociation> associations)
        {
            SqlStringBuilder buf = new SqlStringBuilder();

            OuterJoinableAssociation last = null;

            foreach (OuterJoinableAssociation oj in associations)
            {
                if (oj.JoinType == JoinType.LeftOuterJoin)
                {
                    if (oj.Joinable.IsCollection)
                    {
                        IQueryableCollection queryableCollection = (IQueryableCollection)oj.Joinable;
                        if (queryableCollection.HasOrdering)
                        {
                            string orderByString = queryableCollection.GetSQLOrderByString(oj.RHSAlias);
                            buf.Add(orderByString).Add(StringHelper.CommaSpace);
                        }
                    }
                    else
                    {
                        // it might still need to apply a collection ordering based on a
                        // many-to-many defined order-by...
                        if (last != null && last.Joinable.IsCollection)
                        {
                            IQueryableCollection queryableCollection = (IQueryableCollection)last.Joinable;
                            if (queryableCollection.IsManyToMany && last.IsManyToManyWith(oj))
                            {
                                if (queryableCollection.HasManyToManyOrdering)
                                {
                                    string orderByString = queryableCollection.GetManyToManyOrderByString(oj.RHSAlias);
                                    buf.Add(orderByString).Add(StringHelper.CommaSpace);
                                }
                            }
                        }
                    }
                }
                last = oj;
            }

            if (buf.Count > 0)
            {
                buf.RemoveAt(buf.Count - 1);
            }

            return(buf.ToSqlString());
        }
示例#4
0
        /// <summary>
        /// Generate a sequence of <c>LEFT OUTER JOIN</c> clauses for the given associations.
        /// </summary>
        protected JoinFragment MergeOuterJoins(IList <OuterJoinableAssociation> associations)
        {
            IList <OuterJoinableAssociation> sortedAssociations = new List <OuterJoinableAssociation>();

            var indices = GetTopologicalSortOrder(_dependentAliases);

            for (int index = indices.Length - 1; index >= 0; index--)
            {
                sortedAssociations.Add(associations[indices[index]]);
            }

            JoinFragment outerjoin = Dialect.CreateOuterJoinFragment();

            OuterJoinableAssociation last = null;

            foreach (OuterJoinableAssociation oj in sortedAssociations)
            {
                if (last != null && last.IsManyToManyWith(oj))
                {
                    oj.AddManyToManyJoin(outerjoin, (IQueryableCollection)last.Joinable);
                }
                else
                {
                    oj.AddJoins(outerjoin);
                    // NH Different behavior : NH1179 and NH1293
                    // Apply filters in Many-To-One association
                    if (enabledFiltersForManyToOne.Count > 0)
                    {
                        string manyToOneFilterFragment = oj.Joinable.FilterFragment(oj.RHSAlias, enabledFiltersForManyToOne);
                        bool   joinClauseDoesNotContainsFilterAlready =
                            outerjoin.ToFromFragmentString.IndexOfCaseInsensitive(manyToOneFilterFragment) == -1;
                        if (joinClauseDoesNotContainsFilterAlready)
                        {
                            // Ensure that the join condition is added to the join, not the where clause.
                            // Adding the condition to the where clause causes left joins to become inner joins.
                            outerjoin.AddFromFragmentString(new SqlString(manyToOneFilterFragment));
                        }
                    }
                }
                last = oj;
            }

            return(outerjoin);
        }