Example #1
0
 /// <inheritdoc/>
 protected override void WriteFragmentForSourceJoin(SqlWriter writer, ISourceFragment source)
 {
     if (source.Join.Value != EJoinType.CrossJoin)
     {
         base.WriteFragmentForSourceJoin(writer, source);
     }
 }
Example #2
0
        private void GenerateForInsertReturnStatement(GenerateContext context,
                                                      BlockFragment block, ISourceFragment target, TemporaryTableFragment temptable)
        {
            var data = (GenerateDataForInsert)context.Data;

            if (data.ReturnMembers.Any())
            {
                if (data.SubUnits != null)
                {
                    target = new InheritFragment(context, data.Table);
                }
                var select = new SelectFragment(context, target);
                select.Members.AddRange(data.ReturnMembers.Select(a => target.GetMember(a.Metadata)));
                if (temptable == null)
                {
                    select.Where = target.JoinCondition(data.CommitObject, data.Table.Keys);
                }
                else
                {
                    var datatable = temptable.Clone();
                    select.AddSource(datatable);
                    target.Join(datatable, data.Table.Keys);
                }
                block.Add(select);
            }
        }
 /// <summary>
 /// 写入数据源连接条件。
 /// </summary>
 /// <param name="writer">语句写入器。</param>
 /// <param name="source">数据源语句。</param>
 protected virtual void WriteFragmentForSourceCondition(SqlWriter writer, ISourceFragment source)
 {
     if (source.Condition != null)
     {
         writer.Write(" ON ");
         source.Condition.WriteSql(writer);
     }
 }
Example #4
0
 /// <summary>
 /// 根据分组检索表达式初始化查询输出语句及输出对象。
 /// </summary>
 /// <param name="context">生成上下文。</param>
 /// <param name="current">所在数据源。</param>
 /// <param name="expression">初始化表达式。</param>
 /// <param name="parent">父级输出对象。</param>
 public void InitialRetrieval(GenerateContext context, ISourceFragment current, DbRetrievalFunctionExpression expression, ComplexOutputInfo parent)
 {
     if (!_InitialRetrievalMethods.TryGetValue(expression.Function, out InitialRetrievalDelegate method))
     {
         throw new NotSupportedException(string.Format(Res.NotSupportedInitialRetrieval, expression.Function));
     }
     method(context, current, expression, parent);
 }
Example #5
0
 /// <summary>
 /// 创值插入值语句。
 /// </summary>
 /// <param name="context">生成上下文。</param>
 /// <param name="target">插入目标语句。</param>
 /// <param name="source">用于插入的提交对象语句块。</param>
 /// <param name="data">插入的数据集合。</param>
 public InsertValueFragment(GenerateContext context, ISourceFragment target, CommitObjectFragment source, IEnumerable data)
     : base(context)
 {
     Target     = target;
     Data       = data;
     Source     = source;
     _KeyValues = new Dictionary <ColumnMetadata, ISqlFragment>();
 }
Example #6
0
        /// <summary>
        /// 创建成员片段。
        /// </summary>
        /// <param name="current">当前数据源片段。</param>
        /// <param name="property">成员CLR属性。</param>
        /// <param name="parameter">创建参数。</param>
        /// <returns>新建成员片段。</returns>
        public static IMemberFragment CreateMember(this ISourceFragment current, MemberInfo property, object parameter)
        {
            var context   = current.Context;
            var generator = context.Generator;
            var newMember = generator.CreateMember(context, current, property, parameter);

            current.Members.Add(newMember);
            return(newMember);
        }
Example #7
0
        /// <summary>
        /// 创建通过主键及值关联的返回数据语句片段。
        /// </summary>
        /// <param name="unit">内容对象。</param>
        /// <param name="target">目标对象。</param>
        /// <returns>语句片段。</returns>
        internal static SelectFragment SelectReturns(this IContentUnit unit, ISourceFragment target)
        {
            var data    = (ContentBase)unit;
            var context = data.GenerateContext;
            var select  = new SelectFragment(context, target);

            select.Members.AddRange(unit.ReturnMembers.Select(a => target.GetMember(a.Metadata)));
            select.Where = target.JoinCondition(data.CommitObject, data.Table.Keys);
            return(select);
        }
