多线程报异常问题 返回
SqlSugar
4
151

悬赏:0 飞吻
麻烦问一下大家,我有个基于 .NET 6 Worker Service 的程序,需要分别从多个 WebService 中获得最新的数据存到数据库中,我想用多线程实现,结果一直异常,还请大家帮忙看下是咋回事。
现在的代码是可以运行的,但是如果我把 1 和 3 位置的 CopyNew 去掉,并且将事务处理换成 _dbClient.AsTenant().BeginTran 和 _dbClient.AsTenant().CommitTran 后,就会在 2 的位置报 “Index was out of range. Must be non-negative and less than the size of the collection. (Parameter 'index')”异常,同时在 4 处报 “Object reference not set to an instance of an object.”,这是为啥呢?
... // SqlSugar 客户端 public static ISqlSugarClient _dbClient = new SqlSugarScope(new List<ConnectionConfig> { new() { ConfigId = CommonConstants.DB_ID, DbType = DbType.Oracle, ConnectionString = _connStrs[CommonConstants.DB_ID], IsAutoCloseConnection = true, ConfigureExternalServices = new ConfigureExternalServices { EntityService = (c, p) => { if (new NullabilityInfoContext().Create(c).WriteState is NullabilityState.Nullable) p.IsNullable = true; } } }, new() { ConfigId = CommonConstants.LOCAL_LOGGING_DB_ID, DbType = DbType.Sqlite, ConnectionString = _connStrs[CommonConstants.LOCAL_LOGGING_DB_ID], IsAutoCloseConnection = true, ConfigureExternalServices = new ConfigureExternalServices { EntityService = (c, p) => { if (new NullabilityInfoContext().Create(c).WriteState is NullabilityState.Nullable) p.IsNullable = true; } } } }, db => { db.GetConnection(CommonConstants.LOCAL_LOGGING_DB_ID).Aop.OnLogExecuting = (sql, parameters) => { _logger.Debug($"{CommonConstants.LOCAL_LOGGING_DB_ID} 准备执行语句:{sql}"); _logger.Debug(string.Join(", ", parameters.Select(p => $"{p.ParameterName} = {p.Value}").ToList())); }; db.GetConnection(CommonConstants.DB_ID).Aop.OnLogExecuting = (sql, parameters) => { _logger.Debug($"{CommonConstants.DB_ID} 准备执行语句:{sql}"); _logger.Debug(string.Join(", ", parameters.Select(p => $"{p.ParameterName} = {p.Value}").ToList())); }; }); ... protected override async Task ExecuteAsync(CancellationToken stoppingToken) { while (!stoppingToken.IsCancellationRequested) { var taskList = new List<Task>(); try { foreach (var svcInfo in _ifInfos) { if (svcInfo.svcType is "SomeType") taskList.Add(Task.Factory.StartNew(() => SyncReport<SomeEntity>(svcInfo.svcID, svcInfo.svcAddress, svcInfo.svcOtherParam), stoppingToken)); else if (headerInfo.ServiceType is "OtherType") { taskList.Add(Task.Factory.StartNew( () => SyncReport<OtherEntity>(svcInfo.svcID, svcInfo.svcAddress, svcInfo.svcOtherParam), stoppingToken)); taskList.Add(Task.Factory.StartNew( () => SyncReport<AnotherEntity>(svcInfo.svcID, svcInfo.svcAddress, svcInfo.svcOtherParam), stoppingToken)); } } await Task.WhenAll(taskList); } catch (Exception e) { _logger.LogError("在执行导入任务时发生异常:{}", e.Message); } finally { taskList.Clear(); } } } private void SyncReport<T>(long svcId, string svcAddr, string para) where T: BaseEntity, new() { ... try { var logDb = _dbClient.AsTenant().GetConnectionScope(CommonConstants.LOCAL_LOGGING_DB_ID).CopyNew(); // <---- 1 var lastReportTime = db.Queryable<dynamic>() // <----------------------------------------------------------- 2 .Select(it => new { last_date = SqlFunc.MappingColumn(default(DateTime?), "MAX(`LOG_TIME`)") }) .Where("`SVCID` = @SVCID", new { SVCID = svcId }) .First(); var dataList = ...; // <-- 根据上面获取到的最后记录时间,调用 WebService 获取最新的数据 var db = _dbClient.AsTenant().GetConnectionScope(CommonConstants.DB_ID).CopyNew(); // <--------------------- 3 foreach (var data in dataList) { //_dbClient.AsTenant().BeginTran(); logDb.BeginTran(); db.BeginTran(); try { if (!db.Queryable<T>().WhereClassByPrimaryKey(data).Any()) { db.Insertable(headerEntity).ExecuteCommand(); } if (!logDb.Queryable<THeader>().WhereClassByPrimaryKey(headerEntity).Any()) { logDb.Insertable(headerEntity).ExecuteCommand(); } //_dbClient.AsTenant().CommitTran(); // <----------------------------------------------------------- 4 logDb.CommitTran(); db.CommitTran(); } catch (SqlSugarException dbe) { //_dbClient.AsTenant().RollbackTran(); logDb.RollbackTran(); db.RollbackTran(); _logger.LogError("在导入数据时发生数据库异常:{}。", dbe.Message); } catch (Exception) { //_dbClient.AsTenant().RollbackTran(); logDb.RollbackTran(); db.RollbackTran(); throw; } } } catch (Exception e) { _logger.LogError("在导入数据时发生其它异常:{}。", e.Message); } ... }
热忱回答(4)
-
fate sta VIP0
2022/12/3TaskWhenAll必须加CopyNew
0 回复 -
fate sta VIP0
2022/12/3文档有介绍
0 回复 -
fate sta VIP0
2022/12/3https://www.donet5.com/Home/Doc?typeId=2349
0 回复 -
Rabbituzki VIP0
2022/12/4@fate sta:明白了,非常感谢!
0 回复