浏览代码

Merge branch 'test' into test_tj

tangjiang 4 月之前
父节点
当前提交
afcdf040dc

+ 1 - 0
.gitignore

@@ -344,3 +344,4 @@ ASALocalRun/
 
 # BeatPulse healthcheck temp database
 healthchecksdb
+/merge.ps1

+ 226 - 53
src/Hotline.Api/Controllers/Bi/BiOrderController.cs

@@ -40,6 +40,8 @@ using XF.Domain.Exceptions;
 using XF.Domain.Filters;
 using XF.Domain.Repository;
 using XF.Utility.EnumExtensions;
+using DocumentFormat.OpenXml.Drawing;
+using DocumentFormat.OpenXml.Bibliography;
 
 namespace Hotline.Api.Controllers.Bi
 {
@@ -1880,21 +1882,82 @@ namespace Hotline.Api.Controllers.Bi
             if (callData != null)
                 callData.InvalidCount = callData.InvalidCount - callData.QueueByeCount - callData.IvrByeCount;
             centerReportStatisticsDto.CenterReportCall = callData;
+			#endregion
+
+			#region 语音分类
+			var callTypeDto = await _trCallRecordRepository.Queryable()
+			.Where(x => x.CreatedTime >= StartTime && x.CreatedTime <= EndTime && SqlFunc.Length(x.Gateway) > 4 && x.CallDirection == ECallDirection.In)
+			.GroupBy(x => x.CreatedTime.ToString("yyyy-MM-dd"))
+				.Select(x => new IVRCallTypeDto()
+				{
+					PersonCallInCount = SqlFunc.AggregateSum(SqlFunc.IIF(x.IvrDtmf.Substring(x.IvrDtmf.Length - 1, 1) == "1", 1, 0)),
+					EnterpriseCallInCount = SqlFunc.AggregateSum(SqlFunc.IIF(x.IvrDtmf.Substring(x.IvrDtmf.Length - 1, 1) == "2", 1, 0)),
+					AiCallInCount = SqlFunc.AggregateSum(SqlFunc.IIF(x.Gateway == "82826886", 1, 0)),
+				}).FirstAsync();
+            centerReportStatisticsDto.iVRCallTypeDto = callTypeDto;
             #endregion
 
             #region 工单
-            //工单
+            //工单 信件情况
             var orderData = await _orderRepository.Queryable()
-                .Where(p => p.CreationTime >= StartTime && p.CreationTime <= EndTime)
-                .Select(x => new CenterReportOrderDto
-                {
+				.LeftJoin<SystemOrganize>((x,so) => x.ActualHandleOrgCode == so.Id)
+                .Where((x, so) => x.CreationTime >= StartTime && x.CreationTime <= EndTime)
+                .Select((x, so) => new CenterReportOrderDto
+				{
                     EffectiveCount = SqlFunc.AggregateSum(SqlFunc.IIF(true, 1, 0)),
                     InvalidCount = 0,
                     CompletedCount = SqlFunc.AggregateSum(SqlFunc.IIF(x.Status >= EOrderStatus.Filed, 1, 0)),
-                    InProgressCount = SqlFunc.AggregateSum(SqlFunc.IIF(x.Status < EOrderStatus.Filed, 1, 0))
-                })
+                    InProgressCount = SqlFunc.AggregateSum(SqlFunc.IIF(x.Status < EOrderStatus.Filed, 1, 0)),
+					CityAccept = SqlFunc.AggregateSum(SqlFunc.IIF(so.OrgType == EOrgType.City, 1, 0)),
+					CountyAccept = SqlFunc.AggregateSum(SqlFunc.IIF(so.OrgType == EOrgType.County, 1, 0)),
+					CenterAccept = SqlFunc.AggregateSum(SqlFunc.IIF(so.IsCenter, 1, 0)),
+				})
                 .FirstAsync();
             centerReportStatisticsDto.CenterReportOrder = orderData;
+
+
+			//工单按时办结情况
+			var orderCompletedData = await _orderRepository.Queryable()
+				.LeftJoin<SystemOrganize>((x, so) => x.FileUserOrgId == so.Id)
+				.Where((x, so) => x.CreationTime >= StartTime && x.CreationTime <= EndTime && x.Status >=  EOrderStatus.Filed)
+				.Select((x, so) => new OrderCompletedDto
+				{
+					CompletedCount = SqlFunc.AggregateSum(SqlFunc.IIF(x.Status >= EOrderStatus.Filed, 1, 0)),
+					ExpiredTimeCompletedCount = SqlFunc.AggregateSum(SqlFunc.IIF(x.Status >= EOrderStatus.Filed && x.ExpiredTime > x.ActualHandleTime, 1, 0)),//超期已办
+					CityExpiredTimeCompletedCount = SqlFunc.AggregateSum(SqlFunc.IIF(x.Status >= EOrderStatus.Filed && x.ExpiredTime > x.ActualHandleTime && so.OrgType == EOrgType.City, 1, 0)),//市级超期已办
+					CountyExpiredTimeCompletedCount = SqlFunc.AggregateSum(SqlFunc.IIF(x.Status >= EOrderStatus.Filed && x.ExpiredTime > x.ActualHandleTime && so.OrgType == EOrgType.County, 1, 0)),//区县超期已办
+					CenterExpiredTimeCompletedCount = SqlFunc.AggregateSum(SqlFunc.IIF(x.Status >= EOrderStatus.Filed && x.ExpiredTime > x.ActualHandleTime && so.IsCenter, 1, 0)),//中心超期已办
+					CityCompletedCount = SqlFunc.AggregateSum(SqlFunc.IIF(x.Status >= EOrderStatus.Filed && so.OrgType == EOrgType.City, 1, 0)),
+					CountyCompletedCount = SqlFunc.AggregateSum(SqlFunc.IIF(x.Status >= EOrderStatus.Filed && so.OrgType == EOrgType.County, 1, 0)),
+					CenterCompletedCount = SqlFunc.AggregateSum(SqlFunc.IIF(x.Status >= EOrderStatus.Filed && so.IsCenter, 1, 0)),
+				})
+				.FirstAsync();
+            centerReportStatisticsDto.orderCompletedDto = orderCompletedData;
+
+            //工单办理时效
+            var orderAgingData = await _orderRepository.Queryable()
+				.LeftJoin<SystemOrganize>((x, so) => x.FileUserOrgId == so.Id)
+				.Where((x, so) => x.CreationTime >= StartTime && x.CreationTime <= EndTime && x.Status >= EOrderStatus.Filed)
+                .Select((x, so) => new {
+					FileOrgIsCenter = x.FileOrgIsCenter.Value,
+					CreationTimeHandleDurationWorkday = x.CreationTimeHandleDurationWorkday.HasValue? x.CreationTimeHandleDurationWorkday : 0,
+					CenterToOrgHandleDurationWorkday = x.CenterToOrgHandleDurationWorkday.HasValue ? x.CenterToOrgHandleDurationWorkday : 0,
+					OrgType = so.OrgType
+				})
+                .MergeTable()
+				.Select(temp => new OrderAgingDto
+				{
+                    OrderCount  = SqlFunc.AggregateSum(SqlFunc.IIF(true, 1, 0)),
+					CompletedAging = SqlFunc.AggregateSum(SqlFunc.IIF(temp.FileOrgIsCenter, temp.CreationTimeHandleDurationWorkday, temp.CenterToOrgHandleDurationWorkday)),
+					CityOrderCount = SqlFunc.AggregateSum(SqlFunc.IIF(temp.FileOrgIsCenter == false && temp.OrgType == EOrgType.City, 1, 0)),//市级
+					CityCompletedAging = SqlFunc.AggregateSum(SqlFunc.IIF(temp.FileOrgIsCenter == false  && temp.OrgType == EOrgType.City, temp.CenterToOrgHandleDurationWorkday,0)),
+					CountyOrderCount = SqlFunc.AggregateSum(SqlFunc.IIF(temp.FileOrgIsCenter == false && temp.OrgType == EOrgType.County, 1, 0)),//区县
+					CountyCompletedAging = SqlFunc.AggregateSum(SqlFunc.IIF(temp.FileOrgIsCenter == false && temp.OrgType == EOrgType.County, temp.CenterToOrgHandleDurationWorkday, 0)),
+					CenterOrderCount = SqlFunc.AggregateSum(SqlFunc.IIF(temp.FileOrgIsCenter, 1, 0)),//中心
+					CenterCompletedAging = SqlFunc.AggregateSum(SqlFunc.IIF(temp.FileOrgIsCenter, temp.CreationTimeHandleDurationWorkday, 0)),
+				})
+				.FirstAsync();
+            centerReportStatisticsDto.orderAgingDto = orderAgingData;
             #endregion
 
             #region 信件来源
@@ -1942,14 +2005,18 @@ namespace Hotline.Api.Controllers.Bi
                 .Where(p => p.CreationTime >= StartTime && p.CreationTime <= EndTime)
                 .Select(it => new
                 {
-                    AcceptTypeCode = SqlFunc.IIF(SqlFunc.IsNullOrEmpty(it.AcceptTypeCode), "40", it.AcceptTypeCode)
+                    AcceptTypeCode = SqlFunc.IIF(SqlFunc.IsNullOrEmpty(it.AcceptTypeCode), "40", it.AcceptTypeCode),
+                    FileOrgIsCenter = it.FileOrgIsCenter.HasValue ? it.FileOrgIsCenter : true,
+                    CreationTimeHandleDurationWorkday = it.CreationTimeHandleDurationWorkday.HasValue ? it.CenterToOrgHandleDurationWorkday : 0,
+                    CenterToOrgHandleDurationWorkday = it.CenterToOrgHandleDurationWorkday.HasValue ? it.CenterToOrgHandleDurationWorkday : 0,
                 })
                 .MergeTable()//将查询出来的结果合并成一个新表
-                 .GroupBy(it => new { it.AcceptTypeCode })//对新表进行分组
-                 .Select(it => new CenterReportOrderSourceChannelDto
+                 .GroupBy(temp => new { temp.AcceptTypeCode })//对新表进行分组
+                 .Select(temp => new CenterReportOrderSourceChannelDto
                  {
-                     Code = it.AcceptTypeCode,
-                     CountNum = SqlFunc.AggregateCount(it.AcceptTypeCode)
+                     Code = temp.AcceptTypeCode,
+                     CountNum = SqlFunc.AggregateCount(temp.AcceptTypeCode),
+                     CompletedAging = SqlFunc.AggregateSum(SqlFunc.IIF(temp.FileOrgIsCenter == true, temp.CreationTimeHandleDurationWorkday, temp.CenterToOrgHandleDurationWorkday))
                  })
                  .ToListAsync();
             List<CenterReportOrderSourceChannelDto> acceptType = new();
@@ -1961,8 +2028,9 @@ namespace Hotline.Api.Controllers.Bi
                     AllCountNum = sourceChannelCount,
                     Name = item.DicDataName,
                     Code = item.DicTypeCode,
-                    CountNum = acceptTypeData.Find(p => p.Code == item.DicDataValue)?.CountNum ?? 0
-                });
+                    CountNum = acceptTypeData.Find(p => p.Code == item.DicDataValue)?.CountNum ?? 0,
+					CompletedAging = acceptTypeData.Find(p => p.Code == item.DicDataValue)?.CompletedAging ?? 0
+				});
             }
 
             centerReportStatisticsDto.CenterReportOrderAcceptTypes = acceptType;
