Commit 66be4819fbc7723ba6e265754c0c52efea8a700b

Authored by 李宇
2 parents 4f068096 e63e9808

Merge branch 'master' of http://39.98.150.180/antissoft/lvqianmeiye_ERP

netcore/src/Modularity/Extend/NCC.Extend.Entitys/Dto/LqStatisticsPersonalPerformance/LqStatisticsPersonalPerformanceListOutput.cs 0 → 100644
  1 +using System;
  2 +
  3 +namespace NCC.Extend.Entitys.Dto.LqStatisticsPersonalPerformance
  4 +{
  5 + /// <summary>
  6 + /// 个人开单业绩统计列表输出
  7 + /// </summary>
  8 + public class LqStatisticsPersonalPerformanceListOutput
  9 + {
  10 + /// <summary>
  11 + /// 主键ID
  12 + /// </summary>
  13 + public string Id { get; set; }
  14 +
  15 + /// <summary>
  16 + /// 统计月份(YYYYMM)
  17 + /// </summary>
  18 + public string StatisticsMonth { get; set; }
  19 +
  20 + /// <summary>
  21 + /// 门店ID
  22 + /// </summary>
  23 + public string StoreId { get; set; }
  24 +
  25 + /// <summary>
  26 + /// 门店名称
  27 + /// </summary>
  28 + public string StoreName { get; set; }
  29 +
  30 + /// <summary>
  31 + /// 金三角ID
  32 + /// </summary>
  33 + public string GoldTriangleId { get; set; }
  34 +
  35 + /// <summary>
  36 + /// 金三角名称
  37 + /// </summary>
  38 + public string GoldTriangleName { get; set; }
  39 +
  40 + /// <summary>
  41 + /// 岗位
  42 + /// </summary>
  43 + public string Position { get; set; }
  44 +
  45 + /// <summary>
  46 + /// 员工ID
  47 + /// </summary>
  48 + public string EmployeeId { get; set; }
  49 +
  50 + /// <summary>
  51 + /// 员工姓名
  52 + /// </summary>
  53 + public string EmployeeName { get; set; }
  54 +
  55 + /// <summary>
  56 + /// 总业绩
  57 + /// </summary>
  58 + public decimal TotalPerformance { get; set; }
  59 +
  60 + /// <summary>
  61 + /// 基础业绩
  62 + /// </summary>
  63 + public decimal BasePerformance { get; set; }
  64 +
  65 + /// <summary>
  66 + /// 合作业绩
  67 + /// </summary>
  68 + public decimal CooperationPerformance { get; set; }
  69 +
  70 + /// <summary>
  71 + /// 订单数量
  72 + /// </summary>
  73 + public int OrderCount { get; set; }
  74 +
  75 + /// <summary>
  76 + /// 最后订单日期
  77 + /// </summary>
  78 + public DateTime? LastOrderDate { get; set; }
  79 +
  80 + /// <summary>
  81 + /// 首次订单日期
  82 + /// </summary>
  83 + public DateTime? FirstOrderDate { get; set; }
  84 +
  85 + /// <summary>
  86 + /// 创建时间
  87 + /// </summary>
  88 + public DateTime CreateTime { get; set; }
  89 + }
  90 +}
... ...
netcore/src/Modularity/Extend/NCC.Extend.Entitys/Dto/LqStatisticsPersonalPerformance/LqStatisticsPersonalPerformanceListQueryInput.cs 0 → 100644
  1 +using System;
  2 +using NCC.Common.Filter;
  3 +
  4 +namespace NCC.Extend.Entitys.Dto.LqStatisticsPersonalPerformance
  5 +{
  6 + /// <summary>
  7 + /// 个人开单业绩统计列表查询输入
  8 + /// </summary>
  9 + public class LqStatisticsPersonalPerformanceListQueryInput : PageInputBase
  10 + {
  11 + /// <summary>
  12 + /// 统计月份(YYYYMM)
  13 + /// </summary>
  14 + public string StatisticsMonth { get; set; }
  15 +
  16 + /// <summary>
  17 + /// 门店ID
  18 + /// </summary>
  19 + public string StoreId { get; set; }
  20 +
  21 + /// <summary>
  22 + /// 员工ID
  23 + /// </summary>
  24 + public string EmployeeId { get; set; }
  25 +
  26 + /// <summary>
  27 + /// 员工姓名
  28 + /// </summary>
  29 + public string EmployeeName { get; set; }
  30 +
  31 + /// <summary>
  32 + /// 金三角ID
  33 + /// </summary>
  34 + public string GoldTriangleId { get; set; }
  35 +
  36 + /// <summary>
  37 + /// 岗位
  38 + /// </summary>
  39 + public string Position { get; set; }
  40 + }
  41 +}
