// 获取 LEFT JOIN / INNER JOIN 子句关联表的的别名
        private void GetLfInJoinAlias(DbExpression exp, TableAliasCache aliases)
        {
            Type   type = exp.Expressions[0].Type.GetGenericArguments()[0];
            string name = TypeRuntimeInfoCache.GetRuntimeInfo(type).TableName;

            // on a.Name equals b.Name 或 on new{ Name = a.Name,Id=a.Id } equals new { Name = b.Name,Id=b.Id }
            LambdaExpression left  = exp.Expressions[1] as LambdaExpression;
            LambdaExpression right = exp.Expressions[2] as LambdaExpression;
            NewExpression    body1 = left.Body as NewExpression;

            if (body1 == null)
            {
                aliases.GetTableAlias(exp.Expressions[1]);
                string alias = aliases.GetTableAlias(exp.Expressions[2]);

                // 记录显示指定的LEFT JOIN 表别名
                aliases.AddOrUpdateJoinTableAlias(name, alias);
            }
            else
            {
                NewExpression body2 = right.Body as NewExpression;
                for (int index = 0; index < body1.Arguments.Count; ++index)
                {
                    aliases.GetTableAlias(body1.Arguments[index]);
                    string alias = aliases.GetTableAlias(body2.Arguments[index]);

                    // 记录显示指定的LEFT JOIN 表别名
                    aliases.AddOrUpdateJoinTableAlias(name, alias);
                }
            }
        }
Exemple #2
0
        /// <summary>
        /// 追加列名
        /// </summary>
        /// <param name="aliases">表别名</param>
        /// <param name="expression">列名表达式</param>
        /// <returns>返回解析到的表别名</returns>
        public string AppendMember(TableAliasCache aliases, Expression expression)
        {
            Expression       exp = expression;
            LambdaExpression lambdaExpression = exp as LambdaExpression;

            if (lambdaExpression != null)
            {
                exp = lambdaExpression.Body;
            }

            MemberExpression memExp = exp as MemberExpression;

            if (expression.NodeType == ExpressionType.Constant || memExp.Expression.NodeType == ExpressionType.Constant)
            {
                PartialVisitor visitor = new PartialVisitor();
                var            eval    = visitor.Eval(memExp ?? expression);
                string         value   = eval.NodeType == ExpressionType.Constant
                    ? ExpressionVisitorBase.GetSqlValue((eval as ConstantExpression).Value)
                    : string.Empty;
                _builder.Append(value);

                return(value);
            }
            else
            {
                string alias = aliases == null ? null : aliases.GetTableAlias(memExp);
                this.AppendMember(alias, memExp.Member.Name);
                return(alias);
            }
        }
 /// <summary>
 /// 初始化 <see cref="OrderByExpressionVisitor"/> 类的新实例
 /// </summary>
 public OrderByExpressionVisitor(DbQueryProviderBase provider, TableAliasCache aliases, List <DbExpression> qOrder, DbExpression groupBy = null, string alias = null)
     : base(provider, aliases, null, false)
 {
     _qOrder  = qOrder;
     _aliases = aliases;
     _groupBy = groupBy;
     _alias   = alias;
 }
        // 获取 CROSS JOIN 子句关联表的的别名
        private void GetCrossJoinAlias(DbExpression exp, TableAliasCache aliases)
        {
            LambdaExpression lambdaExp = exp.Expressions[1] as LambdaExpression;

            for (int index = 0; index < lambdaExp.Parameters.Count; ++index)
            {
                aliases.GetTableAlias(lambdaExp.Parameters[index]);
            }
        }
Exemple #5
0
 /// <summary>
 /// 初始化 <see cref="StatisExpressionVisitor"/> 类的新实例
 /// </summary>
 public StatisExpressionVisitor(DbQueryProviderBase provider, TableAliasCache aliases, DbExpression statis, DbExpression groupBy = null, string alias = null)
     : base(provider, aliases, statis.Expressions != null ? statis.Expressions[0] : null, false)
 {
     _provider = provider;
     _aliases  = aliases;
     _statis   = statis;
     _groupBy  = groupBy;
     _alias    = alias;
 }