@@ -1977,49 +2045,101 @@ namespace Hotline.Api.Controllers.Bi
                 WaitVisitd = await _orderVisitRepository.Queryable()
              .Where(x => x.VisitTime >= StartTime && x.VisitTime <= EndTime && x.VisitState != EVisitState.None && x.VisitState != EVisitState.Visited).CountAsync()
             };
-
-            //部门
-            var listOrg = await _orderVisitDetailRepository.Queryable()
+            //
+            var data = await _orderVisitDetailRepository.Queryable()
                 .LeftJoin<OrderVisit>((it, o) => it.VisitId == o.Id)
-                .Where((it, o) => it.VisitTarget == EVisitTarget.Org && o.VisitTime >= StartTime && o.VisitTime <= EndTime && o.VisitState == EVisitState.Visited)
-                 .Select((it, o) => new Satisfaction
+                .LeftJoin<SystemOrganize>((it, o, so) => it.VisitOrgCode == so.Id)
+                .Where((it, o, so) => it.VisitTarget == EVisitTarget.Org && o.VisitTime >= StartTime && o.VisitTime <= EndTime && o.VisitState == EVisitState.Visited)
+                 .Select((it, o, so) => new
                  {
                      Dissatisfied = SqlFunc.AggregateSum(SqlFunc.IIF(SqlFunc.JsonListObjectAny(it.OrgProcessingResults, "key", "1") || SqlFunc.JsonListObjectAny(it.OrgProcessingResults, "key", "2"), 1, 0)),
                      Satisfied = SqlFunc.AggregateSum(SqlFunc.IIF(SqlFunc.JsonListObjectAny(it.OrgProcessingResults, "key", "1") || SqlFunc.JsonListObjectAny(it.OrgProcessingResults, "key", "2"), 0, 1)),
+                     CityDissatisfied = SqlFunc.AggregateSum(SqlFunc.IIF((SqlFunc.JsonListObjectAny(it.OrgProcessingResults, "key", "1") || SqlFunc.JsonListObjectAny(it.OrgProcessingResults, "key", "2")) && so.OrgType == EOrgType.City, 1, 0)),
+                     CitySatisfied = SqlFunc.AggregateSum(SqlFunc.IIF(!SqlFunc.JsonListObjectAny(it.OrgProcessingResults, "key", "1") && !SqlFunc.JsonListObjectAny(it.OrgProcessingResults, "key", "2") && so.OrgType == EOrgType.City, 1, 0)),
+                     CountyDissatisfied = SqlFunc.AggregateSum(SqlFunc.IIF((SqlFunc.JsonListObjectAny(it.OrgProcessingResults, "key", "1") || SqlFunc.JsonListObjectAny(it.OrgProcessingResults, "key", "2")) && so.OrgType == EOrgType.County, 1, 0)),
+                     CountySatisfied = SqlFunc.AggregateSum(SqlFunc.IIF(!SqlFunc.JsonListObjectAny(it.OrgProcessingResults, "key", "1") && !SqlFunc.JsonListObjectAny(it.OrgProcessingResults, "key", "2") && so.OrgType == EOrgType.County, 1, 0)),
+                     CenterDissatisfied = SqlFunc.AggregateSum(SqlFunc.IIF((SqlFunc.JsonListObjectAny(it.OrgProcessingResults, "key", "1") || SqlFunc.JsonListObjectAny(it.OrgProcessingResults, "key", "2")) && so.IsCenter, 1, 0)),
+                     CenterSatisfied = SqlFunc.AggregateSum(SqlFunc.IIF(!SqlFunc.JsonListObjectAny(it.OrgProcessingResults, "key", "1") && !SqlFunc.JsonListObjectAny(it.OrgProcessingResults, "key", "2") && so.IsCenter, 1, 0)),
+                     OrgDissatisfied = SqlFunc.AggregateSum(SqlFunc.IIF((SqlFunc.JsonListObjectAny(it.OrgProcessingResults, "key", "1") || SqlFunc.JsonListObjectAny(it.OrgProcessingResults, "key", "2")) && !so.IsCenter, 1, 0)),
+                     OrgSatisfied = SqlFunc.AggregateSum(SqlFunc.IIF(!SqlFunc.JsonListObjectAny(it.OrgProcessingResults, "key", "1") && !SqlFunc.JsonListObjectAny(it.OrgProcessingResults, "key", "2") && !so.IsCenter, 1, 0)),
                  })
-                .ToListAsync();
-
-            if (listOrg != null && listOrg.Count > 0)
-            {
-                var SatisfiedCount = listOrg[0].Satisfied + listOrg[0].Satisfied;
-                if (SatisfiedCount > 0 && listOrg[0].Satisfied > 0)
-                    centerReportVisitd.OrgRate = Math.Round((listOrg[0].Satisfied / (double)SatisfiedCount) * 100, 2);
-            }
-
-            //if (centerReportVisitd.Visitd > 0 && listOrg != null && listOrg.Count > 0 && listOrg[0].Satisfied > 0)
-            //centerReportVisitd.OrgRate = Math.Round((listOrg[0].Satisfied / (double)centerReportVisitd.Visitd) * 100, 2);
-
-            //坐席
-            var listSet = await _orderVisitDetailRepository.Queryable()
-                .LeftJoin<OrderVisit>((it, o) => it.VisitId == o.Id)
-                .Where((it, o) => it.VisitTarget == EVisitTarget.Seat && o.VisitTime >= StartTime && o.VisitTime <= EndTime && o.VisitState == EVisitState.Visited)
-                .Select((it, o) => new Satisfaction
-                {
-                    Dissatisfied = SqlFunc.AggregateSum(SqlFunc.IIF(it.SeatEvaluate == ESeatEvaluate.NoSatisfied, 1, 0)),
-                    Satisfied = SqlFunc.AggregateSum(SqlFunc.IIF(it.SeatEvaluate != ESeatEvaluate.NoSatisfied, 1, 0)),
-                }).ToListAsync();
-
-            if (listSet != null && listSet.Count > 0)
-            {
-                var SatisfiedCount = listSet[0].Satisfied + listSet[0].Satisfied;
-                if (SatisfiedCount > 0 && listSet[0].Satisfied > 0)
-                    centerReportVisitd.OrgRate = Math.Round((listSet[0].Satisfied / (double)SatisfiedCount) * 100, 2);
-            }
-
-            //if (centerReportVisitd.Visitd > 0 && listSet != null && listSet.Count > 0 && listSet[0].Satisfied > 0)
-            //    centerReportVisitd.SeatsRate = Math.Round((listSet[0].Satisfied / (double)centerReportVisitd.Visitd) * 100, 2);
-
-            centerReportStatisticsDto.CenterReportVisitd = centerReportVisitd;
+                .FirstAsync();
+            if (data.Satisfied > 0)
+            {
+                var count = data.Satisfied + data.Dissatisfied;
+				centerReportVisitd.AllRate = Math.Round((data.Satisfied / (double)count) * 100, 2);
+			}
+			if (data.OrgSatisfied > 0)
+			{
+				var count = data.OrgSatisfied + data.OrgDissatisfied;
+				centerReportVisitd.OrgRate = Math.Round((data.OrgSatisfied / (double)count) * 100, 2);
+			}
+
+			if (data.CitySatisfied > 0)
+			{
+				var count = data.CitySatisfied + data.CityDissatisfied;
+				centerReportVisitd.CityRate = Math.Round((data.CitySatisfied / (double)count) * 100, 2);
+			}
+
+			if (data.CountySatisfied > 0)
+			{
+				var count = data.CountySatisfied + data.CountyDissatisfied;
+				centerReportVisitd.CountyRate = Math.Round((data.CountySatisfied / (double)count) * 100, 2);
+			}
+
+			if (data.CenterSatisfied > 0)
+			{
+				var count = data.CenterSatisfied + data.CenterDissatisfied;
+				centerReportVisitd.CenterRate = Math.Round((data.CenterSatisfied / (double)count) * 100, 2);
+			}
+            centerReportVisitd.Dissatisfied = data.Dissatisfied;
+            centerReportVisitd.CityDissatisfied = data.CityDissatisfied;
+            centerReportVisitd.CountyDissatisfied = data.CountyDissatisfied;
+
+
+
+			//部门
+			//var listOrg = await _orderVisitDetailRepository.Queryable()
+			//    .LeftJoin<OrderVisit>((it, o) => it.VisitId == o.Id)
+			//    .Where((it, o) => it.VisitTarget == EVisitTarget.Org && o.VisitTime >= StartTime && o.VisitTime <= EndTime && o.VisitState == EVisitState.Visited)
+			//     .Select((it, o) => new Satisfaction
+			//     {
+			//         Dissatisfied = SqlFunc.AggregateSum(SqlFunc.IIF(SqlFunc.JsonListObjectAny(it.OrgProcessingResults, "key", "1") || SqlFunc.JsonListObjectAny(it.OrgProcessingResults, "key", "2"), 1, 0)),
+			//         Satisfied = SqlFunc.AggregateSum(SqlFunc.IIF(SqlFunc.JsonListObjectAny(it.OrgProcessingResults, "key", "1") || SqlFunc.JsonListObjectAny(it.OrgProcessingResults, "key", "2"), 0, 1)),
+			//     })
+			//    .ToListAsync();
+
+			//if (listOrg != null && listOrg.Count > 0)
+			//{
+			//    var SatisfiedCount = listOrg[0].Satisfied + listOrg[0].Satisfied;
+			//    if (SatisfiedCount > 0 && listOrg[0].Satisfied > 0)
+			//        centerReportVisitd.OrgRate = Math.Round((listOrg[0].Satisfied / (double)SatisfiedCount) * 100, 2);
+			//}
+
+			////if (centerReportVisitd.Visitd > 0 && listOrg != null && listOrg.Count > 0 && listOrg[0].Satisfied > 0)
+			////centerReportVisitd.OrgRate = Math.Round((listOrg[0].Satisfied / (double)centerReportVisitd.Visitd) * 100, 2);
+
+			////坐席
+			//var listSet = await _orderVisitDetailRepository.Queryable()
+			//    .LeftJoin<OrderVisit>((it, o) => it.VisitId == o.Id)
+			//    .Where((it, o) => it.VisitTarget == EVisitTarget.Seat && o.VisitTime >= StartTime && o.VisitTime <= EndTime && o.VisitState == EVisitState.Visited)
+			//    .Select((it, o) => new Satisfaction
+			//    {
+			//        Dissatisfied = SqlFunc.AggregateSum(SqlFunc.IIF(it.SeatEvaluate == ESeatEvaluate.NoSatisfied, 1, 0)),
+			//        Satisfied = SqlFunc.AggregateSum(SqlFunc.IIF(it.SeatEvaluate != ESeatEvaluate.NoSatisfied, 1, 0)),
+			//    }).ToListAsync();
+
+			//if (listSet != null && listSet.Count > 0)
+			//{
+			//    var SatisfiedCount = listSet[0].Satisfied + listSet[0].Satisfied;
+			//    if (SatisfiedCount > 0 && listSet[0].Satisfied > 0)
+			//        centerReportVisitd.OrgRate = Math.Round((listSet[0].Satisfied / (double)SatisfiedCount) * 100, 2);
+			//}
+
+			//if (centerReportVisitd.Visitd > 0 && listSet != null && listSet.Count > 0 && listSet[0].Satisfied > 0)
+			//    centerReportVisitd.SeatsRate = Math.Round((listSet[0].Satisfied / (double)centerReportVisitd.Visitd) * 100, 2);
+
+			centerReportStatisticsDto.CenterReportVisitd = centerReportVisitd;
             #endregion
 
             #region 信件分布情况
@@ -2079,7 +2199,60 @@ namespace Hotline.Api.Controllers.Bi
             };
             #endregion
 