... ...
netcore/src/Modularity/Extend/NCC.Extend.Entitys/Entity/lq_statistics_personal_performance/LqStatisticsPersonalPerformanceEntity.cs 0 → 100644
  1 +using NCC.Common.Const;
  2 +using SqlSugar;
  3 +using System;
  4 +
  5 +namespace NCC.Extend.Entitys.lq_statistics_personal_performance
  6 +{
  7 + /// <summary>
  8 + /// 个人开单业绩统计表
  9 + /// </summary>
  10 + [SugarTable("lq_statistics_personal_performance")]
  11 + [Tenant(ClaimConst.TENANT_ID)]
  12 + public class LqStatisticsPersonalPerformanceEntity
  13 + {
  14 + /// <summary>
  15 + /// 主键ID
  16 + /// </summary>
  17 + [SugarColumn(ColumnName = "F_Id", IsPrimaryKey = true)]
  18 + public string Id { get; set; }
  19 +
  20 + /// <summary>
  21 + /// 统计月份(YYYYMM)
  22 + /// </summary>
  23 + [SugarColumn(ColumnName = "F_StatisticsMonth")]
  24 + public string StatisticsMonth { get; set; }
  25 +
  26 + /// <summary>
  27 + /// 门店ID
  28 + /// </summary>
  29 + [SugarColumn(ColumnName = "F_StoreId")]
  30 + public string StoreId { get; set; }
  31 +
  32 + /// <summary>
  33 + /// 门店名称
  34 + /// </summary>
  35 + [SugarColumn(ColumnName = "F_StoreName")]
  36 + public string StoreName { get; set; }
  37 +
  38 + /// <summary>
  39 + /// 金三角ID
  40 + /// </summary>
  41 + [SugarColumn(ColumnName = "F_GoldTriangleId")]
  42 + public string GoldTriangleId { get; set; }
  43 +
  44 + /// <summary>
  45 + /// 金三角名称
  46 + /// </summary>
  47 + [SugarColumn(ColumnName = "F_GoldTriangleName")]
  48 + public string GoldTriangleName { get; set; }
  49 +
  50 + /// <summary>
  51 + /// 岗位
  52 + /// </summary>
  53 + [SugarColumn(ColumnName = "F_Position")]
  54 + public string Position { get; set; }
  55 +
  56 + /// <summary>
  57 + /// 员工ID
  58 + /// </summary>
  59 + [SugarColumn(ColumnName = "F_EmployeeId")]
  60 + public string EmployeeId { get; set; }
  61 +
  62 + /// <summary>
  63 + /// 员工姓名
  64 + /// </summary>
  65 + [SugarColumn(ColumnName = "F_EmployeeName")]
  66 + public string EmployeeName { get; set; }
  67 +
  68 + /// <summary>
  69 + /// 总业绩
  70 + /// </summary>
  71 + [SugarColumn(ColumnName = "F_TotalPerformance")]
  72 + public decimal TotalPerformance { get; set; }
  73 +
  74 + /// <summary>
  75 + /// 基础业绩
  76 + /// </summary>
  77 + [SugarColumn(ColumnName = "F_BasePerformance")]
  78 + public decimal BasePerformance { get; set; }
  79 +
  80 + /// <summary>
  81 + /// 合作业绩
  82 + /// </summary>
  83 + [SugarColumn(ColumnName = "F_CooperationPerformance")]
  84 + public decimal CooperationPerformance { get; set; }
  85 +
  86 + /// <summary>
  87 + /// 订单数量
  88 + /// </summary>
  89 + [SugarColumn(ColumnName = "F_OrderCount")]
  90 + public int OrderCount { get; set; }
  91 +
  92 + /// <summary>
  93 + /// 最后订单日期
  94 + /// </summary>
  95 + [SugarColumn(ColumnName = "F_LastOrderDate")]
  96 + public DateTime? LastOrderDate { get; set; }
  97 +
  98 + /// <summary>
  99 + /// 首次订单日期
  100 + /// </summary>
  101 + [SugarColumn(ColumnName = "F_FirstOrderDate")]
  102 + public DateTime? FirstOrderDate { get; set; }
  103 +
  104 + /// <summary>
  105 + /// 创建时间
  106 + /// </summary>
  107 + [SugarColumn(ColumnName = "F_CreateTime")]
  108 + public DateTime CreateTime { get; set; }
  109 + }
  110 +}