Example #8
0
 /// <summary>
 /// 注册指定的表达式关联存储语句片段对象。
 /// </summary>
 /// <param name="expression">关联的表达式。</param>
 /// <param name="source">关联的源对象。</param>
 /// <param name="isforce">是否强制更新关联数据源。</param>
 public void RegisterSource(DbExpression expression, ISourceFragment source, bool isforce = false)
 {
     if (!_RegistedSource.ContainsKey(expression))
     {
         _RegistedSource.Add(expression, source);
     }
     else if (isforce)
     {
         _RegistedSource[expression] = source;
     }
 }
Example #9
0
        /// <summary>
        /// 根据分组检索表达式 Single 初始化查询输出语句及输出对象。
        /// </summary>
        /// <param name="context">生成上下文。</param>
        /// <param name="current">所在数据源。</param>
        /// <param name="expression">初始化表达式。</param>
        /// <param name="parent">父级输出对象。</param>
        protected virtual void InitialRetrievalForSingle(GenerateContext context, ISourceFragment current, DbRetrievalFunctionExpression expression, ComplexOutputInfo parent)
        {
            var select = current as SelectFragment;

            select.Take = 2;
            InitialRetrievalForFilter(context, expression, select);
            if (parent is ObjectOutputInfo output)
            {
                output.Option = EObjectOutputOption.OnlyOne;
            }
        }
Example #10
0
        /// <summary>
        /// 创建通过临时表关联的返回数据语句片段。
        /// </summary>
        /// <param name="unit">内容对象。</param>
        /// <param name="target">目标对象。</param>
        /// <param name="temptable">临时表。</param>
        /// <returns>语句片段。</returns>
        internal static SelectFragment SelectReturns(this IContentUnit unit, ISourceFragment target, TemporaryTableFragment temptable)
        {
            var data    = (ContentBase)unit;
            var context = data.GenerateContext;
            var select  = new SelectFragment(context, target);

            select.Members.AddRange(unit.ReturnMembers.Select(a => target.GetMember(a.Metadata)));

            select.AddSource(temptable);
            target.Join(temptable, data.Table.Keys);
            return(select);
        }
        /// <summary>
        /// 写入数据源连接子句
        /// </summary>
        /// <param name="writer">语句写入器。</param>
        /// <param name="source">目标写入的数据源。</param>
        protected virtual void WriteFragmentForSourceJoin(SqlWriter writer, ISourceFragment source)
        {
            switch (source.Join.Value)
            {
            case EJoinType.CrossJoin: writer.Write("CROSS JOIN "); break;

            case EJoinType.InnerJoin: writer.Write("INNER JOIN "); break;

            case EJoinType.LeftJoin: writer.Write("LEFT JOIN "); break;

            case EJoinType.RightJoin: writer.Write("RIGHT JOIN "); break;
            }
        }
Example #12
0
        /// <summary>
        /// 注册局部表达式关联存储语句片段对象。
        /// </summary>
        /// <param name="expression">关联的表达式。</param>
        /// <param name="source">关联的源对象。</param>
        /// <param name="action">执行方法。</param>
        public void RegisterTempSource(DbExpression expression, ISourceFragment source, Action action)
        {
            var contains = _RegistedTempSource.ContainsKey(expression);

            if (!contains)
            {
                _RegistedTempSource.Add(expression, source);
            }
            action();
            if (!contains)
            {
                _RegistedTempSource.Remove(expression);
            }
        }
 /// <inheritdoc/>
 protected override void WriteFragmentForSourceCondition(SqlWriter writer, ISourceFragment source)
 {
     if (source.Condition != null)
     {
         if (source is InheritFragment && source.Join.Value == EJoinType.InnerJoin)
         {
             writer.Write(" AND ");
         }
         else
         {
             writer.Write(" ON ");
         }
         source.Condition.WriteSql(writer);
     }
 }
