예제 #1
0
        public override JoinQueryResult Visit(RootQueryExpression exp)
        {
            Type           type           = exp.ElementType;
            TypeDescriptor typeDescriptor = EntityTypeContainer.GetDescriptor(type);

            string  explicitTableName = exp.ExplicitTable;
            DbTable dbTable           = typeDescriptor.Table;

            if (explicitTableName != null)
            {
                dbTable = new DbTable(explicitTableName, dbTable.Schema);
            }
            string alias = this._queryModel.GenerateUniqueTableAlias(dbTable.Name);

            DbTableSegment tableSeg = CreateTableSegment(dbTable, alias, exp.Lock);

            DbTable            aliasTable = new DbTable(alias);
            ComplexObjectModel model      = typeDescriptor.GenObjectModel(aliasTable);

            //TODO 解析 on 条件表达式
            var          scopeParameters = this._scopeParameters.Clone(this._conditionExpression.Parameters.Last(), model);
            DbExpression condition       = GeneralExpressionParser.Parse(this._conditionExpression, scopeParameters, this._queryModel.ScopeTables);

            DbJoinTableExpression joinTable = new DbJoinTableExpression(this._joinType.AsDbJoinType(), tableSeg, condition);

            JoinQueryResult result = new JoinQueryResult();

            result.ResultModel = model;
            result.JoinTable   = joinTable;

            return(result);
        }
예제 #2
0
        ComplexObjectModel GenComplexObjectModel(ComplexPropertyDescriptor navigationDescriptor, NavigationNode navigationNode, QueryModel queryModel)
        {
            TypeDescriptor navigationTypeDescriptor = EntityTypeContainer.GetDescriptor(navigationDescriptor.PropertyType);

            DbTable           dbTable      = navigationTypeDescriptor.Table;
            DbTableExpression tableExp     = new DbTableExpression(dbTable);
            string            alias        = queryModel.GenerateUniqueTableAlias(dbTable.Name);
            DbTableSegment    joinTableSeg = new DbTableSegment(tableExp, alias, queryModel.FromTable.Table.Lock);

            DbTable            aliasTable            = new DbTable(alias);
            ComplexObjectModel navigationObjectModel = navigationTypeDescriptor.GenObjectModel(aliasTable);

            navigationObjectModel.NullChecking = navigationObjectModel.PrimaryKey;

            PrimitivePropertyDescriptor foreignKeyPropertyDescriptor = navigationDescriptor.ForeignKeyProperty;
            DbExpression          foreignKeyColumn = this.GetPrimitiveMember(foreignKeyPropertyDescriptor.Property);
            DbExpression          joinCondition    = DbExpression.Equal(foreignKeyColumn, navigationObjectModel.PrimaryKey);
            DbJoinTableExpression joinTableExp     = new DbJoinTableExpression(foreignKeyPropertyDescriptor.IsNullable ? DbJoinType.LeftJoin : DbJoinType.InnerJoin, joinTableSeg, joinCondition);

            this.DependentTable.JoinTables.Add(joinTableExp);

            navigationObjectModel.DependentTable = joinTableExp;

            DbExpression condition = this.ParseCondition(navigationNode.Condition, navigationObjectModel, queryModel.ScopeTables);

            //AndWhere的条件放到join条件里去
            joinTableExp.AppendCondition(condition);

            navigationObjectModel.Filter = this.ParseCondition(navigationNode.Filter, navigationObjectModel, queryModel.ScopeTables);

            //queryModel.Filters.Add(navigationObjectModel.Filter);

            return(navigationObjectModel);
        }