-            return centerReportStatisticsDto;
+            #region 企业服务办件情况
+            var enterpriseOrderDto = await _orderRepository.Queryable()
+                .LeftJoin<SystemOrganize>((x, so) => x.ActualHandleOrgCode == so.Id)
+                .Where((x, so) => x.CreationTime >= StartTime && x.CreationTime <= EndTime && x.IdentityType == EIdentityType.Enterprise)
+                .Select((x, so) => new
+                {
+                    FileOrgIsCenter = x.FileOrgIsCenter.Value,
+                    CreationTimeHandleDurationWorkday = x.CreationTimeHandleDurationWorkday.HasValue ? x.CreationTimeHandleDurationWorkday : 0,
+                    CenterToOrgHandleDurationWorkday = x.CenterToOrgHandleDurationWorkday.HasValue ? x.CenterToOrgHandleDurationWorkday : 0,
+                    OrgType = so.OrgType
+                })
+                .MergeTable()
+                .Select(temp => new EnterpriseOrderDto
+                {
+                    OrderCount = SqlFunc.AggregateSum(SqlFunc.IIF(true, 1, 0)),
+                    CompletedAging = SqlFunc.AggregateSum(SqlFunc.IIF(temp.FileOrgIsCenter, temp.CreationTimeHandleDurationWorkday, temp.CenterToOrgHandleDurationWorkday)),
+                    CityOrderCount = SqlFunc.AggregateSum(SqlFunc.IIF(temp.FileOrgIsCenter == false && temp.OrgType == EOrgType.City, 1, 0)),//市级
+                    CityCompletedAging = SqlFunc.AggregateSum(SqlFunc.IIF(temp.FileOrgIsCenter == false && temp.OrgType == EOrgType.City, temp.CenterToOrgHandleDurationWorkday, 0)),
+                    CountyOrderCount = SqlFunc.AggregateSum(SqlFunc.IIF(temp.FileOrgIsCenter == false && temp.OrgType == EOrgType.County, 1, 0)),//区县
+                    CountyCompletedAging = SqlFunc.AggregateSum(SqlFunc.IIF(temp.FileOrgIsCenter == false && temp.OrgType == EOrgType.County, temp.CenterToOrgHandleDurationWorkday, 0)),
+                    CenterOrderCount = SqlFunc.AggregateSum(SqlFunc.IIF(temp.FileOrgIsCenter, 1, 0)),//中心
+                    CenterCompletedAging = SqlFunc.AggregateSum(SqlFunc.IIF(temp.FileOrgIsCenter, temp.CreationTimeHandleDurationWorkday, 0)),
+                })
+                .FirstAsync();
+
+			centerReportStatisticsDto.enterpriseOrderDto = enterpriseOrderDto;
+			var enterpriseOrderDto2 = await _orderVisitDetailRepository.Queryable()
+                .Includes(it=>it.OrderVisit,ov=>ov.Order)
+				.LeftJoin<SystemOrganize>((it, so) => it.VisitOrgCode == so.Id)
+				.Where((it, so) => it.VisitTarget == EVisitTarget.Org && it.OrderVisit.VisitTime >= StartTime && it.OrderVisit.VisitTime <= EndTime && it.OrderVisit.VisitState == EVisitState.Visited)
+                .GroupBy((it,so)=>it.Id)
+				 .Select((it, so) => new EnterpriseOrderDto
+				 {
+					 VisitdCount = SqlFunc.AggregateSum(SqlFunc.IIF(true, 1, 0)),
+					 Dissatisfied = SqlFunc.AggregateSum(SqlFunc.IIF(SqlFunc.JsonListObjectAny(it.OrgProcessingResults, "key", "1") || SqlFunc.JsonListObjectAny(it.OrgProcessingResults, "key", "2"), 1, 0)),
+					 Satisfied = SqlFunc.AggregateSum(SqlFunc.IIF(!SqlFunc.JsonListObjectAny(it.OrgProcessingResults, "key", "1") &&  !SqlFunc.JsonListObjectAny(it.OrgProcessingResults, "key", "2"), 1, 0)),
+					 CityDissatisfied = SqlFunc.AggregateSum(SqlFunc.IIF((SqlFunc.JsonListObjectAny(it.OrgProcessingResults, "key", "1") || SqlFunc.JsonListObjectAny(it.OrgProcessingResults, "key", "2")) && so.OrgType == EOrgType.City, 1, 0)),
+					 CitySatisfied = SqlFunc.AggregateSum(SqlFunc.IIF(!SqlFunc.JsonListObjectAny(it.OrgProcessingResults, "key", "1") && !SqlFunc.JsonListObjectAny(it.OrgProcessingResults, "key", "2") && so.OrgType == EOrgType.City, 1, 0)),
+					 CountyDissatisfied = SqlFunc.AggregateSum(SqlFunc.IIF((SqlFunc.JsonListObjectAny(it.OrgProcessingResults, "key", "1") || SqlFunc.JsonListObjectAny(it.OrgProcessingResults, "key", "2")) && so.OrgType == EOrgType.County, 1, 0)),
+					 CountySatisfied = SqlFunc.AggregateSum(SqlFunc.IIF(!SqlFunc.JsonListObjectAny(it.OrgProcessingResults, "key", "1") && !SqlFunc.JsonListObjectAny(it.OrgProcessingResults, "key", "2") && so.OrgType == EOrgType.County, 1, 0)),
+				 })
+				.FirstAsync();
+
+            centerReportStatisticsDto.enterpriseOrderDto.VisitdCount = enterpriseOrderDto2.VisitdCount;
+			centerReportStatisticsDto.enterpriseOrderDto.Dissatisfied = enterpriseOrderDto2.Dissatisfied;
+			centerReportStatisticsDto.enterpriseOrderDto.CityDissatisfied = enterpriseOrderDto2.CityDissatisfied;
+			centerReportStatisticsDto.enterpriseOrderDto.CountyDissatisfied = enterpriseOrderDto2.CountyDissatisfied;
+			centerReportStatisticsDto.enterpriseOrderDto.Satisfied = enterpriseOrderDto2.Satisfied;
+			centerReportStatisticsDto.enterpriseOrderDto.CitySatisfied = enterpriseOrderDto2.CitySatisfied;
+			centerReportStatisticsDto.enterpriseOrderDto.CountySatisfied = enterpriseOrderDto2.CountySatisfied;
+
+			#endregion
+
+			return centerReportStatisticsDto;
         }
 
         /// <summary>