Example #14
0
        //分组检索表达式 ElementAt 实现。
        private void InitialRetrievalForElementAtImp(GenerateContext context, ISourceFragment current,
                                                     DbRetrievalFunctionExpression expression, ComplexOutputInfo parent, EObjectOutputOption option)
        {
            var value  = expression.Arguments[0] as DbConstantExpression;
            var select = current as SelectFragment;

            select.Take = 1;
            select.Skip = (int)value.Value;
            if (select.Skip > 0 && select.Sorts.Count == 0)
            {
                var member = GetFirstMemberForOrder(select);
                select.Sorts.Add(new SortFragment(context, member));
            }
            if (parent is ObjectOutputInfo output)
            {
                output.Option = option;
            }
        }
 /// <summary>
 /// 写入数据源内容。
 /// </summary>
 /// <param name="writer">语句写入器。</param>
 /// <param name="source">数据源语句。</param>
 protected virtual void WriteFragmentForSourceContent(SqlWriter writer, ISourceFragment source)
 {
     if (source is SelectFragment || source is SetFragment)
     {
         writer.Write('(');
         source.WriteSql(writer);
         writer.Write(')');
     }
     else
     {
         source.WriteSql(writer);
     }
     if (!(source is InheritFragment))
     {
         writer.Write(" AS ");
         writer.Write(source.AliasName);
     }
 }
Example #16
0
        public static InsertFragment Insert(this GenerateContext context, ISourceFragment source, TableMetadata target
                                            , IEnumerable <ColumnMetadata> members)
        {
            DbName name = null;

            if (context.Data is ContentBase data)
            {
                name = data.TargetName;
            }
            var table   = new TableFragment(context, target, name);
            var select  = new SelectFragment(context, source);
            var current = new InsertFragment(context, table, select);

            foreach (var member in members)
            {
                select.CreateMember(null, source.GetMember(member));
                current.CreateMember(null, member);
            }
            return(current);
        }
Example #17
0
 /// <summary>
 /// 创建删除语句。
 /// </summary>
 /// <param name="context">生成上下文。</param>
 /// <param name="target">删除目标语句。</param>
 public DeleteFragment(GenerateContext context, ISourceFragment target) : base(context)
 {
     AddSource(target); Target = target;
 }
Example #18
0
 /// <summary>
 /// 根据分组检索表达式 ElementAtDefault 初始化查询输出语句及输出对象。
 /// </summary>
 /// <param name="context">生成上下文。</param>
 /// <param name="current">所在数据源。</param>
 /// <param name="expression">初始化表达式。</param>
 /// <param name="parent">父级输出对象。</param>
 protected virtual void InitialRetrievalForElementAtDefault(GenerateContext context, ISourceFragment current, DbRetrievalFunctionExpression expression, ComplexOutputInfo parent)
 {
     InitialRetrievalForElementAtImp(context, current, expression, parent, EObjectOutputOption.ZeroOrOne);
 }