Exemple #6
0
        /// <summary>
        /// 初始化 <see cref="ExpressionVisitorBase"/> 类的新实例
        /// </summary>
        public ExpressionVisitorBase(DbQueryProviderBase provider, TableAliasCache aliases, Expression exp, bool useNominate = true)
        {
            _provider    = provider;
            _aliases     = aliases;
            _navigations = new Dictionary <string, MemberExpression>();

            _expression = exp;
            //var visitor = new PartialVisitor();
            //_expression = useNominate ? visitor.Eval(exp) : exp;
        }
            /// <summary>
            /// 实例化 <see cref="Builder" /> 的新实例
            /// </summary>
            /// <param name="escCharLeft">如 [</param>
            /// <param name="escCharRight">如 ]</param>
            /// <param name="aliases">别名</param>
            public Builder(char escCharLeft, char escCharRight, TableAliasCache aliases)
            {
                _escCharLeft  = escCharLeft;
                _escCharRight = escCharRight;
                _aliases      = aliases;
                _navigations  = new Dictionary <string, MemberExpression>();

                _joinFragment  = new SqlBuilder(escCharLeft, escCharRight);
                _whereFragment = new SqlBuilder(escCharLeft, escCharRight);
            }
        /// <summary>
        /// 初始化 <see cref="ColumnExpressionVisitor"/> 类的新实例
        /// </summary>
        public ColumnExpressionVisitor(DbQueryProviderBase provider, TableAliasCache aliases, DbExpression exp, DbExpression groupBy = null, bool mOnly = false)
            : base(provider, aliases, exp.Expressions != null ? exp.Expressions[0] : null)
        {
            _provider = provider;
            _aliases  = aliases;
            _groupBy  = groupBy;
            _mOnly    = mOnly;

            _columns           = new Dictionary <string, Column>();
            _navDescriptors    = new ColumnNavDescriptorCollection();
            _navDescriptorKeys = new List <string>(10);
        }
        // LEFT OR INNER JOIN
        private void AppendLfInJoin(SqlBuilder builder, DbExpression exp, TableAliasCache aliases)
        {
            // [TableName]
            //var constExp = exp.Expressions[0] as ConstantExpression;
            //constExp.Type.GetGenericArguments()[0]
            //var queryable = constExp.Value as IDbQueryable;
            //var innerExp = queryable.DbExpressions[0];
            //if (innerExp.DbExpressionType != DbExpressionType.GetTable) throw new XfwException("inner expression must be GetTable<T> expression");
            //Type type = (innerExp.Expression as ConstantExpression).Value as Type;

            Type type = exp.Expressions[0].Type.GetGenericArguments()[0];

            builder.Append(' ');
            builder.AppendMember(TypeRuntimeInfoCache.GetRuntimeInfo(type).TableName);

            LambdaExpression left  = exp.Expressions[1] as LambdaExpression;
            LambdaExpression right = exp.Expressions[2] as LambdaExpression;
            NewExpression    body1 = left.Body as NewExpression;
            NewExpression    body2 = right.Body as NewExpression;

            // t0(t1)
            string alias = body1 == null
                ? aliases.GetTableAlias(exp.Expressions[2])
                : aliases.GetTableAlias(body2.Arguments[0]);

            builder.Append(' ');
            builder.Append(alias);
            builder.Append(' ');

            // ON a.Name = b.Name AND a.Id = b.Id
            builder.Append("ON ");

            if (body1 == null)
            {
                builder.AppendMember(aliases, left.Body.ReduceUnary());
                builder.Append(" = ");
                builder.AppendMember(aliases, right.Body.ReduceUnary());
            }
            else
            {
                for (int index = 0; index < body1.Arguments.Count; ++index)
                {
                    builder.AppendMember(aliases, body1.Arguments[index]);
                    builder.Append(" = ");
                    builder.AppendMember(aliases, body2.Arguments[index]);
                    if (index < body1.Arguments.Count - 1)
                    {
                        builder.Append(" AND ");
                    }
                }
            }
        }
        // Cross Join
        private void AppendCrossJoin(SqlBuilder builder, DbExpression exp, TableAliasCache aliases)
        {
            LambdaExpression lambdaExp = exp.Expressions[1] as LambdaExpression;
            Type             type      = lambdaExp.Parameters[1].Type;

            builder.Append(' ');
            builder.AppendMember(TypeRuntimeInfoCache.GetRuntimeInfo(type).TableName);

            string alias = aliases.GetTableAlias(lambdaExp.Parameters[1]);

            builder.Append(' ');
            builder.Append(alias);
            builder.Append(' ');
        }
        /// <summary>
        /// 根据指定表达式取表别名
        /// </summary>
        /// <param name="exp">表达式</param>
        /// <remarks>
        /// t=>t.Id
        /// t.Id
        /// </remarks>
        public string GetTableAlias(Expression exp)
        {
            // p=>p.p
            // p=>p.Id
            // p=>p.t.Id
            // p.Id
            // p.t.Id
            // p.t
            // <>h__TransparentIdentifier0.p.Id
            XfwException.Check.NotNull(exp, "exp");
            string key = TableAliasCache.GetTableAliasKey(exp);

            return(this.GetTableAlias(key));
        }
        private static string GetTableAliasKey(Expression exp)
        {
            if (exp == null)
            {
                return(null);
            }

            Expression expression = exp;

            //c
            if (exp.NodeType == ExpressionType.Constant)
            {
                return(null);
            }

            // p
            ParameterExpression paramExp = expression as ParameterExpression;

            if (paramExp != null)
            {
                return(paramExp.Name);
            }

            // a=>a.Id
            LambdaExpression lambdaExp = expression as LambdaExpression;

            if (lambdaExp != null)
            {
                expression = lambdaExp.Body.ReduceUnary();
            }

            // a.Id
            // t.a
            // t.t.a
            // t.a.Id
            MemberExpression memExp = expression as MemberExpression;

            if (memExp == null)
            {
                return(TableAliasCache.GetTableAliasKey(expression));
            }

            if (memExp.IsVisitable())
            {
                return(TableAliasCache.GetTableAliasKey(memExp.Expression));
            }

            return(memExp.Member.Name);
        }
        // 获取 JOIN 子句关联表的的别名
        protected TableAliasCache PrepareAlias <T>(DbQueryableInfo_Select <T> query)
        {
            TableAliasCache aliases = new TableAliasCache((query.Join != null ? query.Join.Count : 0) + 1);

            foreach (DbExpression exp in query.Join)
            {
                // [INNER/LEFT JOIN]
                if (exp.DbExpressionType == DbExpressionType.GroupJoin || exp.DbExpressionType == DbExpressionType.Join)
                {
                    this.GetLfInJoinAlias(exp, aliases);
                }
                else if (exp.DbExpressionType == DbExpressionType.SelectMany)
                {
                    this.GetCrossJoinAlias(exp, aliases);
                }
            }

            return(aliases);
        }
 /// <summary>
 /// 实例化 <see cref="CommandDefine_Select"/> 类的新实例
 /// </summary>
 /// <param name="escCharLeft">如 [</param>
 /// <param name="escCharRight">如 ]</param>
 /// <param name="aliases">别名</param>
 public CommandDefine_Select(char escCharLeft, char escCharRight, TableAliasCache aliases)
     : base(string.Empty, null, System.Data.CommandType.Text)
 {
     _builder = new Builder(escCharLeft, escCharRight, aliases);
 }
 /// <summary>
 /// 初始化 <see cref="HavingExpressionVisitor"/> 类的新实例
 /// </summary>
 public HavingExpressionVisitor(DbQueryProviderBase provider, TableAliasCache aliases, DbExpression having, DbExpression groupBy)
     : base(provider, aliases, having.Expressions != null ? having.Expressions[0] : null)
 {
     _groupBy = groupBy;
     _aliases = aliases;
 }
 /// <summary>
 /// 初始化 <see cref="WhereExpressionVisitor"/> 类的新实例
 /// </summary>
 public WhereExpressionVisitor(DbQueryProviderBase provider, TableAliasCache aliases, DbExpression exp)
     : base(provider, aliases, exp.Expressions != null ? exp.Expressions[0] : null)
 {
     _expression = base.Expression;
 }
 /// <summary>
 /// 初始化 <see cref="GroupByExpressionVisitor"/> 类的新实例
 /// </summary>
 public GroupByExpressionVisitor(DbQueryProviderBase provider, TableAliasCache aliases, DbExpression groupBy)
     : base(provider, aliases, groupBy != null ? groupBy.Expressions[0] : null, false)
 {
 }
Exemple #18
0
 /// <summary>
 /// 追加列名
 /// </summary>
 /// <param name="expression">列名表达式</param>
 /// <param name="aliases">表别名</param>
 /// <returns>返回解析到的表别名</returns>
 public Expression AppendMember(Expression expression, TableAliasCache aliases)
 {
     this.AppendMember(aliases, expression);
     return(expression);
 }
 /// <summary>
 /// 初始化 <see cref="UpdateExpressionVisitor"/> 类的新实例
 /// </summary>
 public UpdateExpressionVisitor(DbQueryProviderBase provider, TableAliasCache aliases, Expression exp)
     : base(provider, aliases, exp)
 {
     _provider = provider;
     _aliases  = aliases;
 }
 /// <summary>
 /// 初始化 <see cref="JoinExpressionVisitor"/> 类的新实例
 /// </summary>
 public JoinExpressionVisitor(DbQueryProviderBase provider, TableAliasCache aliases, List <DbExpression> qJoin)
     : base(provider, aliases, null, false)
 {
     _qJoin   = qJoin;
     _aliases = aliases;
 }