@@ -2165,7 +2338,7 @@ namespace Hotline.Api.Controllers.Bi
             {
                 var satisfiedCount = listSet.Satisfied + listSet.Dissatisfied;
                 if (satisfiedCount > 0 && listSet.Satisfied > 0)
-                    centerReportVisitd.OrgRate = Math.Round((listSet.Satisfied / (double)satisfiedCount) * 100, 2);
+                    centerReportVisitd.SeatsRate = Math.Round((listSet.Satisfied / (double)satisfiedCount) * 100, 2);
             }
 
             centerReportStatisticsDto.CenterReportVisitd = centerReportVisitd;

+ 2 - 1
src/Hotline.Api/Controllers/CommonPController.cs

@@ -498,7 +498,8 @@ namespace Hotline.Api.Controllers
 				.Includes(x => x.OrderVisit, y => y.Employee)
 				.Includes(x => x.OrderScreens)
 				.Where(x => x.OrderScreens.Any(s => s.Status == EScreenStatus.SendBack && s.ScreenType ==  EOrderScreenType.Org && s.SendBackApply == true) || x.OrderScreens.Any() == false)
-				.Where(x => x.OrderVisit.VisitState == EVisitState.Visited && x.OrderVisit.IsCanHandle)
+                .Where(x => x.OrderVisit.Order.ReceiveProvinceNo.StartsWith("ZGZFW") == false || string.IsNullOrEmpty(x.OrderVisit.Order.ReceiveProvinceNo))
+                .Where(x => x.OrderVisit.VisitState == EVisitState.Visited && x.OrderVisit.IsCanHandle)
 				.Where(x => x.VisitTarget == EVisitTarget.Org && x.VisitOrgCode == _sessionContext.OrgId && (
 					SqlFunc.JsonField(x.OrgProcessingResults, "Key") == "1" ||
 					SqlFunc.JsonField(x.OrgProcessingResults, "Key") == "2" ||

+ 1 - 1
src/Hotline.Api/Controllers/OrderController.cs

@@ -538,7 +538,7 @@ public class OrderController : BaseController
             orderVisit.EmployeeId = string.Empty;
         }
 
-        if (order is { ProcessType: EProcessType.Zhiban, CounterSignType: null } && !order.IsProvince)
+        if (order is { FileOrgIsCenter:true, CounterSignType: null } && !order.IsProvince)
         {
             orderVisit.VisitState = EVisitState.Visited;
             orderVisit.VisitTime = DateTime.Now;

+ 6 - 2
src/Hotline.Application.Tests/Startup.cs

@@ -59,6 +59,9 @@ using Hotline.Application.Tests.SqlSuger;
 using Microsoft.AspNetCore.Http;
 using Hotline.WeChat;
 using Hotline.Api.Controllers.Snapshot;
+using Hotline.Orders.DatabaseEventHandler;
+using Hotline.Orders;
+using XF.Domain.Repository.Events;
 
 namespace Hotline.Application.Tests;
 public class Startup
@@ -151,9 +154,10 @@ public class Startup
                 .ToList()
                 .ForEach(d => ServiceRegister.Register(services, d));
 
-            //services.AddScoped<IThirdIdentiyService, WeChatService>();
-            services.AddScoped<IThirdIdentiyService, ThirdTestService>();
             // services.AddScoped<IThirdIdentiyService, WeChatService>();
+            services.AddScoped<IThirdIdentiyService, ThirdTestService>();
+
+            services.AddScoped<IUpdateDatabaseEvent<OrderVisitDetail>, OrderVisitDetailEventHandler>();
 
             //services.AddScoped<IThirdAccountRepository, ThirdAccountRepository>();
             services.AddApplication();

+ 1 - 1
src/Hotline.Application/Orders/OrderApplication.cs

@@ -3039,7 +3039,7 @@ public class OrderApplication : IOrderApplication, IScopeDependency
                          x.OrderScreens.Any() == false
              //|| x.OrderScreens.Any(s => (s.Status != EScreenStatus.SendBack && s.SendBackApply != true)) == false
              )
-             //.Where(x=> x.OrderVisit.Order.ReceiveProvinceNo.StartsWith("ZGZFW")==false)
+             .Where(x=> x.OrderVisit.Order.ReceiveProvinceNo.StartsWith("ZGZFW")==false || string.IsNullOrEmpty(x.OrderVisit.Order.ReceiveProvinceNo))
              .WhereIF(dto.ScreenType == EOrderScreenType.Seat, x => x.OrderVisit.Order.IsProvince == false)
              .WhereIF(dto.ScreenSendBack is 1,
                  x => x.OrderScreens.Any(s => s.Status == EScreenStatus.SendBack && s.ScreenType == dto.ScreenType && s.SendBackApply == true))

+ 6 - 3
src/Hotline.Application/Quality/QualityApplication.cs

@@ -290,7 +290,8 @@ namespace Hotline.Application.Quality
 										newDetail.Second = sentenceList.start;
 										newDetail.EndSecond = sentenceList.end == null ? 0 : sentenceList.end;
 										newDetail.Content = sentenceList.text;
-										detailsSentence.Add(newDetail);
+                                        if (newDetail.Second > 0)
+											detailsSentence.Add(newDetail);
 									}
 								}
 							}