Example #19
0
        /// <summary>
        /// 生成插入单个数据对象语句,对象的主键是标识列。
        /// </summary>
        /// <param name="context">生成上下文。</param>
        /// <returns>语句片段。</returns>
        protected virtual SqlFragment GenerateForInsertIdentitySingle(GenerateContext context)
        {
            var getidentity = context.Translate(Expression.Call(null, SupportMembers.DbFunctions.GetIdentity));

            var data           = (GenerateDataForInsert)context.Data;
            var identityunit   = (CommitIdentityUnit)data.MainUnit;
            var keyVars        = new Dictionary <ColumnMetadata, VariableFragment>();
            var identityCreate = new CreateVariableFragment(context, identityunit.Identity.Metadata.Member.PropertyType);

            keyVars.Add(identityunit.Identity.Metadata, identityCreate.Name);
            var block = new BlockFragment(context);

            if (!context.Feature.HasCapable(EDbCapable.ImplicitDeclareVariable))
            {
                block.Add(identityCreate);
            }
            var name       = data.TargetName;
            var maintarget = new TableFragment(context, identityunit.Table, name);

            {
                var insert = new InsertValueFragment(context, maintarget, data.CommitObject, data.Items);
                data.CommitObject.Parent = insert;
                identityunit.Members.ForEach(member =>
                {
                    if (member.Metadata.IsKey && member.ValueType == ECommitValueType.Expression)
                    {
                        var expMember = (CommitExpressionMember)member;
                        var exp       = insert.CreateExpression(expMember.Expression);
                        var expVar    = new CreateVariableFragment(context, member.Metadata.Member.PropertyType);
                        block.Add(expVar);
                        block.Add(context.Assign(expVar.Name, exp));
                        keyVars.Add(member.Metadata, expVar.Name);
                    }
                    else
                    {
                        GenerateForInsertMembers(insert, member);
                    }
                });
                block.Add(insert);
                block.Add(context.Assign(identityCreate.Name, insert.CreateExpression(getidentity)));
            }
            if (data.SubUnits != null)
            {
                foreach (var unit in data.SubUnits)
                {
                    var target = new TableFragment(context, unit.Table);
                    var insert = new InsertValueFragment(context, target, data.CommitObject, data.Items);
                    data.CommitObject.Parent = insert;
                    unit.Keys.ForEach(member =>
                    {
                        if (keyVars.TryGetValue(member.Metadata, out VariableFragment value))
                        {
                            insert.SetValue(member.Metadata, value);
                        }
                        else
                        {
                            GenerateForInsertMembers(insert, member);
                        }
                    });
                    unit.Members.ForEach(member => GenerateForInsertMembers(insert, member));
                    block.Add(insert);
                }
            }
            if (data.ReturnMembers.Any())
            {
                ISourceFragment target = maintarget;
                if (data.SubUnits != null)
                {
                    target = new InheritFragment(context, data.Table);
                }
                var select = new SelectFragment(context, target);
                select.Members.AddRange(data.ReturnMembers.Select(a => target.GetMember(a.Metadata)));
                select.Where = data.Table.Keys.Select(key => context.Equal(target.GetMember(key),
                                                                           keyVars.ContainsKey(key) ? (IExpressionFragment)keyVars[key] : data.CommitObject.GetMember(key))).Merge();
                block.Add(select);
            }
            return(block);
        }
        /// <summary>
        /// 根据类型<see cref="DbScalarFunctionExpression"/>表达式创建表达式语句片段。
        /// </summary>
        /// <param name="context">生成上下文。</param>
        /// <param name="expression">所在数据源。</param>
        /// <param name="source">检索表达式。</param>
        /// <returns>创建结果。</returns>
        protected virtual IExpressionFragment CreateExpressionForScalarFunction(GenerateContext context, DbExpression expression, ISourceFragment source)
        {
            var scalar = (DbScalarFunctionExpression)expression;
            var result = new ScalarFragment(context)
            {
                Function = scalar.Function
            };

            foreach (var arg in scalar.Arguments)
            {
                result.Arguments.Add(source.CreateExpression(arg));
            }
            return(result);
        }
Example #21
0
        /// <inheritdoc/>
        protected override IExpressionFragment CreateExpressionForBinary(GenerateContext context, DbExpression expression, ISourceFragment source)
        {
            var binary = (DbBinaryExpression)expression;

            if (binary.Kind == EBinaryKind.Add && binary.ClrType == typeof(string))
            {
                var scalar = new ScalarFragment(context,
                                                source.CreateExpression(binary.Left),
                                                source.CreateExpression(binary.Right));
                scalar.Function = SupportMembers.String.Concat;
                return(scalar);
            }
            return(base.CreateExpressionForBinary(context, expression, source));
        }
        private void WriteFragmentForCommitReturning(SqlWriter writer, List <IMemberFragment> returnMmebers, ISourceFragment target)
        {
            if (returnMmebers.Any())
            {
                var command = target.Context.Data.OperateCommand.GetCustomCommand <IOracleCustomCommand>();

                writer.Write(" RETURNING ");
                returnMmebers.OfType <CommitMemberFragment>().ForEach(
                    () => writer.Write(','),
                    m =>
                {
                    var member = target.GetMember(m.Property);
                    WriteDbName(writer, member.OutputName);
                });
                writer.Write(" INTO ");
                returnMmebers.OfType <CommitMemberFragment>().ForEach(() => writer.Write(','),
                                                                      m => WriteParameterName(writer, command.AddParameter(m.Metadata)));
            }
        }
Example #23
0
 public static InsertFragment Insert(this GenerateContext context, ISourceFragment source, CommitKeyUnit target)
 {
     return(Insert(context, source, target.Table,
                   target.Keys.Concat(target.Members).Select(a => a.Metadata)));
 }
