AdoS8RuleDetectionState.cs 4.1 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283
  1. namespace Admin.NET.Plugin.AiDOP.Entity.S8;
  2. /// <summary>
  3. /// S8 规则检测抗抖累计状态(建单前阶段)。
  4. /// 用途:在"持续 N 次命中才建单 / 持续 N 次未命中才标 recovered"路径上,
  5. /// 承载每条 (rule_code, dedup_key) 在还未建单时的累计计数。
  6. /// 本表无软删字段;唯一记录由 (tenant_id, rule_code, dedup_key) 决定。
  7. /// S8-TENANT-ONLY-BATCH5:factory_id 已退出唯一键。它此前把同一 (tenant, rule, dedup)
  8. /// 按工厂切成多行,抗抖计数因此可能分裂在两行上、trigger/recover 阈值静默失效。
  9. /// 已建单后的抗抖累计落在 ado_s8_exception.consecutive_hit_count / consecutive_miss_count。
  10. /// </summary>
  11. [SugarTable("ado_s8_rule_detection_state", "S8 规则检测抗抖状态")]
  12. [SugarIndex("uk_s8_rule_detection_state_dedup",
  13. nameof(TenantId), OrderByType.Asc,
  14. nameof(RuleCode), OrderByType.Asc,
  15. nameof(DedupKey), OrderByType.Asc,
  16. IsUnique = true)]
  17. [SugarIndex("idx_s8_rule_detection_state_rule",
  18. nameof(TenantId), OrderByType.Asc,
  19. nameof(RuleCode), OrderByType.Asc)]
  20. [SugarIndex("idx_s8_rule_detection_state_active_exception",
  21. nameof(ActiveExceptionId), OrderByType.Asc)]
  22. public class AdoS8RuleDetectionState
  23. {
  24. [SugarColumn(ColumnName = "id", IsPrimaryKey = true, IsIdentity = true, ColumnDataType = "bigint")]
  25. public long Id { get; set; }
  26. [SugarColumn(ColumnName = "tenant_id", ColumnDataType = "bigint")]
  27. public long TenantId { get; set; }
  28. /// <summary>
  29. /// 历史兼容列。S8-TENANT-ONLY-BATCH5 起**不再参与唯一键与任何查询谓词**,
  30. /// 仅作元数据保留(写入时取规则行的 factory_id)。列不删除,等后续 schema 清理。
  31. /// </summary>
  32. [SugarColumn(ColumnName = "factory_id", ColumnDataType = "bigint")]
  33. public long FactoryId { get; set; }
  34. /// <summary>规则人读编码(关联 ado_s8_watch_rule.rule_code)。</summary>
  35. [SugarColumn(ColumnName = "rule_code", Length = 64)]
  36. public string RuleCode { get; set; } = string.Empty;
  37. /// <summary>命中去重键,与 ado_s8_exception.dedup_key 同模型。</summary>
  38. [SugarColumn(ColumnName = "dedup_key", Length = 128)]
  39. public string DedupKey { get; set; } = string.Empty;
  40. /// <summary>源对象类型(DEVICE / ORDER / MATERIAL / QUALITY_CHECK 等)。</summary>
  41. [SugarColumn(ColumnName = "source_object_type", Length = 64, IsNullable = true)]
  42. public string? SourceObjectType { get; set; }
  43. /// <summary>源对象主键或业务 ID(字符串以适配跨表/跨域)。</summary>
  44. [SugarColumn(ColumnName = "source_object_id", Length = 64, IsNullable = true)]
  45. public string? SourceObjectId { get; set; }
  46. /// <summary>建单前的连续命中次数;累计到 trigger_count_required 才建单。</summary>
  47. [SugarColumn(ColumnName = "consecutive_hit_count")]
  48. public int ConsecutiveHitCount { get; set; } = 0;
  49. /// <summary>建单前的连续未命中次数;用于尚未建单但抖动归零的场景。</summary>
  50. [SugarColumn(ColumnName = "consecutive_miss_count")]
  51. public int ConsecutiveMissCount { get; set; } = 0;
  52. /// <summary>当前活跃的异常 Id(建单后写入;建单前为 NULL)。</summary>
  53. [SugarColumn(ColumnName = "active_exception_id", ColumnDataType = "bigint", IsNullable = true)]
  54. public long? ActiveExceptionId { get; set; }
  55. /// <summary>最近一次评估时间(命中或未命中均刷新)。</summary>
  56. [SugarColumn(ColumnName = "last_seen_at", IsNullable = true)]
  57. public DateTime? LastSeenAt { get; set; }
  58. /// <summary>最近一次命中时间。</summary>
  59. [SugarColumn(ColumnName = "last_hit_at", IsNullable = true)]
  60. public DateTime? LastHitAt { get; set; }
  61. /// <summary>最近一次未命中时间。</summary>
  62. [SugarColumn(ColumnName = "last_miss_at", IsNullable = true)]
  63. public DateTime? LastMissAt { get; set; }
  64. [SugarColumn(ColumnName = "created_at")]
  65. public DateTime CreatedAt { get; set; } = DateTime.Now;
  66. [SugarColumn(ColumnName = "updated_at", IsNullable = true)]
  67. public DateTime? UpdatedAt { get; set; }
  68. }