DeliveryExceptionService.cs 3.5 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485
  1. namespace Admin.NET.Plugin.AiDOP.Supply;
  2. /// <summary>
  3. /// 交货单异常记录服务
  4. ///
  5. /// 【租户安全边界】租户一律经 <see cref="AidopTenantScope.ResolveOrThrow"/> 从认证后 JWT 解析,
  6. /// 无有效租户即拒绝,不读前端 tenantId、无默认回退(原实现:类级 <c>[AllowAnonymous]</c> +
  7. /// <c>_userManager.TenantId &gt; 0</c> 跳过分支,匿名时 TenantId=0 使租户过滤整体失效)。
  8. /// </summary>
  9. [ApiDescriptionSettings(Order = 307, Description = "交货单异常记录")]
  10. [Route("api/Supply")]
  11. [NonUnify]
  12. public class DeliveryExceptionService : IDynamicApiController, ITransient
  13. {
  14. private const string C = "utf8mb4_general_ci";
  15. private readonly ISqlSugarClient _db;
  16. private readonly UserManager _userManager;
  17. public DeliveryExceptionService(ISqlSugarClient db, UserManager userManager)
  18. {
  19. _db = db;
  20. _userManager = userManager;
  21. }
  22. /// <summary>交货单异常记录分页列表</summary>
  23. [DisplayName("交货单异常记录列表")]
  24. [HttpGet("delivery-exception/list")]
  25. public async Task<object> GetList([FromQuery] DeliveryExceptionListInput input)
  26. {
  27. var page = input.Page <= 0 ? 1 : input.Page;
  28. var pageSize = input.PageSize <= 0 ? 20 : input.PageSize;
  29. var offset = (page - 1) * pageSize;
  30. var tenantId = AidopTenantScope.ResolveOrThrow(_userManager);
  31. var pars = new List<SugarParameter> { new("@TenantId", tenantId) };
  32. var where = new List<string> { "1=1", "dm.tenant_id = @TenantId" };
  33. if (!string.IsNullOrWhiteSpace(input.OptTime))
  34. {
  35. where.Add($"(CAST(dm.OptTime AS CHAR(50)) COLLATE {C}) LIKE @OptTimeLike");
  36. pars.Add(new SugarParameter("@OptTimeLike", $"%{input.OptTime.Trim()}%"));
  37. }
  38. if (!string.IsNullOrWhiteSpace(input.ItemNum))
  39. {
  40. where.Add($"(dm.ItemNum COLLATE {C}) = @ItemNum");
  41. pars.Add(new SugarParameter("@ItemNum", input.ItemNum.Trim()));
  42. }
  43. var baseSql = BuildListBaseSql(string.Join(" AND ", where));
  44. var total = await _db.Ado.GetIntAsync($"SELECT COUNT(*) FROM ({baseSql}) AS t", pars);
  45. var list = await _db.Ado.SqlQueryAsync<DeliveryExceptionListRow>(
  46. $"SELECT * FROM ({baseSql}) AS t ORDER BY t.Id DESC LIMIT {pageSize} OFFSET {offset}", pars);
  47. return new { total, page, pageSize, list };
  48. }
  49. private static string BuildListBaseSql(string innerWhere) => $"""
  50. SELECT
  51. dm.RecID AS Id,
  52. dm.Domain AS Domain,
  53. dm.Icdsid AS IcdsId,
  54. dm.OptTime AS OptTime,
  55. dm.ItemNum AS ItemNum,
  56. im.Descr AS Descr,
  57. dm.Remark AS Remark,
  58. IFNULL(dm.NeedQty, 0) AS NeedQty
  59. FROM DeliveryExceptionMaster dm
  60. LEFT JOIN ItemMaster im
  61. ON (dm.Domain COLLATE {C}) = (im.Domain COLLATE {C})
  62. AND (dm.ItemNum COLLATE {C}) = (im.ItemNum COLLATE {C})
  63. AND im.tenant_id = @TenantId
  64. WHERE {innerWhere}
  65. """;
  66. private sealed class DeliveryExceptionListRow
  67. {
  68. public long Id { get; set; }
  69. public string? Domain { get; set; }
  70. public long? IcdsId { get; set; }
  71. public DateTime? OptTime { get; set; }
  72. public string? ItemNum { get; set; }
  73. public string? Descr { get; set; }
  74. public decimal? NeedQty { get; set; }
  75. public string? Remark { get; set; }
  76. }
  77. }