dotnetcore / FreeSql

🦄 .NET aot orm, C# orm, VB.NET orm, Mysql orm, Postgresql orm, SqlServer orm, Oracle orm, Sqlite orm, Firebird orm, 达梦 orm, 人大金仓 orm, 神通 orm, 翰高 orm, 南大通用 orm, 虚谷 orm, 国产 orm, Clickhouse orm, QuestDB orm, MsAccess orm.
http://freesql.net
MIT License
3.99k stars 842 forks source link

泛型仓库开启级联保存无效 #1766

Closed yangf85 closed 1 month ago

yangf85 commented 1 month ago

image

问题描述及重现代码:

// c# code
**这是工具类**
 public interface IDataAccess<T> : IDataService<T> where T : BasicEntity, new()
 {
     IFreeSql FreeSql { get; }

     IBaseRepository<T> Repository { get; }
 }

 public class DataService<T> : IDataAccess<T> where T : BasicEntity, new()
 {
     protected readonly IFreeSql _fsql;

     public IFreeSql FreeSql => _fsql;

     public IBaseRepository<T> Repository => _fsql.GetRepository<T>();

     public DataService(IFreeSql fsql)
     {
         _fsql = fsql;
         //Repository.DbContextOptions.EnableCascadeSave = true;
     }

     public async Task<bool> AddAsync(T model)
     {
         return await Task.FromResult(true);
     }

     public async Task<bool> SaveAsync(T model, ItemChangedType changedType)
     {
         switch (changedType)
         {
             case ItemChangedType.Add:
                 return (await Repository.InsertAsync(model)).Id != 0;

             case ItemChangedType.Update:
                 return (await Repository.UpdateAsync(model)) != 0;

             default:
                 return false;
         }
     }

     public async Task<bool> DeleteAsync(IEnumerable<T> models)
     {
         foreach (var model in models)
         {
             await _fsql.Update<T>(model).Set(m => m.IsDeleted, true).Where(model).ExecuteAffrowsAsync(); //软删除,需要配合拦截器使用
         }

         return true;
     }

     public Task<QueryData<T>> QueryAsync(QueryPageOptions option)
     {
         var items = _fsql.Select<T>().WhereDynamicFilter(option.ToDynamicFilter())
         .OrderByPropertyNameIf(option.SortOrder != SortOrder.Unset, option.SortName, option.SortOrder == SortOrder.Asc)
         .Count(out var count);

         if (option.IsPage)
         {
             items = items.Page(option.PageIndex, option.PageItems);
         }
         else if (option.IsVirtualScroll)
         {
             items = items.Skip(option.StartIndex).Take(option.PageItems);
         }

         var ret = new QueryData<T>()
         {
             TotalCount = (int)count,
             Items = items.ToList<T>(),
             IsSorted = option.SortOrder != SortOrder.Unset,
             IsFiltered = option.Filters.Any(),
             IsAdvanceSearch = option.AdvanceSearches.Any(),
             IsSearch = option.Searches.Any() || option.CustomerSearches.Any()
         };
         return Task.FromResult(ret);
     }
 }

数据库版本

### 这是使用Freesql获取具体类型的仓库执行的SQL语句 --------------2024/3/31 16:09:07-------------------- Sql:SELECT TOP 1 a.[Id], a.[CreateTime], a.[UpdateTime], a.[IsDeleted], a.[Name], a.[SerialNumber], a.[EstimatedValue], a.[Status], a.[Address], a.[Contact], a.[Phone], a.[StartDate], a.[EndDate], a.[Note], a.[CustomerId] FROM [Project] a WHERE (a.[IsDeleted] = 0) AND (a.[Id] = 1)

--------------2024/3/31 16:09:07-------------------- Sql:SELECT TOP 1 a.[Id], a.[CreateTime], a.[UpdateTime], a.[IsDeleted], a.[Name], a.[SerialNumber], a.[Category], a.[Address], a.[Contact], a.[Phone], a.[Website], a.[Email], a.[Fax], a.[Note], a.[SalesmanId] FROM [Customer] a WHERE (a.[IsDeleted] = 0) AND (a.[Id] = 3)