@@ -309,7 +310,8 @@ namespace Hotline.Application.Quality
 										newDetail.Second = sentenceList.start;
 										newDetail.EndSecond = sentenceList.end == null ? 0 : sentenceList.end;
 										newDetail.Content = sentenceList.text;
-										detailsSentence.Add(newDetail);
+										if (newDetail.Second > 0)
+											detailsSentence.Add(newDetail);
 									}
 								}
 
@@ -317,7 +319,8 @@ namespace Hotline.Application.Quality
 						}
 						if (detailsSentence.Count == 0)
 						{
-							details.Add(detail);
+							if (detail.Second > 0)
+								details.Add(detail);
 						}
 						else
 						{

+ 2 - 2
src/Hotline.Application/StatisticalReport/OrderReportApplication.cs

@@ -1651,8 +1651,8 @@ namespace Hotline.Application.StatisticalReport
               {
                   OrgCode = IsCenter == true ? it.ActualHandleOrgCode.Substring(SqlFunc.MappingColumn<int>("0"), SqlFunc.MappingColumn<int>("6")) : it.ActualHandleOrgCode.Substring(0, _sessionContext.RequiredOrgId.Length + 3),
                   AcceptTypeCode = it.AcceptTypeCode,
-                  ProcessType = it.ProcessType,
-                  AllTime = it.ProcessType == EProcessType.Zhiban ? it.CreationTimeHandleDurationWorkday : it.CenterToOrgHandleDurationWorkday,
+                  ProcessType = it.FileOrgIsCenter.Value ? EProcessType.Zhiban : EProcessType.Jiaoban,
+                  AllTime = it.FileOrgIsCenter.Value ? it.CreationTimeHandleDurationWorkday : it.CenterToOrgHandleDurationWorkday,
                   FileOrgIsCenter = it.FileOrgIsCenter
               })
               .MergeTable()

+ 1 - 1
src/Hotline.Repository.SqlSugar/Orders/OrderRepository.cs

@@ -1539,7 +1539,7 @@ namespace Hotline.Repository.SqlSugar.Orders
                 .Where(x => x.OrderVisit.VisitState == EVisitState.Visited && x.VisitTarget == EVisitTarget.Org)
                 .WhereIF(hiddenOrder.Any(), x => !hiddenOrder.Contains(x.OrderVisit.Order.No))
                 .WhereIF(IsCenter == false, x => x.VisitOrgCode.StartsWith(orgId))
-                .WhereIF(dto.OrgVisitStatisticsType.HasValue, x => x.OrderVisit.Order.ProcessType == (EProcessType)((int)dto.OrgVisitStatisticsType))
+                .WhereIF(dto.OrgVisitStatisticsType.HasValue, x => x.OrderVisit.Order.FileOrgIsCenter == (dto.OrgVisitStatisticsType== EOrgVisitStatisticsType.CallCenter))
                 .WhereIF(dto.Keyword.NotNullOrEmpty(), x => x.OrderVisit.Order.Title.Contains(dto.Keyword)) // 根据关键字匹配
                 .WhereIF(dto.TypeCode != 0, x => x.OrderVisit.Order.IdentityType == (EIdentityType)dto.TypeCode)
                 //任务 218 市州通用-部门满意度明细:办件结果查询优化为多选

+ 564 - 30
src/Hotline.Share/Dtos/CallCenter/CenterReportStatisticsDto.cs

@@ -19,14 +19,34 @@ namespace Hotline.Share.Dtos.CallCenter
         public CenterReportCallDto CenterReportCall { get; set; }
 
         /// <summary>
-        /// 工单
+        /// 语音分类
         /// </summary>
-        public CenterReportOrderDto CenterReportOrder { get; set; }
+        public IVRCallTypeDto iVRCallTypeDto { get; set; }
+
+		/// <summary>
+		/// 工单
+		/// </summary>
+		public CenterReportOrderDto CenterReportOrder { get; set; }
 
         /// <summary>
-        /// 信件回访量
+        /// 按时办结情况
         /// </summary>
-        public CenterReportVisitdDto CenterReportVisitd { get; set; }
+        public OrderCompletedDto orderCompletedDto { get; set; }
+
+        /// <summary>
+        /// 办理时效
+        /// </summary>
+        public OrderAgingDto orderAgingDto { get; set; }
+
+		/// <summary>
+		/// 企业办件情况
+		/// </summary>
+		public EnterpriseOrderDto enterpriseOrderDto { get; set; }
+
+		/// <summary>
+		/// 信件回访量
+		/// </summary>
+		public CenterReportVisitdDto CenterReportVisitd { get; set; }
 
         /// <summary>
         /// 来源
@@ -139,9 +159,100 @@ namespace Hotline.Share.Dtos.CallCenter
         /// IVR挂断
         /// </summary>
         public int IvrByeCount { get; set; }