Example #24
0
        //生成集合成员虚拟数据源连接。
        private void GenerateVirtualJoinForCollectionMember(GenerateContext context, VirtualSourceFragment source, ISourceFragment body, bool iscomposite)
        {
            var content   = (DbCollectionMemberExpression)source.Expression;
            var container = source.Container;

            if (container.IsRecommandLock)
            {
                container = container.Parent as SelectFragment;
            }
            body.Join = EJoinType.LeftJoin;
            var pairs = content.Pairs;

            if (content.Metadata.IsComposite && iscomposite)
            {
                pairs = content.CompositePairs;
            }
            body.Condition = pairs.Select(a => container.CreateExpression(a)).Merge();
        }
        /// <summary>
        /// 根据类型<see cref="DbBinaryExpression"/>表达式创建表达式语句片段。
        /// </summary>
        /// <param name="context">生成上下文。</param>
        /// <param name="expression">所在数据源。</param>
        /// <param name="source">检索表达式。</param>
        /// <returns>创建结果。</returns>
        protected virtual IExpressionFragment CreateExpressionForBinary(GenerateContext context, DbExpression expression, ISourceFragment source)
        {
            var binary = (DbBinaryExpression)expression;

            if (binary.Kind == EBinaryKind.AndAlso || binary.Kind == EBinaryKind.OrElse)
            {
                return(source.CreateExpression(binary.Left).Merge(binary.Kind, source.CreateExpression(binary.Right)));
            }
            else
            {
                return(new BinaryFragment(context, binary.Kind)
                {
                    Left = source.CreateExpression(binary.Left),
                    Right = source.CreateExpression(binary.Right)
                });
            }
        }
Example #26
0
 /// <summary>
 /// 创建更新语句。
 /// </summary>
 /// <param name="context">生成上下文。</param>
 /// <param name="target">更新目标语句。</param>
 public UpdateFragment(GenerateContext context, ISourceFragment target)
     : base(context)
 {
     Target     = target;
     _KeyValues = new Dictionary <ColumnMetadata, ISqlFragment>();
 }
        /// <summary>
        /// 根据类型<see cref="DbUnaryExpression"/>表达式创建表达式语句片段。
        /// </summary>
        /// <param name="context">生成上下文。</param>
        /// <param name="expression">所在数据源。</param>
        /// <param name="source">检索表达式。</param>
        /// <returns>创建结果。</returns>
        protected virtual IExpressionFragment CreateExpressionForUnary(GenerateContext context, DbExpression expression, ISourceFragment source)
        {
            var unary = (DbUnaryExpression)expression;

            return(new UnaryFragment(context, unary.Kind, unary.Type)
            {
                Expresssion = source.CreateExpression(unary.Expression)
            });
        }
Example #28
0
        private static void SetCommitMembers(this ContentBase data, UpdateFragment update, CommitUnitBase unit, ISourceFragment source = null)
        {
            source = source ?? data.CommitObject;
            foreach (var member in unit.Members)
            {
                switch (member.ValueType)
                {
                case ECommitValueType.Constant:
                    update.SetValue(member.Metadata, source.GetMember(member.Metadata));
                    break;

                case ECommitValueType.Expression:
                    var exp = (CommitExpressionMember)member;
                    update.SetValue(member.Metadata, update.CreateExpression(exp.Expression));
                    break;
                }
            }
        }
Example #29
0
 private void OutputReturnMembers(SqlWriter writer, List <IMemberFragment> members, ISourceFragment target = null)
 {
     if (members.Count > 0)
     {
         writer.WriteLine();
         writer.Write("RETURNING ");
         members.ForEach(
             () => writer.Write(","),
             column =>
         {
             if (target != null)
             {
                 writer.Write(target.AliasName);
                 writer.Write('.');
             }
             this.WriteDbName(writer, column.OutputName);
         });
     }
 }
Example #30
0
        /// <inheritdoc/>
        protected override IExpressionFragment CreateExpressionForBinary(GenerateContext context, DbExpression expression, ISourceFragment source)
        {
            var binary = (DbBinaryExpression)expression;

            if (binary.Kind == EBinaryKind.Add && binary.ClrType == typeof(string))
            {
                return(new StringConcatFragment(context,
                                                source.CreateExpression(binary.Left),
                                                source.CreateExpression(binary.Right)));
            }
            return(base.CreateExpressionForBinary(context, expression, source));
        }