--------------2024/3/31 16:09:07-------------------- Sql:INSERT INTO [Order]([CreateTime], [UpdateTime], [IsDeleted], [Batch], [Status], [Priority], [ProcessFlowStep], [StartDate], [EndDate], [Number], [Note], [ProjectId]) OUTPUT INSERTED.[Id] as [Id], INSERTED.[CreateTime] as [CreateTime], INSERTED.[UpdateTime] as [UpdateTime], INSERTED.[IsDeleted] as [IsDeleted], INSERTED.[Batch] as [Batch], INSERTED.[Status] as [Status], INSERTED.[Priority] as [Priority], INSERTED.[ProcessFlowStep] as [ProcessFlowStep], INSERTED.[StartDate] as [StartDate], INSERTED.[EndDate] as [EndDate], INSERTED.[Number] as [Number], INSERTED.[Note] as [Note], INSERTED.[ProjectId] as [ProjectId] VALUES(getutcdate(), getutcdate(), @IsDeleted_0, @Batch_0, @Status_0, @Priority_0, @ProcessFlowStep_0, @StartDate_0, @EndDate_0, @Number_0, @Note_0, @ProjectId_0)

--------------2024/3/31 16:09:07-------------------- Sql:SELECT TOP 1 a.[Id], a.[CreateTime], a.[UpdateTime], a.[IsDeleted], a.[Name], a.[SerialNumber], a.[EstimatedValue], a.[Status], a.[Address], a.[Contact], a.[Phone], a.[StartDate], a.[EndDate], a.[Note], a.[CustomerId] FROM [Project] a WHERE (a.[IsDeleted] = 0) AND (a.[Id] = 1)

--------------2024/3/31 16:09:07-------------------- Sql:SELECT TOP 1 a.[Id], a.[CreateTime], a.[UpdateTime], a.[IsDeleted], a.[Name], a.[SerialNumber], a.[Category], a.[Address], a.[Contact], a.[Phone], a.[Website], a.[Email], a.[Fax], a.[Note], a.[SalesmanId] FROM [Customer] a WHERE (a.[IsDeleted] = 0) AND (a.[Id] = 3)

--------------2024/3/31 16:09:07-------------------- Sql:INSERT INTO [SheetmatelSummary]([CreateTime], [UpdateTime], [IsDeleted], [Id], [Standard], [Pieces], [Area], [WeldLength], [NotchingLength], [BendingTimes], [Notes]) OUTPUT INSERTED.[CreateTime] as [CreateTime], INSERTED.[UpdateTime] as [UpdateTime], INSERTED.[IsDeleted] as [IsDeleted], INSERTED.[Id] as [Id], INSERTED.[Standard] as [Standard], INSERTED.[Pieces] as [Pieces], INSERTED.[Area] as [Area], INSERTED.[WeldLength] as [WeldLength], INSERTED.[NotchingLength] as [NotchingLength], INSERTED.[BendingTimes] as [BendingTimes], INSERTED.[Notes] as [Notes] VALUES(getutcdate(), getutcdate(), @IsDeleted_0, @Id_0, @Standard_0, @Pieces_0, @Area_0, @WeldLength_0, @NotchingLength_0, @BendingTimes_0, @Notes_0)

--------------2024/3/31 16:09:08-------------------- Sql:SELECT TOP 1 a.[Id], a.[CreateTime], a.[UpdateTime], a.[IsDeleted], a.[Name], a.[SerialNumber], a.[EstimatedValue], a.[Status], a.[Address], a.[Contact], a.[Phone], a.[StartDate], a.[EndDate], a.[Note], a.[CustomerId] FROM [Project] a WHERE (a.[IsDeleted] = 0) AND (a.[Id] = 1)