-    }
+
+
+		/// <summary>
+		/// 总体接通率
+		/// </summary>
+		public double AllEffectiveCountRate => AllEffectiveRate();
+
+		/// <summary>
+		/// 计算总体接通率
+		/// </summary>
+		/// <returns></returns>
+		public double AllEffectiveRate()
+		{
+			if (AllCallCount > 0 && EffectiveCount > 0)
+				return Math.Round(((double)EffectiveCount / AllCallCount) * 100, 2);
+			return 0;
+		}
+	}
 
     /// <summary>
+    /// 语音分类
+    /// </summary>
+    public class IVRCallTypeDto {
+
+		/// <summary>
+		/// 个人服务呼入总量
+		/// </summary>
+		public int PersonCallInCount { get; set; }
+
+		/// <summary>
+		/// 企业服务呼入总量
+		/// </summary>
+		public int EnterpriseCallInCount { get; set; }
+
+		/// <summary>
+		/// 智能应答呼入总量
+		/// </summary>
+		public int AiCallInCount { get; set; }
+
+
+		/// <summary>
+		/// 呼入电话量
+		/// </summary>
+		public int AllCallInCount => PersonCallInCount + EnterpriseCallInCount + AiCallInCount;
+
+		/// <summary>
+		/// 个人服务呼入总量 占比
+		/// </summary>
+		public double PersonCallInRate => GetPersonCallInRate();
+
+		/// <summary>
+		/// 个人服务呼入总量 占比
+		/// </summary>
+		/// <returns></returns>
+		public double GetPersonCallInRate()
+		{
+			if (AllCallInCount > 0 && PersonCallInCount > 0)
+				return Math.Round(((double)PersonCallInCount / AllCallInCount) * 100, 2);
+			return 0;
+		}
+
+		/// <summary>
+		/// 企业服务呼入总量 占比
+		/// </summary>
+		public double EnterpriseCallInRate => GetEnterpriseCallInRate();
+
+		/// <summary>
+		/// 企业服务呼入总量 占比
+		/// </summary>
+		/// <returns></returns>
+		public double GetEnterpriseCallInRate()
+		{
+			if (AllCallInCount > 0 && EnterpriseCallInCount > 0)
+				return Math.Round(((double)EnterpriseCallInCount / AllCallInCount) * 100, 2);
+			return 0;
+		}
+
+		/// <summary>
+		/// 智能应答呼入总量 占比
+		/// </summary>
+		public double AiCallInRate => GetAiCallInRate();
+
+		/// <summary>
+		/// 智能应答呼入总量 占比
+		/// </summary>
+		/// <returns></returns>
+		public double GetAiCallInRate()
+		{
+			if (AllCallInCount > 0 && AiCallInCount > 0)
+				return Math.Round(((double)AiCallInCount / AllCallInCount) * 100, 2);
+			return 0;
+		}
+	}
+    /// <summary>
     /// 工单数据
     /// </summary>
     public class CenterReportOrderDto
@@ -151,10 +262,15 @@ namespace Hotline.Share.Dtos.CallCenter
         /// </summary>
         public int AllCallCount => EffectiveCount + InvalidCount;
 
-        /// <summary>
-        /// 有效
-        /// </summary>
-        public int EffectiveCount { get; set; }
+		/// <summary>
+		/// 中心已办结
+		/// </summary>
+		public int CenterCompletedCount { get; set; }
+
+		/// <summary>
+		/// 有效
+		/// </summary>
+		public int EffectiveCount { get; set; }
 
         /// <summary>
         /// 无效
@@ -162,14 +278,79 @@ namespace Hotline.Share.Dtos.CallCenter
         public int InvalidCount { get; set; }
 
         /// <summary>
-        /// 已办结
-        /// </summary>
-        public int CompletedCount { get; set; }
-
-        /// <summary>
-        /// 按时办结
-        /// </summary>
-        public int OnTimeCompletedCount { get; set; }
+        /// 市级受理
+        /// </summary>
+        public int CityAccept { get; set; }
+
+		/// <summary>
+		/// 市级受理占比
+		/// </summary>
+		public double CityAcceptRate => GetCityAcceptRate();
+
+		/// <summary>
+		/// 市级受理占比
+		/// </summary>
+		/// <returns></returns>
+		public double GetCityAcceptRate()
+		{
+			if (CityAccept > 0 && AllCallCount > 0)
+				return Math.Round(((double)CityAccept / AllCallCount) * 100, 2);
+			return 0;
+		}
+
+		/// <summary>
+		/// 区县受理
+		/// </summary>
+		public int CountyAccept { get; set; }
+
+
+		/// <summary>
+		/// 区县受理占比
+		/// </summary>
+		public double CountyAcceptRate => GetCountyAcceptRate();
+
+		/// <summary>
+		/// 区县受理占比
+		/// </summary>
+		/// <returns></returns>
+		public double GetCountyAcceptRate()
+		{
+			if (CountyAccept > 0 && AllCallCount > 0)
+				return Math.Round(((double)CountyAccept / AllCallCount) * 100, 2);
+			return 0;
+		}
+
+		/// <summary>
+		/// 中心受理
+		/// </summary>
+		public int CenterAccept { get; set; }
+
+		/// <summary>
+		/// 中心受理占比
+		/// </summary>
+		public double CenterAcceptRate => GetCenterAcceptRate();
+
+		/// <summary>
+		/// 中心受理占比
+		/// </summary>
+		/// <returns></returns>
+		public double GetCenterAcceptRate()
+		{
+			if (CenterAccept > 0 && AllCallCount > 0)
+				return Math.Round(((double)CenterAccept / AllCallCount) * 100, 2);
+			return 0;
+		}
+
+
+		/// <summary>
+		/// 已办结
+		/// </summary>
+		public int CompletedCount { get; set; }
+
+		/// <summary>
+		/// 按时办结
+		/// </summary>
+		public int OnTimeCompletedCount { get; set; }
 
         /// <summary>
         /// 按时办结率
@@ -187,11 +368,6 @@ namespace Hotline.Share.Dtos.CallCenter
             return 0;
         }
 
-        /// <summary>
-        /// 中心已办结
-        /// </summary>
-        public int CenterCompletedCount { get; set; }
-
         /// <summary>
         /// 部门已办结
         /// </summary>
@@ -213,12 +389,316 @@ namespace Hotline.Share.Dtos.CallCenter
         public int OrgInProgressCount { get; set; }
 
 
-    }
+		/// <summary>
+		/// 总体办结率
+		/// </summary>
+		public double AllCompletedRate => GetAllCompletedRate();
+
+		public double GetAllCompletedRate()
+		{
+			if (CompletedCount > 0 && AllCallCount > 0)
+				return Math.Round(((double)CompletedCount / AllCallCount) * 100, 2);
+			return 0;
+		}
+
+	}
+
+    /// <summary>
+    /// 按时办结情况
+    /// </summary>
+    public class OrderCompletedDto {
+
+
+		/// <summary>
+		/// 已办结
+		/// </summary>
+		public int CompletedCount { get; set; }
+
+		/// <summary>
+		/// 市级已办结
+		/// </summary>
+		public int CityCompletedCount { get; set; }
+
+		/// <summary>
+		/// 区县已办结
+		/// </summary>
+		public int CountyCompletedCount { get; set; }
+
+		/// <summary>
+		/// 中心已办结
+		/// </summary>
+		public int CenterCompletedCount { get; set; }
+
+		/// <summary>
+		/// 超期已办办结
+		/// </summary>
+		public int ExpiredTimeCompletedCount { get; set; }
+
+		/// <summary>
+		/// 总体按时办结率
+		/// </summary>
+		public double AllCompletedRate => GetAllCompletedRate();
+
+		public double GetAllCompletedRate()
+		{
+			if (CompletedCount > 0)
+				return Math.Round(((double)(CompletedCount - ExpiredTimeCompletedCount) / CompletedCount) * 100, 2);
+			return 0;
+		}
+
+		/// <summary>
+		/// 市级超期已办办结
+		/// </summary>
+		public int CityExpiredTimeCompletedCount { get; set; }
+
+		/// <summary>
+		/// 市级办结率
+		/// </summary>
+		public double CityCompletedRate => GetCityCompletedRate();
+
+		public double GetCityCompletedRate()
+		{
+			if (CityCompletedCount > 0)
+				return Math.Round(((double)(CityCompletedCount - CityExpiredTimeCompletedCount) / CityCompletedCount) * 100, 2);
+			return 0;
+		}
+
+		/// <summary>
+		/// 区县超期已办办结
+		/// </summary>
+		public int CountyExpiredTimeCompletedCount { get; set; }
+
+		/// <summary>
+		/// 区县办结率
+		/// </summary>
+		public double CountyCompletedRate => GetCountyCompletedRate();
+
+		public double GetCountyCompletedRate()
+		{
+			if (CountyCompletedCount > 0)
+				return Math.Round(((double)(CountyCompletedCount - CountyExpiredTimeCompletedCount) / CountyCompletedCount) * 100, 2);
+			return 0;
+		}
+
+		/// <summary>
+		/// 中心超期已办办结
+		/// </summary>
+		public int CenterExpiredTimeCompletedCount { get; set; }
+
+		/// <summary>
+		/// 中心办结率
+		/// </summary>
+		public double CenterCompletedRate => GetCenterCompletedRate();
+
+		public double GetCenterCompletedRate()
+		{
+			if (CenterCompletedCount > 0)
+				return Math.Round(((double)(CenterCompletedCount - CenterExpiredTimeCompletedCount) / CenterCompletedCount) * 100, 2);
+			return 0;
+		}
+	}
 
     /// <summary>