... ...
netcore/src/Modularity/Extend/NCC.Extend/LqGzService.cs
... ... @@ -26,7 +26,6 @@ using NCC.Extend.Entitys.lq_kd_pxmx;
26 26 using NCC.Extend.Entitys.lq_mdxx;
27 27 using NCC.Extend.Entitys.lq_xmzl;
28 28 using NCC.Extend.Entitys.lq_ycsd_jsj;
29   -using NCC.Extend.Entitys.lq_statistics_gold_triangle;
30 29 using NCC.Extend.Interfaces.LqGz;
31 30 using NCC.FriendlyException;
32 31 using NCC.JsonSerialization;
... ... @@ -915,233 +914,6 @@ namespace NCC.Extend.LqGz
915 914  
916 915 #endregion
917 916  
918   - #region 金三角统计数据保存
919   -
920   - /// <summary>
921   - /// 保存金三角开卡业绩统计数据
922   - /// </summary>
923   - /// <remarks>
924   - /// 根据金三角设定和开单记录统计金三角的业绩数据
925   - /// 使用直接SQL查询提高效率,完全按照原始SQL逻辑实现
926   - ///
927   - /// 示例请求:
928   - /// ```json
929   - /// POST /api/Extend/LqGz/save-gold-triangle-statistics
930   - /// {
931   - /// "statisticsMonth": "202401"
932   - /// }
933   - /// ```
934   - /// </remarks>
935   - /// <param name="statisticsMonth">统计月份(YYYYMM格式)</param>
936   - /// <returns>保存结果</returns>
937   - /// <response code="200">成功保存统计数据</response>
938   - /// <response code="400">参数错误</response>
939   - /// <response code="500">服务器内部错误</response>
940   - [HttpPost("save-gold-triangle-statistics")]
941   - public async Task<dynamic> SaveGoldTriangleStatistics(string statisticsMonth)
942   - {
943   - if (string.IsNullOrEmpty(statisticsMonth) || statisticsMonth.Length != 6)
944   - {
945   - throw NCCException.Oh("统计月份格式错误,请使用YYYYMM格式");
946   - }
947   -
948   - try
949   - {
950   - // 使用直接SQL查询,完全按照原始SQL逻辑
951   - var sql = @"
952   - SELECT
953   - jsj.F_Id AS JsjId,
954   - jsj.jsj AS JsjName,
955   - jsj.yf AS Month,
956   - jsj.md AS StoreId,
957   - md.dm AS StoreName,
958   - COUNT(DISTINCT jksyj.glkdbh) AS OrderCount,
959   - SUM(CAST(jksyj.jksyj AS DECIMAL(18,2))) AS TotalPerformance,
960   - MAX(jksyj.yjsj) AS LastOrderDate,
961   - MIN(jksyj.yjsj) AS FirstOrderDate
962   - FROM lq_ycsd_jsj jsj
963   - LEFT JOIN lq_kd_jksyj jksyj ON (
964   - jsj.F_Id = jksyj.jsj_id
965   - AND YEAR(jksyj.yjsj) = SUBSTRING(jsj.yf, 1, 4)
966   - AND MONTH(jksyj.yjsj) = SUBSTRING(jsj.yf, 5, 2)
967   - )
968   - LEFT JOIN lq_mdxx md ON jsj.md = md.F_Id
969   - WHERE jsj.yf = @statisticsMonth
970   - AND jksyj.yjsj IS NOT NULL
971   - AND jksyj.jksyj IS NOT NULL
972   - AND jksyj.jksyj <> ''
973   - AND jksyj.jksyj <> '0'
974   - GROUP BY jsj.F_Id, jsj.jsj, jsj.yf, jsj.md, md.dm
975   - ORDER BY jsj.yf DESC, TotalPerformance DESC";
976   -
977   - var statisticsData = await _db.Ado.SqlQueryAsync<dynamic>(sql, new { statisticsMonth });
978   -
979   - if (!statisticsData.Any())
980   - {
981   - return new
982   - {
983   - Success = true,
984   - Message = $"未找到 {statisticsMonth} 月份的金三角统计数据",
985   - SavedCount = 0
986   - };
987   - }
988   -
989   - // 转换为实体对象并保存
990   - var entities = statisticsData.Select(data => new LqStatisticsGoldTriangleEntity
991   - {
992   - Id = YitIdHelper.NextId().ToString(),
993   - GoldTriangleId = data.JsjId?.ToString(),
994   - GoldTriangleName = data.JsjName?.ToString(),
995   - StatisticsMonth = data.Month?.ToString(),
996   - StoreId = data.StoreId?.ToString(),
997   - StoreName = data.StoreName?.ToString(),
998   - OrderCount = Convert.ToInt32(data.OrderCount),
999   - TotalPerformance = Convert.ToDecimal(data.TotalPerformance),
1000   - LastOrderDate = data.LastOrderDate as DateTime?,
1001   - FirstOrderDate = data.FirstOrderDate as DateTime?,
1002   - CreateTime = DateTime.Now
1003   - }).ToList();
1004   -
1005   - // 先删除该月份的历史数据
1006   - await _db.Deleteable<LqStatisticsGoldTriangleEntity>()
1007   - .Where(x => x.StatisticsMonth == statisticsMonth)
1008   - .ExecuteCommandAsync();
1009   -
1010   - // 批量插入新数据
1011   - var savedCount = await _db.Insertable(entities).ExecuteCommandAsync();
1012   -
1013   - _logger.LogInformation($"成功保存金三角统计数据 - 月份: {statisticsMonth}, 记录数: {savedCount}");
1014   -
1015   - return new
1016   - {
1017   - Success = true,
1018   - Message = $"成功保存 {savedCount} 条金三角统计数据",
1019   - SavedCount = savedCount,
1020   - StatisticsMonth = statisticsMonth
1021   - };
1022   - }
1023   - catch (Exception ex)
1024   - {
1025   - _logger.LogError(ex, $"保存金三角统计数据失败 - 月份: {statisticsMonth}");
1026   - throw NCCException.Oh($"保存金三角统计数据失败: {ex.Message}");
1027   - }
1028   - }
1029   -
1030   - /// <summary>
1031   - /// 测试金三角统计SQL查询
1032   - /// </summary>
1033   - /// <remarks>
1034   - /// 直接执行SQL查询,验证统计逻辑是否正确
1035   - ///
1036   - /// 示例请求:
1037   - /// ```json
1038   - /// GET /api/Extend/LqGz/test-gold-triangle-sql?statisticsMonth=202401
1039   - /// ```
1040   - /// </remarks>
1041   - /// <param name="statisticsMonth">统计月份(YYYYMM格式)</param>
1042   - /// <returns>原始SQL查询结果</returns>
1043   - /// <response code="200">成功返回查询结果</response>
1044   - /// <response code="400">参数错误</response>
1045   - [HttpGet("test-gold-triangle-sql")]
1046   - public async Task<dynamic> TestGoldTriangleSql(string statisticsMonth)
1047   - {
1048   - if (string.IsNullOrEmpty(statisticsMonth) || statisticsMonth.Length != 6)
1049   - {
1050   - throw NCCException.Oh("统计月份格式错误,请使用YYYYMM格式");
1051   - }
1052   -
1053   - try
1054   - {
1055   - var sql = @"
1056   - SELECT
1057   - jsj.F_Id AS JsjId,
1058   - jsj.jsj AS JsjName,
1059   - jsj.yf AS Month,
1060   - jsj.md AS StoreId,
1061   - md.dm AS StoreName,
1062   - COUNT(DISTINCT jksyj.glkdbh) AS OrderCount,
1063   - SUM(CAST(jksyj.jksyj AS DECIMAL(18,2))) AS TotalPerformance,
1064   - MAX(jksyj.yjsj) AS LastOrderDate,
1065   - MIN(jksyj.yjsj) AS FirstOrderDate
1066   - FROM lq_ycsd_jsj jsj
1067   - LEFT JOIN lq_kd_jksyj jksyj ON (
1068   - jsj.F_Id = jksyj.jsj_id
1069   - AND YEAR(jksyj.yjsj) = SUBSTRING(jsj.yf, 1, 4)
1070   - AND MONTH(jksyj.yjsj) = SUBSTRING(jsj.yf, 5, 2)
1071   - )
1072   - LEFT JOIN lq_mdxx md ON jsj.md = md.F_Id
1073   - WHERE jsj.yf = @statisticsMonth
1074   - AND jksyj.yjsj IS NOT NULL
1075   - AND jksyj.jksyj IS NOT NULL
1076   - AND jksyj.jksyj <> ''
1077   - AND jksyj.jksyj <> '0'
1078   - GROUP BY jsj.F_Id, jsj.jsj, jsj.yf, jsj.md, md.dm
1079   - ORDER BY jsj.yf DESC, TotalPerformance DESC";
1080   -
1081   - var result = await _db.Ado.SqlQueryAsync<dynamic>(sql, new { statisticsMonth });
1082   -
1083   - return new
1084   - {
1085   - Success = true,
1086   - Data = result,
1087   - Count = result.Count,
1088   - StatisticsMonth = statisticsMonth,
1089   - Sql = sql
1090   - };
1091   - }
1092   - catch (Exception ex)
1093   - {
1094   - _logger.LogError(ex, $"测试金三角统计SQL失败 - 月份: {statisticsMonth}");
1095   - throw NCCException.Oh($"测试金三角统计SQL失败: {ex.Message}");
1096   - }
1097   - }
1098   -
1099   - /// <summary>
1100   - /// 获取金三角统计数据
1101   - /// </summary>
1102   - /// <remarks>
1103   - /// 查询指定月份的金三角统计数据
1104   - ///
1105   - /// 示例请求:
1106   - /// ```json
1107   - /// GET /api/Extend/LqGz/get-gold-triangle-statistics?statisticsMonth=202401
1108   - /// ```
1109   - /// </remarks>
1110   - /// <param name="statisticsMonth">统计月份(YYYYMM格式)</param>
1111   - /// <returns>统计数据列表</returns>
1112   - /// <response code="200">成功返回统计数据</response>
1113   - /// <response code="400">参数错误</response>
1114   - [HttpGet("get-gold-triangle-statistics")]
1115   - public async Task<dynamic> GetGoldTriangleStatistics(string statisticsMonth)
1116   - {
1117   - if (string.IsNullOrEmpty(statisticsMonth))
1118   - {
1119   - throw NCCException.Oh("统计月份不能为空");
1120   - }
1121   -
1122   - try
1123   - {
1124   - var statistics = await _db.Queryable<LqStatisticsGoldTriangleEntity>()
1125   - .Where(x => x.StatisticsMonth == statisticsMonth)
1126   - .OrderBy(x => x.TotalPerformance, OrderByType.Desc)
1127   - .ToListAsync();
1128   -
1129   - return new
1130   - {
1131   - Success = true,
1132   - Data = statistics,
1133   - Count = statistics.Count,
1134   - StatisticsMonth = statisticsMonth
1135   - };
1136   - }
1137   - catch (Exception ex)
1138   - {
1139   - _logger.LogError(ex, $"查询金三角统计数据失败 - 月份: {statisticsMonth}");
1140   - throw NCCException.Oh($"查询金三角统计数据失败: {ex.Message}");
1141   - }
1142   - }
1143   -
1144   - #endregion
1145 917  
1146 918  
1147 919  
... ...
netcore/src/Modularity/Extend/NCC.Extend/LqStatisticsService.cs
... ... @@ -23,12 +23,18 @@ using NCC.Extend.Entitys.lq_mdxx;
23 23 using NCC.Extend.Entitys.lq_xh_kjbsyj;
24 24 using NCC.Extend.Entitys.lq_ycsd_jsj;
25 25 using NCC.Extend.Entitys.lq_yjmxb;
  26 +using NCC.Extend.Entitys.lq_statistics_gold_triangle;
  27 +using NCC.Extend.Entitys.lq_statistics_personal_performance;
  28 +using NCC.Extend.Entitys.lq_xmzl;
  29 +using NCC.Extend.Entitys.Dto.LqStatisticsPersonalPerformance;