예제 #3
0
        ComplexObjectModel GenCollectionElementObjectModel(TypeDescriptor elementTypeDescriptor, NavigationNode navigationNode, QueryModel queryModel)
        {
            DbTable           dbTable      = elementTypeDescriptor.Table;
            DbTableExpression tableExp     = new DbTableExpression(dbTable);
            string            alias        = queryModel.GenerateUniqueTableAlias(dbTable.Name);
            DbTableSegment    joinTableSeg = new DbTableSegment(tableExp, alias, queryModel.FromTable.Table.Lock);

            DbTable            aliasTable         = new DbTable(alias);
            ComplexObjectModel elementObjectModel = elementTypeDescriptor.GenObjectModel(aliasTable);

            elementObjectModel.NullChecking = elementObjectModel.PrimaryKey;

            ComplexPropertyDescriptor navigationDescriptor = elementTypeDescriptor.ComplexPropertyDescriptors.Where(a => a.PropertyType == this.ObjectType).FirstOrDefault();

            if (navigationDescriptor == null)
            {
                throw new ChloeException($"You have to define a navigation property which type is '{this.ObjectType.FullName}' on class '{elementTypeDescriptor.Definition.Type.FullName}'.");
            }

            DbExpression          elementForeignKeyColumn = elementObjectModel.GetPrimitiveMember(navigationDescriptor.ForeignKeyProperty.Property);
            DbExpression          joinCondition           = DbExpression.Equal(this.PrimaryKey, elementForeignKeyColumn);
            DbJoinTableExpression joinTableExp            = new DbJoinTableExpression(DbJoinType.LeftJoin, joinTableSeg, joinCondition);

            this.DependentTable.JoinTables.Add(joinTableExp);

            elementObjectModel.DependentTable = joinTableExp;
            var condition = this.ParseCondition(navigationNode.Condition, elementObjectModel, queryModel.ScopeTables);

            //AndWhere的条件放到join条件里去
            joinTableExp.AppendCondition(condition);

            elementObjectModel.Filter = this.ParseCondition(navigationNode.Filter, elementObjectModel, queryModel.ScopeTables);

            bool orderByPrimaryKeyExists = queryModel.Orderings.Where(a => a.Expression == this.PrimaryKey).Any();

            if (!orderByPrimaryKeyExists)
            {
                //结果集分组
                DbOrdering ordering = new DbOrdering(this.PrimaryKey, DbOrderType.Asc);
                queryModel.Orderings.Add(ordering);
            }

            //queryModel.Filters.Add(elementObjectModel.Filter);

            return(elementObjectModel);
        }
예제 #4
0
        static QueryModel CreateQueryModel(RootQueryExpression rootQueryExp, ScopeParameterDictionary scopeParameters, StringSet scopeTables, Func <string, string> tableAliasGenerator)
        {
            Type entityType = rootQueryExp.ElementType;

            if (entityType.IsAbstract || entityType.IsInterface)
            {
                throw new ArgumentException("The type of input can not be abstract class or interface.");
            }

            QueryModel queryModel = new QueryModel(scopeParameters, scopeTables);

            TypeDescriptor typeDescriptor = EntityTypeContainer.GetDescriptor(entityType);

            DbTable dbTable = typeDescriptor.GenDbTable(rootQueryExp.ExplicitTable);
            string  alias   = null;

            if (tableAliasGenerator != null)
            {
                alias = tableAliasGenerator(dbTable.Name);
            }
            else
            {
                alias = queryModel.GenerateUniqueTableAlias(dbTable.Name);
            }

            queryModel.FromTable = CreateRootTable(dbTable, alias, rootQueryExp.Lock);

            DbTable            aliasTable = new DbTable(alias);
            ComplexObjectModel model      = typeDescriptor.GenObjectModel(aliasTable);

            model.DependentTable = queryModel.FromTable;

            queryModel.ResultModel = model;

            ParseFilters(queryModel, typeDescriptor.Definition.Filters, rootQueryExp.ContextFilters);

            return(queryModel);
        }
예제 #5
0
        static QueryModel CreateQueryModel(Type type, string explicitTableName, LockType lockType, ScopeParameterDictionary scopeParameters, StringSet scopeTables)
        {
            if (type.IsAbstract || type.IsInterface)
                throw new ArgumentException("The type of input can not be abstract class or interface.");

            QueryModel queryModel = new QueryModel(scopeParameters, scopeTables);

            TypeDescriptor typeDescriptor = EntityTypeContainer.GetDescriptor(type);

            DbTable dbTable = typeDescriptor.Table;
            if (explicitTableName != null)
                dbTable = new DbTable(explicitTableName, dbTable.Schema);
            string alias = queryModel.GenerateUniqueTableAlias(dbTable.Name);

            queryModel.FromTable = CreateRootTable(dbTable, alias, lockType);

            DbTable aliasTable = new DbTable(alias);
            ComplexObjectModel model = typeDescriptor.GenObjectModel(aliasTable);
            model.DependentTable = queryModel.FromTable;

            queryModel.ResultModel = model;

            return queryModel;
        }