-    /// 信件来源
+    /// 办理时效情况
     /// </summary>
-    public class CenterReportOrderSourceChannelDto
+    public class OrderAgingDto {
+    
+        /// <summary>
+        /// 来件总计
+        /// </summary>
+        public int OrderCount {  get; set; }
+
+        /// <summary>
+        /// 办理总时长
+        /// </summary>
+        public double? CompletedAging {  get; set; }
+
+        /// <summary>
+        /// 办理总时长平均
+        /// </summary>
+        public double CompletedAgingMean => GetCompletedAgingMean();
+
+        public double GetCompletedAgingMean() {
+            if (OrderCount > 0 && CompletedAging > 0)
+				return Math.Round(((CompletedAging.Value / OrderCount) / 3600), 2);
+			return 0;
+		}
+
+		/// <summary>
+		/// 市级来件总计
+		/// </summary>
+		public int CityOrderCount { get; set; }
+
+		/// <summary>
+		/// 市级办理总时长
+		/// </summary>
+		public double? CityCompletedAging { get; set; }
+
+		/// <summary>
+		/// 市级办理总时长平均
+		/// </summary>
+		public double CityCompletedAgingMean => GetCityCompletedAgingMean();
+
+		public double GetCityCompletedAgingMean()
+		{
+			if (CityOrderCount > 0 && CityCompletedAging > 0)
+				return Math.Round(((CityCompletedAging.Value / CityOrderCount) / 3600), 2);
+			return 0;
+		}
+
+		/// <summary>
+		/// 区县来件总计
+		/// </summary>
+		public int CountyOrderCount { get; set; }
+
+		/// <summary>
+		/// 区县办理总时长
+		/// </summary>
+		public double? CountyCompletedAging { get; set; }
+
+		/// <summary>
+		/// 区县办理总时长平均
+		/// </summary>
+		public double CountyCompletedAgingMean => GetCountyCompletedAgingMean();
+
+		public double GetCountyCompletedAgingMean()
+		{
+			if (CountyOrderCount > 0 && CountyCompletedAging > 0)
+				return Math.Round(((CountyCompletedAging.Value / CountyOrderCount) / 3600), 2);
+			return 0;
+		}
+
+		/// <summary>
+		/// 中心来件总计
+		/// </summary>
+		public int CenterOrderCount { get; set; }
+
+		/// <summary>
+		/// 中心办理总时长
+		/// </summary>
+		public double? CenterCompletedAging { get; set; }
+
+		/// <summary>
+		/// 中心办理总时长平均
+		/// </summary>
+		public double CenterCompletedAgingMean => GetCenterCompletedAgingMean();
+
+		public double GetCenterCompletedAgingMean()
+		{
+			if (CenterOrderCount > 0 && CenterCompletedAging > 0)
+				return Math.Round(((CenterCompletedAging.Value / CenterOrderCount) / 3600), 2);
+			return 0;
+		}
+	}
+
+
+    public class EnterpriseOrderDto : OrderAgingDto
+	{
+
+		/// <summary>
+		/// 在办
+		/// </summary>
+		public int InProgressCount { get; set; }
+
+		/// <summary>
+		/// 已办结
+		/// </summary>
+		public int CompletedCount { get; set; }
+
+		/// <summary>
+		/// 中心件
+		/// </summary>
+		public int CenterCount { get; set; }
+
+		/// <summary>
+		/// 市级件
+		/// </summary>
+		public int CityCount { get; set; }
+
+		/// <summary>
+		/// 区县件
+		/// </summary>
+		public int CountyCount { get; set; }
+
+		/// <summary>
+		/// 已回访
+		/// </summary>
+		public int VisitdCount { get; set; }
+
+		/// <summary>
+		/// 不满意
+		/// </summary>
+		public int Dissatisfied { get; set; }
+
+		/// <summary>
+		/// 市级部门不满意
+		/// </summary>
+		public int CityDissatisfied { get; set; }
+
+		/// <summary>
+		/// 县(区)不满意
+		/// </summary>
+		public int CountyDissatisfied { get; set; }
+
+		/// <summary>
+		/// 满意
+		/// </summary>
+		public int Satisfied { get; set; }
+
+		/// <summary>
+		/// 市级部门满意
+		/// </summary>
+		public int CitySatisfied { get; set; }
+
+		/// <summary>
+		/// 县(区)满意
+		/// </summary>
+		public int CountySatisfied { get; set; }
+
+		/// <summary>
+		/// 总满意率
+		/// </summary>
+		public double SatisfiedRate => GetSatisfiedRate();
+
+		
+		public double GetSatisfiedRate()
+		{
+			if (Satisfied > 0 )
+				return Math.Round(((double)Satisfied / (double)(Satisfied + Dissatisfied)) * 100, 2);
+			return 0;
+		}
+
+		/// <summary>
+		/// 市级满意率
+		/// </summary>
+		/// <returns></returns>
+		public double CitySatisfiedRate => GetCitySatisfiedRate();
+
+		public double GetCitySatisfiedRate()
+		{
+			if (CitySatisfied > 0)
+				return Math.Round(((double)CitySatisfied / (double)(CitySatisfied + CityDissatisfied)) * 100, 2);
+			return 0;
+		}
+
+		/// <summary>
+		/// 区县满意率
+		/// </summary>
+		/// <returns></returns>
+		public double CountySatisfiedRate => GetCountySatisfiedRate();
+
+		public double GetCountySatisfiedRate()
+		{
+			if (CountySatisfied > 0)
+				return Math.Round(((double)CountySatisfied / (double)(CountySatisfied + CountyDissatisfied)) * 100, 2);
+			return 0;
+		}
+	}
+
+	/// <summary>
+	/// 信件来源
+	/// </summary>
+	public class CenterReportOrderSourceChannelDto
     {
         /// <summary>
         /// 名称
@@ -245,10 +725,28 @@ namespace Hotline.Share.Dtos.CallCenter
         /// </summary>
         public string Remark { get; set; }
 
-        /// <summary>
-        /// 占比
-        /// </summary>
-        public double ProportionRate => CalcProportionRate();
+
+		/// <summary>
+		/// 办理总时长
+		/// </summary>
+		public double? CompletedAging { get; set; }
+
+		/// <summary>
+		/// 办理总时长平均
+		/// </summary>
+		public double CompletedAgingMean => GetCompletedAgingMean();
+
+		public double GetCompletedAgingMean()
+		{
+			if (CountNum > 0 && CompletedAging > 0)
+				return Math.Round(((CompletedAging.Value / CountNum) / 3600), 2);
+			return 0;
+		}
+
+		/// <summary>
+		/// 占比
+		/// </summary>
+		public double ProportionRate => CalcProportionRate();
 
         public double CalcProportionRate()
         {
@@ -299,7 +797,43 @@ namespace Hotline.Share.Dtos.CallCenter
         /// 部门满意度
         /// </summary>
         public double OrgRate { get; set; }
-    }
+
+        /// <summary>
+        /// 总体满意度
+        /// </summary>
+        public double AllRate { get; set; }
+
+		/// <summary>
+		/// 市级部门满意率
+		/// </summary>
+		public double CityRate { get; set; }
+
+		/// <summary>
+		/// 县(区)满意率
+		/// </summary>
+		public double CountyRate { get; set; }
+
+		/// <summary>
+		/// 12345中心满意率
+		/// </summary>
+		public double CenterRate { get; set; }
+
+		/// <summary>
+		/// 不满意
+		/// </summary>
+		public int Dissatisfied { get; set; }
+
+		/// <summary>
+		/// 市级部门不满意
+		/// </summary>
+		public int CityDissatisfied { get; set; }
+
+		/// <summary>
+		/// 县(区)不满意
+		/// </summary>
+		public int CountyDissatisfied { get; set; }
+
+	}
 
     public class Satisfaction
     {

+ 1 - 0
src/Hotline.Share/Requests/PagedKeywordRequest.cs

@@ -340,6 +340,7 @@ public record QueryOrderDelayDataListRequest : ReportPagedRequest
     public string? OrgName { get; set; }
 }
 