--------------2024/3/31 16:09:08-------------------- Sql:SELECT TOP 1 a.[Id], a.[CreateTime], a.[UpdateTime], a.[IsDeleted], a.[Name], a.[SerialNumber], a.[Category], a.[Address], a.[Contact], a.[Phone], a.[Website], a.[Email], a.[Fax], a.[Note], a.[SalesmanId] FROM [Customer] a WHERE (a.[IsDeleted] = 0) AND (a.[Id] = 3)

--------------2024/3/31 16:09:08-------------------- Sql:INSERT INTO [CoatingSummary]([CreateTime], [UpdateTime], [IsDeleted], [Id], [Standard], [Pieces], [Area], [Packing], [Notes]) OUTPUT INSERTED.[CreateTime] as [CreateTime], INSERTED.[UpdateTime] as [UpdateTime], INSERTED.[IsDeleted] as [IsDeleted], INSERTED.[Id] as [Id], INSERTED.[Standard] as [Standard], INSERTED.[Pieces] as [Pieces], INSERTED.[Area] as [Area], INSERTED.[Packing] as [Packing], INSERTED.[Notes] as [Notes] VALUES(getutcdate(), getutcdate(), @IsDeleted_0, @Id_0, @Standard_0, @Pieces_0, @Area_0, @Packing_0, @Notes_0)

--------------2024/3/31 16:09:08-------------------- Sql:SELECT TOP 1 a.[Id], a.[CreateTime], a.[UpdateTime], a.[IsDeleted], a.[Name], a.[SerialNumber], a.[EstimatedValue], a.[Status], a.[Address], a.[Contact], a.[Phone], a.[StartDate], a.[EndDate], a.[Note], a.[CustomerId] FROM [Project] a WHERE (a.[IsDeleted] = 0) AND (a.[Id] = 1)

--------------2024/3/31 16:09:08-------------------- Sql:SELECT TOP 1 a.[Id], a.[CreateTime], a.[UpdateTime], a.[IsDeleted], a.[Name], a.[SerialNumber], a.[Category], a.[Address], a.[Contact], a.[Phone], a.[Website], a.[Email], a.[Fax], a.[Note], a.[SalesmanId] FROM [Customer] a WHERE (a.[IsDeleted] = 0) AND (a.[Id] = 3)

--------------2024/3/31 16:09:08-------------------- Sql:INSERT INTO [MaterialSummary]([CreateTime], [UpdateTime], [IsDeleted], [Id], [MaterialSource], [SheetUtilization], [ExpandMeshUtilization], [PaintUtilization], [TransferPaperUtilization], [Notes]) OUTPUT INSERTED.[CreateTime] as [CreateTime], INSERTED.[UpdateTime] as [UpdateTime], INSERTED.[IsDeleted] as [IsDeleted], INSERTED.[Id] as [Id], INSERTED.[MaterialSource] as [MaterialSource], INSERTED.[SheetUtilization] as [SheetUtilization], INSERTED.[ExpandMeshUtilization] as [ExpandMeshUtilization], INSERTED.[PaintUtilization] as [PaintUtilization], INSERTED.[TransferPaperUtilization] as [TransferPaperUtilization], INSERTED.[Notes] as [Notes] VALUES(getutcdate(), getutcdate(), @IsDeleted_0, @Id_0, @MaterialSource_0, @SheetUtilization_0, @ExpandMeshUtilization_0, @PaintUtilization_0, @TransferPaperUtilization_0, @Notes_0)

--------------2024/3/31 16:09:08-------------------- Sql:SELECT TOP 1 a.[Id], a.[CreateTime], a.[UpdateTime], a.[IsDeleted], a.[Name], a.[SerialNumber], a.[EstimatedValue], a.[Status], a.[Address], a.[Contact], a.[Phone], a.[StartDate], a.[EndDate], a.[Note], a.[CustomerId] FROM [Project] a WHERE (a.[IsDeleted] = 0) AND (a.[Id] = 1)

--------------2024/3/31 16:09:08-------------------- Sql:SELECT TOP 1 a.[Id], a.[CreateTime], a.[UpdateTime], a.[IsDeleted], a.[Name], a.[SerialNumber], a.[Category], a.[Address], a.[Contact], a.[Phone], a.[Website], a.[Email], a.[Fax], a.[Note], a.[SalesmanId] FROM [Customer] a WHERE (a.[IsDeleted] = 0) AND (a.[Id] = 3)