26 30 using NCC.Extend.Entitys.v_tech_teacher_flow;
27 31 using NCC.Extend.Interfaces.LqStatistics;
28 32 using NCC.Extend.Utils;
29 33 using NCC.FriendlyException;
30 34 using NCC.System.Entitys.Permission;
31 35 using SqlSugar;
  36 +using Yitter.IdGenerator;
  37 +using NCC.Extend.Entitys.lq_kd_pxmx;
32 38  
33 39 namespace NCC.Extend.LqStatistics
34 40 {
... ... @@ -1178,27 +1184,475 @@ namespace NCC.Extend.LqStatistics
1178 1184 throw NCCException.Oh(ErrorCode.COM1001, "查询金三角业绩统计失败");
1179 1185 }
1180 1186 }
  1187 +
1181 1188 #endregion
1182   - }
1183 1189  
1184   - /// <summary>
1185   - /// 部门信息
1186   - /// </summary>
1187   - public class DepartmentInfo
1188   - {
  1190 + #region 金三角统计数据保存
  1191 +
  1192 + /// <summary>
  1193 + /// 1、保存金三角开卡业绩统计数据
  1194 + /// </summary>
  1195 + /// <remarks>
  1196 + /// 根据金三角设定和开单记录统计金三角的业绩数据
  1197 + /// 使用SqlSugar框架实现,优化查询性能
  1198 + ///
  1199 + /// 示例请求:
  1200 + /// ```json
  1201 + /// POST /api/Extend/LqStatistics/save-gold-triangle-statistics
  1202 + /// {
  1203 + /// "statisticsMonth": "202401"
  1204 + /// }
  1205 + /// ```
  1206 + /// </remarks>
  1207 + /// <param name="statisticsMonth">统计月份(YYYYMM格式)</param>
  1208 + /// <returns>保存结果</returns>
  1209 + /// <response code="200">成功保存统计数据</response>
  1210 + /// <response code="400">参数错误</response>
  1211 + /// <response code="500">服务器内部错误</response>
  1212 + [HttpPost("save-gold-triangle-statistics")]
  1213 + public async Task<dynamic> SaveGoldTriangleStatistics(string statisticsMonth)
  1214 + {
  1215 + if (string.IsNullOrEmpty(statisticsMonth) || statisticsMonth.Length != 6)
  1216 + {
  1217 + throw NCCException.Oh("统计月份格式错误,请使用YYYYMM格式");
  1218 + }
  1219 +
  1220 + try
  1221 + {
  1222 + // 使用数据库聚合方式,直接在数据库中完成所有统计计算
  1223 + var sql = @"
  1224 + SELECT
  1225 + jsj.F_Id AS GoldTriangleId,
  1226 + jsj.jsj AS GoldTriangleName,
  1227 + jsj.yf AS StatisticsMonth,
  1228 + jsj.md AS StoreId,
  1229 + COALESCE(md.dm, '') AS StoreName,
  1230 + COUNT(DISTINCT jksyj.glkdbh) AS OrderCount,
  1231 + SUM(CAST(jksyj.jksyj AS DECIMAL(18,2))) AS TotalPerformance,
  1232 + MAX(jksyj.yjsj) AS LastOrderDate,
  1233 + MIN(jksyj.yjsj) AS FirstOrderDate
  1234 + FROM lq_ycsd_jsj jsj
  1235 + LEFT JOIN lq_kd_jksyj jksyj ON (
  1236 + jsj.F_Id = jksyj.jsj_id
  1237 + AND YEAR(jksyj.yjsj) = SUBSTRING(jsj.yf, 1, 4)
  1238 + AND MONTH(jksyj.yjsj) = SUBSTRING(jsj.yf, 5, 2)
  1239 + )
  1240 + LEFT JOIN lq_mdxx md ON jsj.md = md.F_Id
  1241 + WHERE jsj.yf = @statisticsMonth
  1242 + AND (jksyj.yjsj IS NULL OR (
  1243 + jksyj.yjsj IS NOT NULL
  1244 + AND jksyj.jksyj IS NOT NULL
  1245 + AND jksyj.jksyj != ''
  1246 + AND jksyj.jksyj != '0'
  1247 + ))
  1248 + GROUP BY
  1249 + jsj.F_Id,
  1250 + jsj.jsj,
  1251 + jsj.yf,
  1252 + jsj.md,
  1253 + md.dm
  1254 + ORDER BY TotalPerformance DESC";
  1255 +
  1256 + // 解析统计月份
  1257 + var year = int.Parse(statisticsMonth.Substring(0, 4));
  1258 + var month = int.Parse(statisticsMonth.Substring(4, 2));
  1259 +
  1260 + // 执行SQL查询
  1261 + var statisticsData = await _db.Ado.SqlQueryAsync<dynamic>(sql, new { statisticsMonth });
  1262 +
  1263 + if (!statisticsData.Any())
  1264 + {
  1265 + return new
  1266 + {
  1267 + Success = true,
  1268 + Message = $"未找到 {statisticsMonth} 月份的金三角统计数据",
  1269 + SavedCount = 0
  1270 + };
  1271 + }
  1272 +
  1273 + // 转换为实体对象
  1274 + var entities = statisticsData.Select(data => new LqStatisticsGoldTriangleEntity
  1275 + {
  1276 + Id = YitIdHelper.NextId().ToString(),
  1277 + GoldTriangleId = data.GoldTriangleId?.ToString() ?? "",
  1278 + GoldTriangleName = data.GoldTriangleName?.ToString() ?? "",
  1279 + StatisticsMonth = data.StatisticsMonth?.ToString() ?? statisticsMonth,
  1280 + StoreId = data.StoreId?.ToString() ?? "",
  1281 + StoreName = data.StoreName?.ToString() ?? "",
  1282 + OrderCount = Convert.ToInt32(data.OrderCount ?? 0),
  1283 + TotalPerformance = Convert.ToDecimal(data.TotalPerformance ?? 0),
  1284 + LastOrderDate = data.LastOrderDate as DateTime?,
  1285 + FirstOrderDate = data.FirstOrderDate as DateTime?,
  1286 + CreateTime = DateTime.Now
  1287 + }).ToList();
  1288 +
  1289 + // 使用事务确保数据一致性
  1290 + var result = await _db.Ado.UseTranAsync(async () =>
  1291 + {
  1292 + // 先删除该月份的历史数据
  1293 + await _db.Deleteable<LqStatisticsGoldTriangleEntity>()
  1294 + .Where(x => x.StatisticsMonth == statisticsMonth)
  1295 + .ExecuteCommandAsync();
  1296 +
  1297 + // 批量插入新数据
  1298 + return await _db.Insertable(entities).ExecuteCommandAsync();
  1299 + });
  1300 +
  1301 + var savedCount = result.IsSuccess ? result.Data : 0;
  1302 + _logger.LogInformation($"成功保存金三角统计数据 - 月份: {statisticsMonth}, 记录数: {savedCount}");
  1303 +
  1304 + return new
  1305 + {
  1306 + Success = true,
  1307 + Message = $"成功保存 {savedCount} 条金三角统计数据",
  1308 + SavedCount = savedCount,
  1309 + StatisticsMonth = statisticsMonth
  1310 + };
  1311 + }
  1312 + catch (Exception ex)
  1313 + {
  1314 + _logger.LogError(ex, $"保存金三角统计数据失败 - 月份: {statisticsMonth}");
  1315 + throw NCCException.Oh($"保存金三角统计数据失败: {ex.Message}");
  1316 + }
  1317 + }
  1318 +
  1319 + /// <summary>
  1320 + /// 获取金三角统计数据
  1321 + /// </summary>
  1322 + /// <remarks>
  1323 + /// 查询指定月份的金三角统计数据
  1324 + ///
  1325 + /// 示例请求:
  1326 + /// ```json
  1327 + /// GET /api/Extend/LqStatistics/get-gold-triangle-statistics?statisticsMonth=202401
  1328 + /// ```
  1329 + /// </remarks>
  1330 + /// <param name="statisticsMonth">统计月份(YYYYMM格式)</param>
  1331 + /// <returns>统计数据列表</returns>
  1332 + /// <response code="200">成功返回统计数据</response>
  1333 + /// <response code="400">参数错误</response>
  1334 + [HttpGet("get-gold-triangle-statistics")]
  1335 + public async Task<dynamic> GetGoldTriangleStatistics(string statisticsMonth)
  1336 + {
  1337 + if (string.IsNullOrEmpty(statisticsMonth))
  1338 + {
  1339 + throw NCCException.Oh("统计月份不能为空");
  1340 + }
  1341 +
  1342 + try
  1343 + {
  1344 + var statistics = await _db.Queryable<LqStatisticsGoldTriangleEntity>()
  1345 + .Where(x => x.StatisticsMonth == statisticsMonth)
  1346 + .OrderBy(x => x.TotalPerformance, OrderByType.Desc)
  1347 + .ToListAsync();
  1348 +
  1349 + return new
  1350 + {
  1351 + Success = true,
  1352 + Data = statistics,
  1353 + Count = statistics.Count,
  1354 + StatisticsMonth = statisticsMonth
  1355 + };
  1356 + }
  1357 + catch (Exception ex)
  1358 + {
  1359 + _logger.LogError(ex, $"查询金三角统计数据失败 - 月份: {statisticsMonth}");
  1360 + throw NCCException.Oh($"查询金三角统计数据失败: {ex.Message}");
  1361 + }
  1362 + }
  1363 +
  1364 + #endregion
  1365 +
  1366 + #region 个人开单业绩统计
  1367 +
  1368 + /// <summary>
  1369 + /// 保存个人开单业绩统计数据
  1370 + /// </summary>
  1371 + /// <remarks>
  1372 + /// 根据开单记录统计个人的业绩数据,包括基础业绩和合作业绩
  1373 + /// 基础业绩和合作业绩的划分根据品项ID查询lq_xmzl表的fl3字段
  1374 + /// 使用数据库聚合方式优化性能,避免大量数据加载到内存
  1375 + ///
  1376 + /// 示例请求:
  1377 + /// ```json
  1378 + /// POST /api/Extend/LqStatistics/save-personal-performance-statistics
  1379 + /// {
  1380 + /// "statisticsMonth": "202401"
  1381 + /// }
  1382 + /// ```
  1383 + /// </remarks>
  1384 + /// <param name="statisticsMonth">统计月份(YYYYMM格式)</param>
  1385 + /// <returns>保存结果</returns>
  1386 + /// <response code="200">成功保存统计数据</response>
  1387 + /// <response code="400">参数错误</response>
  1388 + /// <response code="500">服务器内部错误</response>
  1389 + [HttpPost("save-personal-performance-statistics")]
  1390 + public async Task<dynamic> SavePersonalPerformanceStatistics(string statisticsMonth)
  1391 + {
  1392 + if (string.IsNullOrEmpty(statisticsMonth) || statisticsMonth.Length != 6)
  1393 + {
  1394 + throw NCCException.Oh("统计月份格式错误,请使用YYYYMM格式");
  1395 + }
  1396 +
  1397 + try
  1398 + {
  1399 + // 使用数据库聚合方式,直接在数据库中完成所有统计计算
  1400 + // 按照开单记录统计,避免重复计算
  1401 + var sql = @"
  1402 + SELECT
  1403 + jksyj.jkszh AS EmployeeId,
  1404 + u.F_REALNAME AS EmployeeName,
  1405 + u.F_MDID AS StoreId,
  1406 + COALESCE(md.dm, '') AS StoreName,
  1407 + COALESCE(jsj.F_Id, '') AS GoldTriangleId,
  1408 + COALESCE(jsj.jsj, '') AS GoldTriangleName,
  1409 + CASE
  1410 + WHEN jsjUser.is_leader = 1 THEN '顾问'
  1411 + ELSE COALESCE(u.F_GW, '')
  1412 + END AS Position,
  1413 + COUNT(DISTINCT jksyj.glkdbh) AS OrderCount,
  1414 + MAX(jksyj.yjsj) AS LastOrderDate,
  1415 + MIN(jksyj.yjsj) AS FirstOrderDate,
  1416 + SUM(
  1417 + CASE
  1418 + WHEN xmzl.fl3 = '合作业绩' THEN CAST(jksyj.jksyj AS DECIMAL(18,2))
  1419 + ELSE 0
  1420 + END
  1421 + ) AS CooperationPerformance,
  1422 + SUM(
  1423 + CASE
  1424 + WHEN xmzl.fl3 IS NULL OR xmzl.fl3 != '合作业绩' THEN CAST(jksyj.jksyj AS DECIMAL(18,2))
  1425 + ELSE 0
  1426 + END
  1427 + ) AS BasePerformance,
  1428 + SUM(CAST(jksyj.jksyj AS DECIMAL(18,2))) AS TotalPerformance
  1429 + FROM lq_kd_jksyj jksyj
  1430 + INNER JOIN lq_kd_pxmx pxmx ON jksyj.F_kdpxid = pxmx.F_Id
  1431 + INNER JOIN lq_xmzl xmzl ON pxmx.px = xmzl.F_Id
  1432 + INNER JOIN BASE_USER u ON jksyj.jkszh = u.F_Id
  1433 + LEFT JOIN lq_mdxx md ON u.F_MDID = md.F_Id
  1434 + LEFT JOIN lq_ycsd_jsj jsj ON jksyj.jsj_id = jsj.F_Id AND jsj.yf = @statisticsMonth
  1435 + LEFT JOIN (
  1436 + SELECT DISTINCT user_id, F_Month, MAX(is_leader) as is_leader
  1437 + FROM lq_jinsanjiao_user
  1438 + WHERE F_Month = @statisticsMonth
  1439 + GROUP BY user_id, F_Month
  1440 + ) jsjUser ON jksyj.jkszh = jsjUser.user_id
  1441 + WHERE jksyj.yjsj IS NOT NULL
  1442 + AND jksyj.jksyj IS NOT NULL
  1443 + AND jksyj.jksyj != ''
  1444 + AND jksyj.jksyj != '0'
  1445 + AND jksyj.F_kdpxid IS NOT NULL
  1446 + AND jksyj.F_kdpxid != ''
  1447 + AND YEAR(jksyj.yjsj) = @year
  1448 + AND MONTH(jksyj.yjsj) = @month
  1449 + GROUP BY
  1450 + jksyj.jkszh,
  1451 + u.F_REALNAME,
  1452 + u.F_MDID,
  1453 + md.dm,
  1454 + jsj.F_Id,
  1455 + jsj.jsj,
  1456 + jsjUser.is_leader,
  1457 + u.F_GW
  1458 + ORDER BY TotalPerformance DESC";
  1459 +
  1460 + // 解析统计月份
  1461 + var year = int.Parse(statisticsMonth.Substring(0, 4));
  1462 + var month = int.Parse(statisticsMonth.Substring(4, 2));
  1463 +
  1464 + var parameters = new Dictionary<string, object>
  1465 + {
  1466 + { "@statisticsMonth", statisticsMonth },
  1467 + { "@year", year },
  1468 + { "@month", month }
  1469 + };
  1470 +
  1471 + _logger.LogInformation($"执行个人业绩统计SQL - 月份: {statisticsMonth}");
  1472 +
  1473 + var statisticsData = await _db.Ado.SqlQueryAsync<dynamic>(sql, parameters);
  1474 +
  1475 + if (!statisticsData.Any())
  1476 + {
  1477 + return new
  1478 + {
  1479 + Success = true,
  1480 + Message = $"未找到 {statisticsMonth} 月份的开单记录数据",
  1481 + SavedCount = 0
  1482 + };
  1483 + }
  1484 +
  1485 + _logger.LogInformation($"查询到个人业绩统计数据: {statisticsData.Count} 条");
  1486 +
  1487 + // 创建实体列表
  1488 + var entities = statisticsData.Select(stats => new LqStatisticsPersonalPerformanceEntity
  1489 + {
  1490 + Id = YitIdHelper.NextId().ToString(),
  1491 + StatisticsMonth = statisticsMonth,
  1492 + StoreId = stats.StoreId?.ToString() ?? "",
  1493 + StoreName = stats.StoreName?.ToString() ?? "",
  1494 + GoldTriangleId = stats.GoldTriangleId?.ToString() ?? "",
  1495 + GoldTriangleName = stats.GoldTriangleName?.ToString() ?? "",
  1496 + Position = stats.Position?.ToString() ?? "",
  1497 + EmployeeId = stats.EmployeeId?.ToString() ?? "",
  1498 + EmployeeName = stats.EmployeeName?.ToString() ?? "",
  1499 + TotalPerformance = Convert.ToDecimal(stats.TotalPerformance ?? 0),
  1500 + BasePerformance = Convert.ToDecimal(stats.BasePerformance ?? 0),
  1501 + CooperationPerformance = Convert.ToDecimal(stats.CooperationPerformance ?? 0),
  1502 + OrderCount = Convert.ToInt32(stats.OrderCount ?? 0),
  1503 + LastOrderDate = stats.LastOrderDate as DateTime?,
  1504 + FirstOrderDate = stats.FirstOrderDate as DateTime?,
  1505 + CreateTime = DateTime.Now
  1506 + }).ToList();
  1507 +
  1508 + // 使用事务确保数据一致性
  1509 + var result = await _db.Ado.UseTranAsync(async () =>
  1510 + {
  1511 + // 先删除该月份的历史数据
  1512 + await _db.Deleteable<LqStatisticsPersonalPerformanceEntity>()
  1513 + .Where(x => x.StatisticsMonth == statisticsMonth)
  1514 + .ExecuteCommandAsync();
  1515 +
  1516 + // 批量插入新数据
  1517 + return await _db.Insertable(entities).ExecuteCommandAsync();
  1518 + });
  1519 +
  1520 + var savedCount = result.IsSuccess ? result.Data : 0;
  1521 + _logger.LogInformation($"成功保存个人业绩统计数据 - 月份: {statisticsMonth}, 记录数: {savedCount}");
  1522 +
  1523 + return new
  1524 + {
  1525 + Success = true,
  1526 + Message = $"成功保存 {savedCount} 条个人业绩统计数据",
  1527 + SavedCount = savedCount,
  1528 + StatisticsMonth = statisticsMonth
  1529 + };
  1530 + }
  1531 + catch (Exception ex)
  1532 + {
  1533 + _logger.LogError(ex, $"保存个人业绩统计数据失败 - 月份: {statisticsMonth}");
  1534 + throw NCCException.Oh($"保存个人业绩统计数据失败: {ex.Message}");
  1535 + }
  1536 + }
  1537 +
1189 1538 /// <summary>
1190   - /// 部门ID
  1539 + /// 获取个人开单业绩统计数据
1191 1540 /// </summary>
1192   - public string DepartmentId { get; set; }
  1541 + /// <remarks>
  1542 + /// 查询指定月份的个人业绩统计数据
  1543 + ///
  1544 + /// 示例请求:
  1545 + /// ```json
  1546 + /// GET /api/Extend/LqStatistics/get-personal-performance-statistics?statisticsMonth=202401
  1547 + /// ```
  1548 + /// </remarks>
  1549 + /// <param name="statisticsMonth">统计月份(YYYYMM格式)</param>
  1550 + /// <returns>统计数据列表</returns>
  1551 + /// <response code="200">成功返回统计数据</response>
  1552 + /// <response code="400">参数错误</response>
  1553 + [HttpGet("get-personal-performance-statistics")]
  1554 + public async Task<dynamic> GetPersonalPerformanceStatistics(string statisticsMonth)
  1555 + {
  1556 + if (string.IsNullOrEmpty(statisticsMonth))
  1557 + {
  1558 + throw NCCException.Oh("统计月份不能为空");
  1559 + }
  1560 +
  1561 + try
  1562 + {
  1563 + var statistics = await _db.Queryable<LqStatisticsPersonalPerformanceEntity>()
  1564 + .Where(x => x.StatisticsMonth == statisticsMonth)
  1565 + .OrderBy(x => x.TotalPerformance, OrderByType.Desc)
  1566 + .ToListAsync();
  1567 +
  1568 + return statistics;
  1569 + }
  1570 + catch (Exception ex)
  1571 + {
  1572 + _logger.LogError(ex, $"查询个人业绩统计数据失败 - 月份: {statisticsMonth}");
  1573 + throw NCCException.Oh($"查询个人业绩统计数据失败: {ex.Message}");
  1574 + }
  1575 + }
1193 1576  
1194 1577 /// <summary>
1195   - /// 部门名称
  1578 + /// 分页查询个人开单业绩统计数据
1196 1579 /// </summary>
1197   - public string DepartmentName { get; set; }
  1580 + /// <remarks>
  1581 + /// 分页查询个人业绩统计数据,支持多条件筛选
  1582 + ///
  1583 + /// 示例请求:
  1584 + /// ```json
  1585 + /// POST /api/Extend/LqStatistics/get-personal-performance-statistics-list
  1586 + /// {
  1587 + /// "statisticsMonth": "202401",
  1588 + /// "storeId": "store123",
  1589 + /// "employeeName": "张三",
  1590 + /// "pageIndex": 1,
  1591 + /// "pageSize": 20
  1592 + /// }
  1593 + /// ```
  1594 + /// </remarks>
  1595 + /// <param name="input">查询条件</param>
  1596 + /// <returns>分页统计数据</returns>
  1597 + /// <response code="200">成功返回分页数据</response>
  1598 + /// <response code="400">参数错误</response>
  1599 + [HttpPost("get-personal-performance-statistics-list")]
  1600 + public async Task<dynamic> GetPersonalPerformanceStatisticsList(LqStatisticsPersonalPerformanceListQueryInput input)
  1601 + {
  1602 + try
  1603 + {
  1604 + var query = _db.Queryable<LqStatisticsPersonalPerformanceEntity>();
  1605 +
  1606 + // 添加查询条件
  1607 + query = query.WhereIF(!string.IsNullOrEmpty(input.StatisticsMonth), x => x.StatisticsMonth == input.StatisticsMonth);
  1608 + query = query.WhereIF(!string.IsNullOrEmpty(input.StoreId), x => x.StoreId == input.StoreId);
  1609 + query = query.WhereIF(!string.IsNullOrEmpty(input.EmployeeId), x => x.EmployeeId == input.EmployeeId);
  1610 + query = query.WhereIF(!string.IsNullOrEmpty(input.EmployeeName), x => x.EmployeeName.Contains(input.EmployeeName));
  1611 + query = query.WhereIF(!string.IsNullOrEmpty(input.GoldTriangleId), x => x.GoldTriangleId == input.GoldTriangleId);
  1612 + query = query.WhereIF(!string.IsNullOrEmpty(input.Position), x => x.Position == input.Position);
  1613 +
  1614 + // 按总业绩降序排序
  1615 + query = query.OrderBy(x => x.TotalPerformance, OrderByType.Desc);
  1616 +
  1617 + // 分页查询
  1618 + var result = await query.ToPagedListAsync(input.currentPage, input.pageSize);
  1619 +
  1620 + return new
  1621 + {
  1622 + Records = result.list,
  1623 + Total = result.pagination.Total,
  1624 + PageIndex = input.currentPage,
  1625 + PageSize = input.pageSize
  1626 + };
  1627 + }
  1628 + catch (Exception ex)
  1629 + {
  1630 + _logger.LogError(ex, "查询个人业绩统计数据列表失败");
  1631 + throw NCCException.Oh($"查询个人业绩统计数据列表失败: {ex.Message}");
  1632 + }
  1633 + }
  1634 +
  1635 + #endregion
1198 1636  
1199 1637 /// <summary>
1200   - /// 父部门ID
  1638 + /// 部门信息
1201 1639 /// </summary>
1202   - public string ParentId { get; set; }
  1640 + public class DepartmentInfo
  1641 + {
  1642 + /// <summary>
  1643 + /// 部门ID
  1644 + /// </summary>
  1645 + public string DepartmentId { get; set; }
  1646 +
  1647 + /// <summary>
  1648 + /// 部门名称
  1649 + /// </summary>
  1650 + public string DepartmentName { get; set; }
  1651 +
  1652 + /// <summary>
  1653 + /// 父部门ID
  1654 + /// </summary>
  1655 + public string ParentId { get; set; }
  1656 + }
1203 1657 }
1204 1658 }
... ...
netcore/src/Modularity/Extend/NCC.Extend/LqYcsdJsjService.cs
... ... @@ -327,11 +327,11 @@ namespace NCC.Extend.LqYcsdJsj
327 327 {
328 328 await CreateJsjMembers(entity.Id, input.members, userInfo.userId);
329 329 }
330   - // 3. 创建站点战队T区(如果金三角不是T区且不是单人)
331   - if (!input.jsj.EndsWith("T区") && input.members != null && input.members.Count > 1)
332   - {
333   - await CreateOrUpdateTeamTArea(input.yf, input.jsj, input.md, userInfo.userId);
334   - }
  330 + // 3. 创建站点战队T区(如果金三角不是T区且不是单人),暂时不用创建金三角的T区,等待业务部门确认逻辑后进行
  331 + // if (!input.jsj.EndsWith("T区") && input.members != null && input.members.Count > 1)
  332 + // {
  333 + // await CreateOrUpdateTeamTArea(input.yf, input.jsj, input.md, userInfo.userId);
  334 + // }
335 335 // 提交事务
336 336 _db.CommitTran();
337 337 }
... ...