+
 public record QueryOrderDelayDataDetailRequest : ReportRequiredPagedRequest
 {
     public string? OrgCode { get; set; }

+ 1 - 0
src/Hotline/FlowEngine/Workflows/WorkflowDomainService.cs

@@ -2119,6 +2119,7 @@ namespace Hotline.FlowEngine.Workflows
                 pubTrace.AcceptorName = acceptor.UserName;
                 pubTrace.AcceptorOrgId = acceptor.OrgId;
                 pubTrace.AcceptorOrgName = acceptor.OrgName;
+                pubTrace.AcceptTime = handleTime;
                 pubTrace.HandlerId = handler.UserId;
                 pubTrace.HandlerName = handler.UserName;
                 pubTrace.HandlerOrgId = handler.OrgId;

+ 3 - 3
src/Hotline/Orders/OrderDomainService.cs

@@ -222,7 +222,7 @@ public class OrderDomainService : IOrderDomainService, IScopeDependency
             orderVisit.EmployeeId = string.Empty;
         }
 
-        if (order is { ProcessType: EProcessType.Zhiban, CounterSignType: null } && !order.IsProvince)
+        if (order is { FileOrgIsCenter:true, CounterSignType: null } && !order.IsProvince)
         {
             orderVisit.VisitState = EVisitState.Visited;
             orderVisit.VisitTime = DateTime.Now;
@@ -256,7 +256,7 @@ public class OrderDomainService : IOrderDomainService, IScopeDependency
         orgDetail.VisitOrgCode = order.ActualHandleOrgCode;
         orgDetail.VisitOrgName = order.ActualHandleOrgName;
         orgDetail.VisitTarget = EVisitTarget.Org;
-        if (order is { ProcessType: EProcessType.Zhiban, CounterSignType: null, IsProvince: false })
+        if (order is { FileOrgIsCenter:true , CounterSignType: null, IsProvince: false })
         {
             var satisfy = new Kv() { Key = "4", Value = "满意" };
             orgDetail.OrgProcessingResults = satisfy;
@@ -265,7 +265,7 @@ public class OrderDomainService : IOrderDomainService, IScopeDependency
 
         visitedDetail.Add(orgDetail);
 
-        if (order is { ProcessType: EProcessType.Zhiban, CounterSignType: null })
+        if (order is { FileOrgIsCenter:true, CounterSignType: null })
         {
             seatDetail.VoiceEvaluate = EVoiceEvaluate.Satisfied;
             seatDetail.SeatEvaluate = ESeatEvaluate.Satisfied;

+ 0 - 1
src/Hotline/Orders/OrderVisitDetail.cs

@@ -105,7 +105,6 @@ namespace Hotline.Orders
         public void ReplyBackfill(Kv visitSatisfactionKv)
         {
             this.OrgProcessingResults = visitSatisfactionKv;
-            this.OrgHandledAttitude = visitSatisfactionKv;
             this.VisitContent = visitSatisfactionKv.Value;
         }
 

+ 7 - 1
src/Hotline/Orders/OrderVisitDomainService.cs

@@ -12,6 +12,8 @@ using XF.Domain.Exceptions;
 using XF.Domain.Repository;
 using Hotline.EventBus;
 using Hotline.Orders.Notifications;
+using Hotline.Configurations;
+using Microsoft.Extensions.Options;
 
 namespace Hotline.Orders;
 public class OrderVisitDomainService : IOrderVisitDomainService, IScopeDependency
@@ -23,8 +25,9 @@ public class OrderVisitDomainService : IOrderVisitDomainService, IScopeDependenc
     private readonly IOrderVisitRepository _orderVisitRepository;
     private readonly ICapPublisher _capPublisher;
     private readonly Publisher _publisher;
+    private readonly IOptionsSnapshot<AppConfiguration> _appOptions;
 
-    public OrderVisitDomainService(IRepository<OrderVisitDetail> orderVisitDetailRepository, ILogger<OrderVisitDomainService> logger, IRepository<Order> orderRepository, ISystemDicDataCacheManager systemDicDataCacheManager, IOrderVisitRepository orderVisitRepository, ICapPublisher capPublisher, Publisher publisher)
+    public OrderVisitDomainService(IRepository<OrderVisitDetail> orderVisitDetailRepository, ILogger<OrderVisitDomainService> logger, IRepository<Order> orderRepository, ISystemDicDataCacheManager systemDicDataCacheManager, IOrderVisitRepository orderVisitRepository, ICapPublisher capPublisher, Publisher publisher, IOptionsSnapshot<AppConfiguration> appOptions)
     {
         _orderVisitDetailRepository = orderVisitDetailRepository;
         _logger = logger;
@@ -33,6 +36,7 @@ public class OrderVisitDomainService : IOrderVisitDomainService, IScopeDependenc
         _orderVisitRepository = orderVisitRepository;
         _capPublisher = capPublisher;
         _publisher = publisher;
+        _appOptions = appOptions;
     }
 
     /// <summary>
@@ -164,6 +168,8 @@ public class OrderVisitDomainService : IOrderVisitDomainService, IScopeDependenc
         foreach (var item in detailOrg)
         {
             item.ReplyBackfill(visitSatisfactionKv);
+            if (_appOptions.Value.IsZiGong)
+                item.OrgHandledAttitude = visitSatisfactionKv;
         }
         await _orderVisitDetailRepository.UpdateRangeAsync(detailOrg);
 

+ 3 - 3
src/Hotline/Statistics/StatisticsDepart.cs

@@ -221,21 +221,21 @@ namespace Hotline.Statistics
 		/// </summary>
 		/// </summary>
 		[SugarColumn(ColumnDescription = "满意")]
-		public int SatisfactionCount { get; set; }
+		public int? SatisfactionCount { get; set; }
 
 		/// <summary>
 		/// 不满意
 		/// </summary>
 		/// </summary>
 		[SugarColumn(ColumnDescription = "不满意")]
-		public int NotSatisfactionCount { get; set; }
+		public int? NotSatisfactionCount { get; set; }
 
 		/// <summary>
 		/// 按时办结
 		/// </summary>
 		/// </summary>
 		[SugarColumn(ColumnDescription = "按时办结")]
-		public int CompleteOnTime { get; set; }
+		public int? CompleteOnTime { get; set; }
 
 	}
 }