### 这是工具类获取的仓库执行的sql,可以看到没有执行级联保存 --------------2024/3/31 16:11:52-------------------- Sql:SELECT TOP 1 a.[Id], a.[CreateTime], a.[UpdateTime], a.[IsDeleted], a.[Name], a.[SerialNumber], a.[EstimatedValue], a.[Status], a.[Address], a.[Contact], a.[Phone], a.[StartDate], a.[EndDate], a.[Note], a.[CustomerId] FROM [Project] a WHERE (a.[IsDeleted] = 0) AND (a.[Id] = 1)

--------------2024/3/31 16:11:52-------------------- Sql:SELECT TOP 1 a.[Id], a.[CreateTime], a.[UpdateTime], a.[IsDeleted], a.[Name], a.[SerialNumber], a.[Category], a.[Address], a.[Contact], a.[Phone], a.[Website], a.[Email], a.[Fax], a.[Note], a.[SalesmanId] FROM [Customer] a WHERE (a.[IsDeleted] = 0) AND (a.[Id] = 3)

--------------2024/3/31 16:11:52-------------------- Sql:INSERT INTO [Order]([CreateTime], [UpdateTime], [IsDeleted], [Batch], [Status], [Priority], [ProcessFlowStep], [StartDate], [EndDate], [Number], [Note], [ProjectId]) OUTPUT INSERTED.[Id] as [Id], INSERTED.[CreateTime] as [CreateTime], INSERTED.[UpdateTime] as [UpdateTime], INSERTED.[IsDeleted] as [IsDeleted], INSERTED.[Batch] as [Batch], INSERTED.[Status] as [Status], INSERTED.[Priority] as [Priority], INSERTED.[ProcessFlowStep] as [ProcessFlowStep], INSERTED.[StartDate] as [StartDate], INSERTED.[EndDate] as [EndDate], INSERTED.[Number] as [Number], INSERTED.[Note] as [Note], INSERTED.[ProjectId] as [ProjectId] VALUES(getutcdate(), getutcdate(), @IsDeleted_0, @Batch_0, @Status_0, @Priority_0, @ProcessFlowStep_0, @StartDate_0, @EndDate_0, @Number_0, @Note_0, @ProjectId_0)

--------------2024/3/31 16:11:52-------------------- Sql:SELECT TOP 1 a.[Id], a.[CreateTime], a.[UpdateTime], a.[IsDeleted], a.[Name], a.[SerialNumber], a.[EstimatedValue], a.[Status], a.[Address], a.[Contact], a.[Phone], a.[StartDate], a.[EndDate], a.[Note], a.[CustomerId] FROM [Project] a WHERE (a.[IsDeleted] = 0) AND (a.[Id] = 1)

--------------2024/3/31 16:11:52-------------------- Sql:SELECT TOP 1 a.[Id], a.[CreateTime], a.[UpdateTime], a.[IsDeleted], a.[Name], a.[SerialNumber], a.[Category], a.[Address], a.[Contact], a.[Phone], a.[Website], a.[Email], a.[Fax], a.[Note], a.[SalesmanId] FROM [Customer] a WHERE (a.[IsDeleted] = 0) AND (a.[Id] = 3)

安装的Nuget包

.net framework/. net core? 及具体版本

luoyunchong commented 1 month ago
   public IBaseRepository<T> Repository => _fsql.GetRepository<T>();

每次获取的都是不同的仓储实例

yangf85 commented 1 month ago
   public IBaseRepository<T> Repository => _fsql.GetRepository<T>();

每次获取的都是不同的仓储实例

哦,原来是这样啊,有什么好的解决方案吗?

luoyunchong commented 1 month ago

使用依赖注入仓储,不要自己创建仓储

yangf85 commented 1 month ago

使用依赖注入仓储,不要自己创建仓储

好的谢谢