diff --git a/Src/Asp.Net/SqlSugar/Abstract/SaveableProvider/StorageableDataTable.cs b/Src/Asp.Net/SqlSugar/Abstract/SaveableProvider/StorageableDataTable.cs new file mode 100644 index 000000000..ee982bc65 --- /dev/null +++ b/Src/Asp.Net/SqlSugar/Abstract/SaveableProvider/StorageableDataTable.cs @@ -0,0 +1,182 @@ +using System; +using System.Collections.Generic; +using System.Data; +using System.Linq; +using System.Text; +using System.Threading.Tasks; + +namespace SqlSugar +{ + public class StorageableDataTable + { + internal DataTable DataTable { get; set; } + internal SqlSugarProvider Context { get; set; } + internal string[] Columns { get; set; } = new string[] { }; + internal string SugarGroupId = "SugarGroupId"; + internal string SugarUpdateRows = "SugarUpdateRows"; + internal string SugarColumns = "SugarColumns"; + internal string SugarErrorMessage = "SugarErrorMessage"; + internal List dbDataList = new List(); + List,string>> whereFuncs = new List,string>>(); + public StorageableDataTable WhereColumns(string name) + { + return WhereColumns(new string[] { name}); + } + public StorageableDataTable WhereColumns(string[] names) + { + this.Columns = names; + var queryable = this.Context.Queryable(); + Check.Exception(Columns==null|| Columns.Length==0,"need WhereColums"); + var tableName = queryable.SqlBuilder.GetTranslationTableName(DataTable.TableName); + this.Context.Utilities.PageEach(DataTable.Rows.Cast(), 200, itemList => + { + List conditList = new List(); + SetConditList(itemList, Columns, conditList); + var addItem = this.Context.Queryable().AS(tableName).Where(conditList).ToDataTable().Rows.Cast().ToList(); + this.dbDataList.AddRange(addItem); + }); + return this; + } + public StorageableDataTable WhereColumns(List names) + { + return WhereColumns(names.ToArray()); + } + public StorageableDataTable SplitInsert(Func conditions, string message = null) + { + whereFuncs.Add(new KeyValuePair, string>(StorageType.Insert, conditions,message)); + return this; + } + public StorageableDataTable SplitDelete(Func conditions, string message = null) + { + whereFuncs.Add(new KeyValuePair,string>(StorageType.Delete, conditions,message)); + return this; + } + public StorageableDataTable SplitUpdate(Func conditions, string message = null) + { + whereFuncs.Add(new KeyValuePair,string>(StorageType.Update, conditions,message)); + return this; + } + + public StorageableDataTable Saveable(string inserMessage = null, string updateMessage = null) + { + SplitUpdate(it => it.Any(), updateMessage); + SplitInsert(it => it.Any(), inserMessage); + return this; + } + public StorageableDataTable SplitError(Func conditions, string message = null) + { + whereFuncs.Add(new KeyValuePair, string>(StorageType.Error, conditions, message)); + return this; + } + public StorageableDataTable SplitIgnore(Func conditions, string message = null) + { + whereFuncs.Add(new KeyValuePair, string>(StorageType.Ignore, conditions, message)); + return this; + } + + public DataTableResult ToStorage() + { + foreach (DataRow row in DataTable.Rows) + { + foreach (var item in whereFuncs.OrderByDescending(it => (int)it.key)) + { + SplitMethod(item.value1,item.key,row,item.value2); + } + } + DataTable.Columns.Remove(SugarUpdateRows); + DataTable.Columns.Remove(SugarColumns); + var Groups=DataTable.Rows.Cast() + .GroupBy(it => ((StorageType)it[SugarGroupId]).ToString()).Select(it=>new DataTableGroups{ Type=it.Key,DataTable= it.CopyToDataTable() }) + .ToList(); + DataTable.Columns.Remove(SugarGroupId); + DataTable.Columns.Remove(SugarErrorMessage); + DataTableResult result = new DataTableResult() + { + DataTableGroups=Groups, + AsDeleteable=this.Context.Deleteable().AS(DataTable.TableName).Where(""), + AsUpdateable= this.Context.Updateable(new List>()).AS(DataTable.TableName).WhereColumns(Columns), + AsInsertable=this.Context.Insertable(new List>()).AS(DataTable.TableName) + }; + return result; + } + + private void SplitMethod(Func conditions, StorageType type,DataRow item,string message) + { + item[SugarColumns] = Columns; + item[SugarUpdateRows] = dbDataList; + if ((item[SugarGroupId]==null|| item[SugarGroupId] == DBNull.Value) && conditions(item)) + { + item[SugarGroupId] = type; + item[SugarErrorMessage] = message; + } + } + private void SetConditList(List itemList, string[] whereColumns, List conditList) + { + ; + foreach (var dataItem in itemList) + { + var condition = new ConditionalCollections() + { + ConditionalList = new List>() + }; + conditList.Add(condition); + int i = 0; + foreach (var name in whereColumns) + { + var value = dataItem[name]; + if (value != null && value.GetType().IsEnum()) + { + value = Convert.ToInt64(value); + } + condition.ConditionalList.Add(new KeyValuePair(i == 0 ? WhereType.Or : WhereType.And, new ConditionalModel() + { + FieldName = name, + ConditionalType = ConditionalType.Equal, + FieldValue = value + "", + FieldValueConvertFunc = this.Context.CurrentConnectionConfig.DbType == DbType.PostgreSQL ? + UtilMethods.GetTypeConvert(value) : null + })); + ++i; + } + } + } + } + + public class DataTableResult + { + public List DataTableGroups { get; set; } + public IUpdateable> AsUpdateable { get; set; } + public IDeleteable AsDeleteable { get; set; } + public IInsertable> AsInsertable { get; set; } + } + public class DataTableGroups + { + public string Type { get; set; } + public DataTable DataTable { get; set; } + } + public static class StorageableDataTableExtensions + { + public static bool Any(this DataRow row) + { + var list=row["SugarUpdateRows"] as List; + var columns = row["SugarColumns"] as string[]; + return list.Any(it => + { + var result = true; + foreach (var name in columns) + { + + if (result) + { + result = row[name].ObjToString() == it[name].ObjToString(); + if (result == false) + { + break; + } + } + } + return result; + }); + } + } +} diff --git a/Src/Asp.Net/SqlSugar/Abstract/SugarProvider/SqlSugarProvider.cs b/Src/Asp.Net/SqlSugar/Abstract/SugarProvider/SqlSugarProvider.cs index 932492555..15c911db9 100644 --- a/Src/Asp.Net/SqlSugar/Abstract/SugarProvider/SqlSugarProvider.cs +++ b/Src/Asp.Net/SqlSugar/Abstract/SugarProvider/SqlSugarProvider.cs @@ -765,6 +765,18 @@ namespace SqlSugar { return Storageable(new List() { data }); } + public StorageableDataTable Storageable(DataTable data) + { + var result = new StorageableDataTable(); + Check.Exception(data.TableName.IsNullOrEmpty() || data.TableName == "Table",ErrorMessage.GetThrowMessage( "DataTable data.TableName is null", "参数DataTable没有设置TableName ,参数.TableName=表名")); + result.DataTable = data; + result.Context = this; + data.Columns.Add(new DataColumn("SugarGroupId", typeof(StorageType))); + data.Columns.Add(new DataColumn("SugarUpdateRows", typeof(List))); + data.Columns.Add(new DataColumn("SugarErrorMessage", typeof(string))); + data.Columns.Add(new DataColumn("SugarColumns", typeof(string[]))); + return result; + } #endregion #region Reportable diff --git a/Src/Asp.Net/SqlSugar/Interface/ISqlSugarClient.cs b/Src/Asp.Net/SqlSugar/Interface/ISqlSugarClient.cs index 7c291016e..041c86af3 100644 --- a/Src/Asp.Net/SqlSugar/Interface/ISqlSugarClient.cs +++ b/Src/Asp.Net/SqlSugar/Interface/ISqlSugarClient.cs @@ -1,5 +1,6 @@ using System; using System.Collections.Generic; +using System.Data; using System.Dynamic; using System.Linq.Expressions; using System.Threading.Tasks; @@ -122,6 +123,7 @@ namespace SqlSugar #region Saveable IStorageable Storageable(List dataList) where T : class, new(); IStorageable Storageable(T data) where T : class, new(); + StorageableDataTable Storageable(DataTable data); [Obsolete("use Storageable")] ISaveable Saveable(List saveObjects) where T : class, new(); [Obsolete("use Storageable")] diff --git a/Src/Asp.Net/SqlSugar/SqlSugar.csproj b/Src/Asp.Net/SqlSugar/SqlSugar.csproj index e239bc4f5..7d46558de 100644 --- a/Src/Asp.Net/SqlSugar/SqlSugar.csproj +++ b/Src/Asp.Net/SqlSugar/SqlSugar.csproj @@ -94,6 +94,7 @@ + diff --git a/Src/Asp.Net/SqlSugar/SqlSugarClient.cs b/Src/Asp.Net/SqlSugar/SqlSugarClient.cs index 86ad4fcb3..43ac21a94 100644 --- a/Src/Asp.Net/SqlSugar/SqlSugarClient.cs +++ b/Src/Asp.Net/SqlSugar/SqlSugarClient.cs @@ -1,5 +1,6 @@ using System; using System.Collections.Generic; +using System.Data; using System.Diagnostics; using System.Dynamic; using System.Linq; @@ -345,6 +346,10 @@ namespace SqlSugar #endregion #region Saveable + public StorageableDataTable Storageable(DataTable data) + { + return this.Context.Storageable(data); + } public IStorageable Storageable(List dataList) where T : class, new() { diff --git a/Src/Asp.Net/SqlSugar/SqlSugarScope.cs b/Src/Asp.Net/SqlSugar/SqlSugarScope.cs index 52a0762b7..a2b372d97 100644 --- a/Src/Asp.Net/SqlSugar/SqlSugarScope.cs +++ b/Src/Asp.Net/SqlSugar/SqlSugarScope.cs @@ -1,5 +1,6 @@ using System; using System.Collections.Generic; +using System.Data; using System.Diagnostics; using System.Dynamic; using System.Linq; @@ -539,6 +540,10 @@ namespace SqlSugar { return ScopedContext.Storageable(data); } + public StorageableDataTable Storageable(DataTable data) + { + return ScopedContext.Storageable(data); + } public ISugarQueryable Union(List> queryables) where T : class, new() {