diff --git a/Src/Asp.Net/SqlServerTest/Demo/DemoJ_Report.cs b/Src/Asp.Net/SqlServerTest/Demo/DemoJ_Report.cs new file mode 100644 index 000000000..e48fed680 --- /dev/null +++ b/Src/Asp.Net/SqlServerTest/Demo/DemoJ_Report.cs @@ -0,0 +1,142 @@ +using SqlSugar; +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; + +namespace OrmTest +{ + public class DemoJ_Report + { + public static void Init() + { + Console.WriteLine(""); + Console.WriteLine("#### Utilities Start ####"); + + SqlSugarClient db = new SqlSugarClient(new ConnectionConfig() + { + DbType = DbType.SqlServer, + ConnectionString = Config.ConnectionString, + InitKeyType = InitKeyType.Attribute, + IsAutoCloseConnection = true, + AopEvents = new AopEvents + { + OnLogExecuting = (sql, p) => + { + Console.WriteLine(sql); + Console.WriteLine(string.Join(",", p?.Select(it => it.ParameterName + ":" + it.Value))); + } + } + }); + Demo1(db); + Demo2(db); + Demo3(db); + } + + private static void Demo1(SqlSugarClient db) + { + var list = new List() { 1, 2, 3 }; + var query1 = db.Queryable(); + var queryable2 = db.Reportable(list).ToSingleColumnQueryable(); + var x = db.Queryable(query1, queryable2, (x1, x2) => x1.Id.Equals(x2.ColumnName)) + .Select((x1, x2) => new { x = x1.Id, x2 = x2.ColumnName }).ToList(); + } + private static void Demo2(SqlSugarClient db) + { + var list = db.Queryable().ToList(); + var query1 = db.Queryable(); + var queryable2 = db.Reportable(list).ToQueryable(); + var x = db.Queryable(query1, queryable2, (x1, x2) => x1.Id.Equals(x2.OrderId)) + .Select((x1, x2) => new { name = x1.Name,id=x1.Id, orderid = x2.OrderId }).ToList(); + } + private static void Demo3(SqlSugarClient db) + { + db.CodeFirst.InitTables(); + db.Deleteable().ExecuteCommand(); + db.Insertable(new operateinfo() + { + id=1, + operate_type=1, + operate_time=Convert.ToDateTime("2021-1-1") + }).ExecuteCommand(); + db.Insertable(new operateinfo() + { + id = 1, + operate_type = 1, + operate_time = Convert.ToDateTime("2021-1-2") + }).ExecuteCommand(); + db.Insertable(new operateinfo() + { + id = 1, + operate_type = 1, + operate_time = Convert.ToDateTime("2021-3-1") + }).ExecuteCommand(); + db.Insertable(new operateinfo() + { + id = 1, + operate_type = 1, + operate_time = Convert.ToDateTime("2021-3-2") + }).ExecuteCommand(); + db.Insertable(new operateinfo() + { + id = 1, + operate_type = 1, + operate_time = Convert.ToDateTime("2021-4-2") + }).ExecuteCommand(); + + + var queryableLeft = db.Reportable(ReportableDateType.MonthsInLast1years).ToSingleColumnQueryable(); + var queryableRight = db.Queryable(); + var list= db.Queryable(queryableLeft, queryableRight, JoinType.Left, + (x1, x2) => x2.operate_time.ToString("yyyy-MM")==SqlFunc.ToDate(x1.ColumnName).ToString("yyyy-MM")) + .GroupBy((x1,x2)=>x1.ColumnName) + .Where(x1=>SqlFunc.Between(x1.ColumnName,"2021-01-01",DateTime.Now)) + .Select((x1, x2) => new + { + count=SqlFunc.AggregateSum(SqlFunc.IIF(x2.id>0,1,0)) , + date=SqlFunc.ToDate(x1.ColumnName).ToString("yyyy-MM") + + }).ToList(); + } + + + public partial class operateinfo + { + public operateinfo() + { + + + } + /// + /// Desc:操作序号 + /// Default: + /// Nullable:False + /// + public int id { get; set; } + + /// + /// Desc:操作时间 + /// Default: + /// Nullable:False + /// + public DateTime operate_time { get; set; } + + /// + /// Desc:操作类型 + /// Default: + /// Nullable:False + /// + public int operate_type { get; set; } + + /// + /// Desc:操作人编号 + /// Default: + /// Nullable:False + /// + public int user_id { get; set; } + + } + } + +} \ No newline at end of file diff --git a/Src/Asp.Net/SqlServerTest/SqlServerTest.csproj b/Src/Asp.Net/SqlServerTest/SqlServerTest.csproj index cfa5ae7b7..39ae8ffd1 100644 --- a/Src/Asp.Net/SqlServerTest/SqlServerTest.csproj +++ b/Src/Asp.Net/SqlServerTest/SqlServerTest.csproj @@ -68,6 +68,7 @@ + diff --git a/Src/Asp.Net/SqlSugar/Abstract/Reportable/ReportableProvider.cs b/Src/Asp.Net/SqlSugar/Abstract/Reportable/ReportableProvider.cs new file mode 100644 index 000000000..734baef1f --- /dev/null +++ b/Src/Asp.Net/SqlSugar/Abstract/Reportable/ReportableProvider.cs @@ -0,0 +1,193 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; + +namespace SqlSugar +{ + public class ReportableProvider : IReportable + { + public SqlSugarProvider Context { get; set; } + private List datas = new List(); + private List dates = new List(); + private bool isDates = false; + internal InsertBuilder formatBuilder { get; set; } + + public ReportableProvider(T data) + { + datas.Add(data); + Init(); + } + + public ReportableProvider(List list) + { + datas = list; + Init(); + } + + public IReportable MakeUp(Func auto) + { + throw new NotImplementedException(); + } + + public ISugarQueryable ToQueryable() + { + StringBuilder sb = new StringBuilder(); + if (datas.Any()) + { + if (isDates) + { + var da = this.dates; + Each(sb, da); + } + else + { + var da = this.datas; + Each(sb, da); + } + } + else + { + if (typeof(T).IsClass()) + { + + var result = (T)Activator.CreateInstance(typeof(T), true); + datas.Add(result); + ClassMethod(result, sb, true); + } + else + { + sb.Append("SELECT NULL as ColumnName "); + sb.Append(GetNextSql); + } + } + return this.Context.SqlQueryable(sb.ToString()).Select(); + } + + private void Each(StringBuilder sb, List list) + { + foreach (var item in list) + { + var isLast = list.IndexOf(item) == list.Count - 1; + var isClass = typeof(T).IsClass(); + if (isClass) + { + ClassMethod(item, sb, isLast); + } + else + { + NoClassMethod(item, sb, isLast); + } + } + } + + public ISugarQueryable ToSingleColumnQueryable() + { + return ToQueryable().Select(); + } + + private void ClassMethod(Y data, StringBuilder sb,bool isLast) + { + var columns = new StringBuilder(); + var entity=this.Context.EntityMaintenance.GetEntityInfo(); + columns.Append(string.Join(",",entity.Columns.Select(it=>GetSelect(it,data)))); + sb.AppendLine(" SELECT " + columns.ToString()); + sb.Append(GetNextSql); + if (!isLast) + { + sb.AppendLine(" UNION ALL "); + } + } + + private object GetSelect(EntityColumnInfo it,Y data) + { + return string.Format(" {0} AS {1} ",formatBuilder.FormatValue(it.PropertyInfo.GetValue(data,null)),it.PropertyName); + } + + private void NoClassMethod(Y data, StringBuilder sb,bool isLast) + { + sb.AppendLine(" SELECT "+ formatBuilder.FormatValue(data)); + sb.Append(" AS ColumnName "); + sb.Append(GetNextSql); + if (!isLast) + { + sb.AppendLine(" UNION ALL "); + } + } + public string GetNextSql + { + get + { + if (this.Context.CurrentConnectionConfig.DbType == DbType.Oracle) + { + return " from dual "; + } + else + { + return null; + } + } + } + private void Init() + { + if (datas.Count == 1) + { + isDates = true; + var data=datas.First(); + if (data is ReportableDateType) + { + var type = UtilMethods.ChangeType2(data, typeof(ReportableDateType)); + switch (type) + { + case ReportableDateType.MonthsInLast1years: + dates.AddRange(GetMonths(1)); + break; + case ReportableDateType.MonthsInLast3years: + dates.AddRange(GetMonths(3)); + break; + case ReportableDateType.MonthsInLast10years: + dates.AddRange(GetMonths(10)); + break; + case ReportableDateType.years1: + dates.AddRange(GetYears(1)); + break; + case ReportableDateType.years3: + dates.AddRange(GetYears(3)); + break; + case ReportableDateType.years10: + dates.AddRange(GetYears(10)); + break; + default: + break; + } + } + } + } + + private List GetYears(int v) + { + List result = new List(); + for (int i = 0; i < v; i++) + { + var year= (DateTime.Now.AddYears(i * -1).Year+"-01"+"-01").ObjToDate(); + result.Add(year); + } + return result; + } + private List GetMonths(int v) + { + List result = new List(); + var years = GetYears(v); + foreach (var item in years) + { + for (int i = 0; i < 12; i++) + { + result.Add(item.AddMonths(i)); + } + } + return result; + } + + } +} diff --git a/Src/Asp.Net/SqlSugar/Abstract/SugarProvider/SqlSugarProvider.cs b/Src/Asp.Net/SqlSugar/Abstract/SugarProvider/SqlSugarProvider.cs index 31b3b587f..1e2d99319 100644 --- a/Src/Asp.Net/SqlSugar/Abstract/SugarProvider/SqlSugarProvider.cs +++ b/Src/Asp.Net/SqlSugar/Abstract/SugarProvider/SqlSugarProvider.cs @@ -754,6 +754,32 @@ namespace SqlSugar } #endregion + #region Reportable + public IReportable Reportable(T data) + { + var result = new ReportableProvider(data); + result.formatBuilder = InstanceFactory.GetInsertBuilder(this.Context.CurrentConnectionConfig); + result.Context = this; + return result; + } + public IReportable Reportable(List list) + { + var result = new ReportableProvider(list); + result.formatBuilder = InstanceFactory.GetInsertBuilder(this.Context.CurrentConnectionConfig); + result.Context = this; + return result; + } + public IReportable Reportable(T [] list) + { + if (list == null) + list = new T[] { }; + var result = new ReportableProvider(list.ToList()); + result.formatBuilder = InstanceFactory.GetInsertBuilder(this.Context.CurrentConnectionConfig); + result.Context = this; + return result; + } + #endregion + #region DbFirst public virtual IDbFirst DbFirst { diff --git a/Src/Asp.Net/SqlSugar/Entities/SingleColumnsEntity.cs b/Src/Asp.Net/SqlSugar/Entities/SingleColumnsEntity.cs new file mode 100644 index 000000000..f795c85d5 --- /dev/null +++ b/Src/Asp.Net/SqlSugar/Entities/SingleColumnsEntity.cs @@ -0,0 +1,13 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; + +namespace SqlSugar +{ + public class SingleColumnEntity + { + public object ColumnName { get; set; } + } +} diff --git a/Src/Asp.Net/SqlSugar/Enum/ReportableDateType.cs b/Src/Asp.Net/SqlSugar/Enum/ReportableDateType.cs new file mode 100644 index 000000000..fa24750bf --- /dev/null +++ b/Src/Asp.Net/SqlSugar/Enum/ReportableDateType.cs @@ -0,0 +1,18 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; + +namespace SqlSugar +{ + public enum ReportableDateType + { + MonthsInLast1years=0, + MonthsInLast3years=1, + MonthsInLast10years=2, + years1=3, + years3=4, + years10=5 + } +} diff --git a/Src/Asp.Net/SqlSugar/ExpressionsToSql/ResolveItems/NewExpressionResolve.cs b/Src/Asp.Net/SqlSugar/ExpressionsToSql/ResolveItems/NewExpressionResolve.cs index 0bc23c853..c1fbbc8c6 100644 --- a/Src/Asp.Net/SqlSugar/ExpressionsToSql/ResolveItems/NewExpressionResolve.cs +++ b/Src/Asp.Net/SqlSugar/ExpressionsToSql/ResolveItems/NewExpressionResolve.cs @@ -42,8 +42,16 @@ namespace SqlSugar case ResolveExpressType.ArraySingle: foreach (var item in expression.Arguments) { - base.Expression = item; - base.Start(); + if (IsDateValue(item)) + { + var value = GetNewExpressionValue(item); + base.Context.Result.Append(value); + } + else + { + base.Expression = item; + base.Start(); + } } break; case ResolveExpressType.Join: @@ -75,6 +83,25 @@ namespace SqlSugar } } + private bool IsDateValue(Expression item) + { + var isMember = item is MemberExpression; + if (isMember) + { + var m = (item as MemberExpression); + var isInt= m.Type == UtilConstants.IntType; + if (m.Expression != null && isInt&& m.Expression is MemberExpression) + { + var mm = (m.Expression as MemberExpression); + if (m.Member.Name.IsIn("Year", "Day", "Month")&&mm.Type==UtilConstants.DateType) + { + return true; + } + } + } + return false; + } + private void NewValueType(ExpressionParameter parameter, NewExpression expression) { try diff --git a/Src/Asp.Net/SqlSugar/Interface/IReportable.cs b/Src/Asp.Net/SqlSugar/Interface/IReportable.cs new file mode 100644 index 000000000..d9f15e294 --- /dev/null +++ b/Src/Asp.Net/SqlSugar/Interface/IReportable.cs @@ -0,0 +1,15 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; + +namespace SqlSugar +{ + public interface IReportable + { + IReportable MakeUp(Func auto); + ISugarQueryable ToQueryable(); + ISugarQueryable ToSingleColumnQueryable(); + } +} diff --git a/Src/Asp.Net/SqlSugar/SqlSugar.csproj b/Src/Asp.Net/SqlSugar/SqlSugar.csproj index 7aea5aaff..9a6d6e019 100644 --- a/Src/Asp.Net/SqlSugar/SqlSugar.csproj +++ b/Src/Asp.Net/SqlSugar/SqlSugar.csproj @@ -88,16 +88,20 @@ + + + + diff --git a/Src/Asp.Net/SqlSugar/SqlSugarClient.cs b/Src/Asp.Net/SqlSugar/SqlSugarClient.cs index 453fe63bc..1aa553583 100644 --- a/Src/Asp.Net/SqlSugar/SqlSugarClient.cs +++ b/Src/Asp.Net/SqlSugar/SqlSugarClient.cs @@ -358,6 +358,21 @@ namespace SqlSugar } #endregion + #region Reportable + public IReportable Reportable(T data) + { + return this.Context.Reportable(data); + } + public IReportable Reportable(List list) + { + return this.Context.Reportable(list); + } + public IReportable Reportable(T [] array) + { + return this.Context.Reportable(array); + } + #endregion + #region Queue public QueueList Queues { get { return this.Context.Queues; } set { this.Context.Queues = value; } } public void AddQueue(string sql, object parsmeters = null)