Quellcode durchsuchen

penBehatvior: update

Yi vor 1 Monat
Ursprung
Commit
45d2e89b89
43 geänderte Dateien mit 4394 neuen und 3649 gelöschten Zeilen
  1. 15 2
      config/app.go
  2. 1 0
      dep/di_alert.go
  3. 6 2
      dep/di_crontab.go
  4. 2 2
      go.mod
  5. 14 0
      go.sum
  6. 25 0
      http/handler/analysis/analysis.go
  7. 1 8
      http/handler/cow/cow.go
  8. 26 0
      http/handler/test.go
  9. 86 86
      http/handler/upload/upload.go
  10. 17 14
      http/route/analysis_api.go
  11. 1 1
      http/route/files_api.go
  12. 2 0
      http/route/test_api.go
  13. 17 15
      model/cow.go
  14. 90 0
      model/cow_calving.go
  15. 0 25
      model/event_enter.go
  16. 54 22
      model/event_mating.go
  17. 45 2
      model/neck_active_habit.go
  18. 13 12
      model/neck_ring_configure.go
  19. 8 0
      model/neck_ring_health.go
  20. 4 3
      model/neck_ring_health_warning.go
  21. 1 0
      model/pen_behavior.go
  22. 1 126
      module/backend/analysis.go
  23. 255 0
      module/backend/analysis_cow.go
  24. 113 0
      module/backend/analysis_more.go
  25. 137 10
      module/backend/cow.go
  26. 7 4
      module/backend/dashboard.go
  27. 4 0
      module/backend/goods.go
  28. 4 0
      module/backend/interface.go
  29. 5 1
      module/backend/neck_ring_warning.go
  30. 12 0
      module/backend/sql.go
  31. 2996 0
      module/backend/test_service.go
  32. 200 2
      module/backend/upload_file.go
  33. 2 2
      module/crontab/cow_cron.go
  34. 133 35
      module/crontab/health_warning.go
  35. 3 0
      module/crontab/interface.go
  36. 11 10
      module/crontab/model.go
  37. 12 10
      module/crontab/neck_ring_calculate.go
  38. 0 3227
      module/crontab/neck_ring_estus_test.go
  39. 4 18
      module/crontab/neck_ring_merge.go
  40. 3 7
      module/crontab/pen_behavior.go
  41. 38 0
      module/crontab/twenty_one_pregnant_rate.go
  42. 26 0
      service/alert/alert.go
  43. 0 3
      util/util.go

+ 15 - 2
config/app.go

@@ -45,6 +45,8 @@ type AppConfig struct {
 	CronSetting     CronSetting     `json:"cron_setting" yaml:"cron"`
 	Mqtt            MqttSetting     `json:"mqtt"`
 	MilkHall        MilkHallSetting `json:"milkHall"`
+
+	EmailConfig EmailConfig `json:"emailConfig" yaml:"email_config"`
 }
 
 type CronSetting struct {
@@ -58,8 +60,8 @@ type CronSetting struct {
 	SameTimePlan            string `yaml:"same_time_plan"`             //  同期
 	UpdateSameTime          string `yaml:"update_same_time"`           //  更新同期
 	SystemBasicCrontab      string `yaml:"system_basic_crontab"`       //  系统基础定时任务
-	DeleteOldOriginal       string `yaml:"delete_old_original"`        // 删除脖环历史数据
-	UpdateDiseaseToCalendar string `yaml:"update_disease_to_calendar"` // 更新每天治疗中牛头数到日历表中
+	DeleteOldOriginal       string `yaml:"delete_old_original"`        //  删除脖环历史数据
+	UpdateDiseaseToCalendar string `yaml:"update_disease_to_calendar"` //  更新每天治疗中牛头数到日历表中
 	CowPregnant             string `yaml:"cow_pregnant"`               //  月度牛只怀孕清单
 	UpdateActiveHabit       string `yaml:"update_active_habit"`        //  脖环2小时数据重新整合
 	NeckRingEstrus          string `yaml:"neck_ring_estrus"`           //  脖环牛只发情
@@ -71,6 +73,7 @@ type CronSetting struct {
 	UpdatePenBehaviorDaily  string `yaml:"update_pen_behavior_daily"`  //  栏舍饲养监测
 	UpdateMilkOriginal      string `yaml:"update_milk_original"`       //  奶厅原始数据更新
 	InsertMilkDaily         string `yaml:"insert_milk_daily"`          //  牛只每日奶量数据
+	TwentyOnePregnantRate   string `yaml:"twenty_one_pregnant_rate"`   //  21怀孕率
 }
 
 type JwtTokenKeyConfig struct {
@@ -196,6 +199,16 @@ type MilkHallSetting struct {
 	MilkHallNumber string   `yaml:"milk_hall_number"`
 }
 
+// EmailConfig 邮件配置
+type EmailConfig struct {
+	Host     string   `yaml:"host"`     // SMTP服务器地址
+	Port     int      `json:"port"`     // SMTP服务器端口
+	Username string   `yaml:"username"` // 发件人邮箱
+	Password string   `json:"password"` // 发件人密码
+	From     string   `yaml:"from"`     // 发件人名称
+	To       []string `yaml:"to"`       // 收件人列表
+}
+
 func (a *AppConfig) Name() string {
 	return fmt.Sprintf("%s-%s", a.AppName, a.AppEnv)
 }

+ 1 - 0
dep/di_alert.go

@@ -0,0 +1 @@
+package dep

+ 6 - 2
dep/di_crontab.go

@@ -57,6 +57,10 @@ func EntryCrontab(dependency CrontabDependency) *cron.Crontab {
 		panic(err)
 	}
 
+	if err := newCrontab.Bind("TwentyOnePregnantRate", cs.TwentyOnePregnantRate, dependency.CrontabHub.TwentyOnePregnantRate); err != nil {
+		panic(err)
+	}
+
 	if err := newCrontab.Bind("SameTimePlan", cs.SameTimePlan, dependency.CrontabHub.SameTimePlan); err != nil {
 		panic(err)
 	}
@@ -98,10 +102,10 @@ func EntryCrontab(dependency CrontabDependency) *cron.Crontab {
 		panic(err)
 	}
 
-	if err := newCrontab.Bind("NeckRingHealthWarning", cs.NeckRingHealthWarning, dependency.CrontabHub.NeckRingHealthWarning); err != nil {
+	/*if err := newCrontab.Bind("NeckRingHealthWarning", cs.NeckRingHealthWarning, dependency.CrontabHub.NeckRingHealthWarning); err != nil {
 		zaplog.Error("EntryCrontab", zap.Any("NeckRingHealthWarning", err))
 		panic(err)
-	}
+	}*/
 
 	if err := newCrontab.Bind("UpdatePenBehavior", cs.UpdatePenBehavior, dependency.CrontabHub.UpdatePenBehavior); err != nil {
 		zaplog.Error("EntryCrontab", zap.Any("UpdatePenBehavior", err))

+ 2 - 2
go.mod

@@ -3,8 +3,8 @@ module kpt-pasture
 go 1.17
 
 require (
-	gitee.com/xuyiping_admin/go_proto v0.0.0-20250430023822-7c5bf763451e
-	gitee.com/xuyiping_admin/pkg v0.0.0-20241108060137-caea58c59f5b
+	gitee.com/xuyiping_admin/go_proto v0.0.0-20250514085954-501d0d6cb26c
+	gitee.com/xuyiping_admin/pkg v0.0.0-20250514071642-f92d2ac9a85d
 	github.com/dgrijalva/jwt-go v3.2.0+incompatible
 	github.com/eclipse/paho.mqtt.golang v1.4.3
 	github.com/eko/gocache v1.1.0

+ 14 - 0
go.sum

@@ -88,8 +88,22 @@ gitee.com/xuyiping_admin/go_proto v0.0.0-20250429032832-f43ab362a21b h1:9Shzi/Jp
 gitee.com/xuyiping_admin/go_proto v0.0.0-20250429032832-f43ab362a21b/go.mod h1:BKrFW6YLDectlQcQk3FYKBeXvjEiodAKJ5rq7O/QiPE=
 gitee.com/xuyiping_admin/go_proto v0.0.0-20250430023822-7c5bf763451e h1:IWZC/FOxItSt33n+qzMdJhclW9oFzOnrze0SGC3jT+c=
 gitee.com/xuyiping_admin/go_proto v0.0.0-20250430023822-7c5bf763451e/go.mod h1:BKrFW6YLDectlQcQk3FYKBeXvjEiodAKJ5rq7O/QiPE=
+gitee.com/xuyiping_admin/go_proto v0.0.0-20250513060115-1841a323de9e h1:w+6CKL+iJYBwsmaLIUby7xeqlZKHlbL+GV/BeiEZBYo=
+gitee.com/xuyiping_admin/go_proto v0.0.0-20250513060115-1841a323de9e/go.mod h1:BKrFW6YLDectlQcQk3FYKBeXvjEiodAKJ5rq7O/QiPE=
+gitee.com/xuyiping_admin/go_proto v0.0.0-20250514013843-42f268c5cc98 h1:xAEEFgktRY0mQWtHcM4czFrR0ArCTH/5g2oQw2+qe5o=
+gitee.com/xuyiping_admin/go_proto v0.0.0-20250514013843-42f268c5cc98/go.mod h1:BKrFW6YLDectlQcQk3FYKBeXvjEiodAKJ5rq7O/QiPE=
+gitee.com/xuyiping_admin/go_proto v0.0.0-20250514015819-8b4ba0765b3c h1:F1lFnBnt1AIPzERyzGOGuMjZLEUkU2XDEeBH2MKMlK4=
+gitee.com/xuyiping_admin/go_proto v0.0.0-20250514015819-8b4ba0765b3c/go.mod h1:BKrFW6YLDectlQcQk3FYKBeXvjEiodAKJ5rq7O/QiPE=
+gitee.com/xuyiping_admin/go_proto v0.0.0-20250514022148-95b29436d061 h1:hKrOp5DfZp2F+VPG44YKP7DcmgcvAYz14yx7lLrMNMQ=
+gitee.com/xuyiping_admin/go_proto v0.0.0-20250514022148-95b29436d061/go.mod h1:BKrFW6YLDectlQcQk3FYKBeXvjEiodAKJ5rq7O/QiPE=
+gitee.com/xuyiping_admin/go_proto v0.0.0-20250514080018-cb20fb9800f8 h1:FWbFRaJGr2cvOyr7hbwC3DFBKWM1Y+5+UK+xliShcpU=
+gitee.com/xuyiping_admin/go_proto v0.0.0-20250514080018-cb20fb9800f8/go.mod h1:BKrFW6YLDectlQcQk3FYKBeXvjEiodAKJ5rq7O/QiPE=
+gitee.com/xuyiping_admin/go_proto v0.0.0-20250514085954-501d0d6cb26c h1:PkMErJiu4y8ft7jgjzVkfnV3OnqT2tKer5YnjS6fMRc=
+gitee.com/xuyiping_admin/go_proto v0.0.0-20250514085954-501d0d6cb26c/go.mod h1:BKrFW6YLDectlQcQk3FYKBeXvjEiodAKJ5rq7O/QiPE=
 gitee.com/xuyiping_admin/pkg v0.0.0-20241108060137-caea58c59f5b h1:w05MxH7yqveRlaRbxHhbif5YjPrJFodRPfOjYhXn7Zk=
 gitee.com/xuyiping_admin/pkg v0.0.0-20241108060137-caea58c59f5b/go.mod h1:8tF25X6pE9WkFCczlNAC0K2mrjwKvhhp02I7o0HtDxY=
+gitee.com/xuyiping_admin/pkg v0.0.0-20250514071642-f92d2ac9a85d h1:vBXmMRggF7mZVPGRDgavZ87igJgkezwX0a3v1/XtIMQ=
+gitee.com/xuyiping_admin/pkg v0.0.0-20250514071642-f92d2ac9a85d/go.mod h1:8tF25X6pE9WkFCczlNAC0K2mrjwKvhhp02I7o0HtDxY=
 github.com/BurntSushi/toml v0.3.1/go.mod h1:xHWCNGjB5oqiDr8zfno3MHue2Ht5sIBksp03qcyfWMU=
 github.com/BurntSushi/xgb v0.0.0-20160522181843-27f122750802/go.mod h1:IVnqGOEym/WlBOVXweHU+Q+/VP0lqqI8lqeDx9IjBqo=
 github.com/Knetic/govaluate v3.0.1-0.20171022003610-9aa49832a739+incompatible/go.mod h1:r7JcOSlj0wfOMncg0iLm8Leh48TZaKVeNIfJntJ2wa0=

+ 25 - 0
http/handler/analysis/analysis.go

@@ -133,6 +133,31 @@ func TwentyOnePregnantRate(c *gin.Context) {
 	ginutil.JSONResp(c, res)
 }
 
+func TwentyOnePregnantDetail(c *gin.Context) {
+	var req pasturePb.TwentyOnePregnantDetailsRequest
+	if err := ginutil.BindProto(c, &req); err != nil {
+		apierr.AbortBadRequest(c, http.StatusBadRequest, err)
+		return
+	}
+
+	if err := valid.ValidateStruct(&req,
+		valid.Field(&req.StartDate, valid.Required),
+		valid.Field(&req.EndDate, valid.Required),
+		valid.Field(&req.CowType, valid.Required),
+		valid.Field(&req.Type, valid.Required),
+	); err != nil {
+		apierr.AbortBadRequest(c, http.StatusBadRequest, err)
+		return
+	}
+
+	res, err := middleware.Dependency(c).StoreEventHub.OpsService.TwentyOnePregnantDetail(c, &req)
+	if err != nil {
+		apierr.ClassifiedAbort(c, err)
+		return
+	}
+	ginutil.JSONResp(c, res)
+}
+
 func AbortionRate(c *gin.Context) {
 	var req pasturePb.AbortionRateRequest
 	if err := ginutil.BindProto(c, &req); err != nil {

+ 1 - 8
http/handler/cow/cow.go

@@ -19,13 +19,6 @@ func Detail(c *gin.Context) {
 		return
 	}
 
-	if err := valid.ValidateStruct(&req,
-		valid.Field(&req.EarNumber, valid.Required),
-	); err != nil {
-		apierr.AbortBadRequest(c, http.StatusBadRequest, err)
-		return
-	}
-
 	res, err := middleware.Dependency(c).StoreEventHub.OpsService.Detail(c, &req)
 	if err != nil {
 		apierr.AbortBadRequest(c, http.StatusOK, err)
@@ -121,7 +114,7 @@ func GrowthCurve(c *gin.Context) {
 
 	res, err := middleware.Dependency(c).StoreEventHub.OpsService.CowGrowthCurve(c, &req)
 	if err != nil {
-		apierr.ClassifiedAbort(c, err)
+		apierr.AbortBadRequest(c, http.StatusOK, err)
 		return
 	}
 	ginutil.JSONResp(c, res)

+ 26 - 0
http/handler/test.go

@@ -128,3 +128,29 @@ func PastureInit(c *gin.Context) {
 		Data: &operationPb.Success{Success: true},
 	})
 }
+
+func CalvingAge(c *gin.Context) {
+	if err := middleware.BackendOperation(c).OpsService.CalvingAge(c); err != nil {
+		apierr.ClassifiedAbort(c, err)
+		return
+	}
+
+	ginutil.JSONResp(c, &operationPb.CommonOK{
+		Code: http.StatusOK,
+		Msg:  "ok",
+		Data: &operationPb.Success{Success: true},
+	})
+}
+
+func AdmissionAge(c *gin.Context) {
+	if err := middleware.BackendOperation(c).OpsService.AdmissionAge(c); err != nil {
+		apierr.ClassifiedAbort(c, err)
+		return
+	}
+
+	ginutil.JSONResp(c, &operationPb.CommonOK{
+		Code: http.StatusOK,
+		Msg:  "ok",
+		Data: &operationPb.Success{Success: true},
+	})
+}

+ 86 - 86
http/handler/upload/upload.go

@@ -11,10 +11,14 @@ import (
 	"strings"
 	"time"
 
+	"github.com/xuri/excelize/v2"
+
+	operationPb "gitee.com/xuyiping_admin/go_proto/proto/go/backend/operation"
+	"gitee.com/xuyiping_admin/pkg/ginutil"
+
 	"gitee.com/xuyiping_admin/pkg/apierr"
 	"gitee.com/xuyiping_admin/pkg/xerr"
 	"github.com/gin-gonic/gin"
-	"github.com/xuri/excelize/v2"
 )
 
 func Photos(c *gin.Context) {
@@ -40,46 +44,7 @@ func Photos(c *gin.Context) {
 	c.JSON(http.StatusOK, gin.H{"code": http.StatusOK, "Msg": "ok", "data": res})
 }
 
-func Files2(c *gin.Context) {
-	// 定义配置
-	cf := ExcelImportConfig{
-		AllowedExtensions: []string{".xlsx", ".xls"},
-		RequiredHeaders: []string{"耳号", "牛舍名称", "性别", "出生日期", "胎次", "进场日期", "父号", "母号", "最近配种日期", "预产期",
-			"配后天数", "累计配次", "最近妊检日期", "最近产犊日期", "产后天数", "品种", "出生重量", "断奶日期", "是否禁配", "体重", "体高", "流产日期", "流产原因",
-		},
-		MaxFileSize: 10 << 20,
-	}
-
-	// 实现处理逻辑
-	ImportExcel(c, cf)
-}
-
-// ExcelImportConfig 导入配置
-type ExcelImportConfig struct {
-	AllowedExtensions []string
-	MaxFileSize       int64
-	RequiredHeaders   []string // 必须包含的表头
-}
-
-// DefaultExcelImportConfig 默认配置
-var DefaultExcelImportConfig = ExcelImportConfig{
-	AllowedExtensions: []string{".xlsx", ".xls"},
-	MaxFileSize:       10 << 20, // 10MB
-}
-
-// ExcelHandler Excel处理接口
-type ExcelHandler interface {
-	ProcessExcelData([][]string) error
-}
-
-// ImportExcel 导入Excel文件
-func ImportExcel(c *gin.Context, config ...ExcelImportConfig) {
-	// 获取配置
-	cfg := DefaultExcelImportConfig
-	if len(config) > 0 {
-		cfg = config[0]
-	}
-
+func Files(c *gin.Context) {
 	// 1. 获取上传的文件
 	file, err := c.FormFile("file")
 	if err != nil {
@@ -87,8 +52,9 @@ func ImportExcel(c *gin.Context, config ...ExcelImportConfig) {
 		return
 	}
 
+	cf := GetExcelImportConfig(c.GetHeader("farmid"))
 	// 2. 验证文件基本属性
-	if err = validateFile(file, cfg); err != nil {
+	if err = validateFile(file, cf); err != nil {
 		apierr.AbortBadRequest(c, http.StatusBadRequest, err)
 		return
 	}
@@ -100,32 +66,97 @@ func ImportExcel(c *gin.Context, config ...ExcelImportConfig) {
 		return
 	}
 	defer os.Remove(filePath) // 处理完成后删除临时文件
+
 	// 4. 读取并验证Excel文件
 	excelData, err := readExcelFile(filePath, filepath.Ext(file.Filename))
 	if err != nil {
-		apierr.AbortBadRequest(c, http.StatusBadRequest, err)
+		apierr.AbortBadRequest(c, http.StatusInternalServerError, err)
 		return
 	}
 	// 5. 验证表头
-	if err = validateHeaders(excelData[0], cfg.RequiredHeaders); err != nil {
-		apierr.AbortBadRequest(c, http.StatusBadRequest, err)
+	if err = validateHeaders(excelData[0], cf.RequiredHeaders); err != nil {
+		apierr.AbortBadRequest(c, http.StatusInternalServerError, err)
 		return
 	}
-
-	if err = middleware.BackendOperation(c).OpsService.ImportExcel(c, excelData); err != nil {
+	// 实现处理逻辑
+	if err = middleware.BackendOperation(c).OpsService.ImportExcel2(c, excelData, cf.RequiredHeaders); err != nil {
 		apierr.AbortBadRequest(c, http.StatusBadRequest, err)
 		return
 	}
 
-	c.JSON(http.StatusOK, gin.H{
-		"code": http.StatusOK,
-		"msg":  "导入成功",
-		"data": nil,
+	ginutil.JSONResp(c, &operationPb.CommonOK{
+		Code: http.StatusOK,
+		Msg:  "ok",
+		Data: &operationPb.Success{Success: true},
 	})
 }
 
+// ExcelImportConfig 导入配置
+type ExcelImportConfig struct {
+	AllowedExtensions []string
+	MaxFileSize       int64
+	RequiredHeaders   []string // 必须包含的表头
+	HeadOfField       []string
+}
+
+// readExcelFile 读取Excel文件
+func readExcelFile(filePath, ext string) ([][]string, error) {
+	// 尝试使用excelize读取
+	f, err := excelize.OpenFile(filePath)
+	if err != nil {
+		// 如果是xls格式且读取失败,尝试使用xls库
+		if ext == ".xls" {
+			return readXlsFile(filePath)
+		}
+		return nil, xerr.Customf("读取Excel文件失败: %s", err.Error())
+	}
+	defer f.Close()
+
+	// 获取第一个工作表
+	sheetName := f.GetSheetName(0)
+	rows, err := f.GetRows(sheetName)
+	if err != nil {
+		return nil, xerr.Customf("读取工作表失败: %s", err.Error())
+	}
+
+	if len(rows) == 0 {
+		return nil, xerr.Custom("Excel文件为空")
+	}
+
+	return rows, nil
+}
+
+// readXlsFile 使用xls库读取旧版Excel文件
+func readXlsFile(filePath string) ([][]string, error) {
+	// 这里需要实现xls文件的读取逻辑
+	// 可以使用第三方库如github.com/extrame/xls
+	return nil, xerr.Custom("暂不支持.xls格式文件")
+}
+
+func GetExcelImportConfig(farmId string) *ExcelImportConfig {
+	switch farmId {
+	case "e50cd455dec93edf3d8135abbc770680":
+		return &ExcelImportConfig{
+			AllowedExtensions: []string{".xlsx", ".xls"},
+			RequiredHeaders: []string{"", "", "耳号", "牛舍名称", "性别", "出生日期", "胎次", "进场日期", "父号", "母号", "最近配种日期", "预产期", "配后天数",
+				"累计配次", "最近妊检日期", "最近产犊日期", "产后天数", "品种", "出生重量", "断奶日期", "是否禁配", "体重", "体高", "流产日期", "流产原因"},
+			HeadOfField: []string{"", "", "earNumber", "penName", "sex", "birthAt", "lact", "admissionAt", "fatherNumber", "motherNumber",
+				"lastMatingAt", "", "matingAge", "allMatingTimes", "lastPregnantCheckAt", "lastCalvingAt", "lactationAge",
+				"cowKind", "birthWeight", "weaningAt", "isForbiddenMating", "currentWeight", "currenWtHeight", "lastAbortionAt", ""},
+			MaxFileSize: 10 << 20,
+		}
+	default:
+		return nil
+	}
+}
+
+// ExcelHandler Excel处理接口
+type ExcelHandler interface {
+	ProcessExcelData([][]string) error
+}
+
 // validateFile 验证文件基本属性
-func validateFile(file *multipart.FileHeader, cfg ExcelImportConfig) error {
+func validateFile(file *multipart.FileHeader, cfg *ExcelImportConfig) error {
 	// 检查文件扩展名
 	ext := strings.ToLower(filepath.Ext(file.Filename))
 	validExt := false
@@ -167,40 +198,6 @@ func saveUploadedFile(c *gin.Context, file *multipart.FileHeader) (string, error
 	return filePath, nil
 }
 
-// readExcelFile 读取Excel文件
-func readExcelFile(filePath, ext string) ([][]string, error) {
-	// 尝试使用excelize读取
-	f, err := excelize.OpenFile(filePath)
-	if err != nil {
-		// 如果是xls格式且读取失败,尝试使用xls库
-		if ext == ".xls" {
-			return readXlsFile(filePath)
-		}
-		return nil, xerr.Customf("读取Excel文件失败: %s", err.Error())
-	}
-	defer f.Close()
-
-	// 获取第一个工作表
-	sheetName := f.GetSheetName(0)
-	rows, err := f.GetRows(sheetName)
-	if err != nil {
-		return nil, xerr.Customf("读取工作表失败: %s", err.Error())
-	}
-
-	if len(rows) == 0 {
-		return nil, xerr.Custom("Excel文件为空")
-	}
-
-	return rows, nil
-}
-
-// readXlsFile 使用xls库读取旧版Excel文件
-func readXlsFile(filePath string) ([][]string, error) {
-	// 这里需要实现xls文件的读取逻辑
-	// 可以使用第三方库如github.com/extrame/xls
-	return nil, xerr.Custom("暂不支持.xls格式文件")
-}
-
 // validateHeaders 验证表头
 func validateHeaders(headers []string, requiredHeaders []string) error {
 	if len(requiredHeaders) == 0 {
@@ -214,6 +211,9 @@ func validateHeaders(headers []string, requiredHeaders []string) error {
 
 	var missingHeaders []string
 	for _, req := range requiredHeaders {
+		if req == "" {
+			continue
+		}
 		if !headerMap[req] {
 			missingHeaders = append(missingHeaders, req)
 		}

+ 17 - 14
http/route/analysis_api.go

@@ -13,22 +13,25 @@ func AnalysisAPI(opts ...func(engine *gin.Engine)) func(s *gin.Engine) {
 		}
 		// analysis API 组
 		analysisRoute := authRouteGroup(s, "/api/v1/analysis/")
-		analysisRoute.POST("/weight/scatter/plot", analysis.WeightScatterPlot)          // 体重散点图
-		analysisRoute.POST("/weight/range", analysis.WeightRange)                       // 体重区间图
-		analysisRoute.POST("/mating/timely", analysis.MatingTimeLy)                     // 配种及时性
-		analysisRoute.POST("/pen/weight", analysis.PenWeight)                           // 栏舍体重
-		analysisRoute.POST("/abortion/rate", analysis.AbortionRate)                     // 流产率
-		analysisRoute.POST("/twenty/one/pregnant/rate", analysis.TwentyOnePregnantRate) // 21天怀孕率
-		analysisRoute.POST("/pregnancy/report", analysis.PregnancyReport)               // 孕检报告
-		analysisRoute.POST("/calving/report", analysis.CalvingReport)                   // 产犊报告
-		analysisRoute.POST("/disease/cure/report", analysis.DiseaseCureReport)          // 疾病治疗报告
-		analysisRoute.POST("/sale/cow/report", analysis.SaleCowReport)                  // 销售牛牛报告
+		analysisRoute.POST("/weight/scatter/plot", analysis.WeightScatterPlot) // 体重散点图
+		analysisRoute.POST("/weight/range", analysis.WeightRange)              // 体重区间图
 
+		analysisRoute.POST("/mating/timely", analysis.MatingTimeLy) // 配种及时性
+		analysisRoute.POST("/pen/weight", analysis.PenWeight)       // 栏舍体重
+		analysisRoute.POST("/abortion/rate", analysis.AbortionRate) // 流产率
+
+		analysisRoute.POST("/twenty/one/pregnant/rate", analysis.TwentyOnePregnantRate)     // 21天怀孕率
+		analysisRoute.POST("/twenty/one/pregnant/detail", analysis.TwentyOnePregnantDetail) // 21天怀孕率详情
+		analysisRoute.POST("/pregnancy/report", analysis.PregnancyReport)                   // 孕检报告
+		analysisRoute.POST("/calving/report", analysis.CalvingReport)                       // 产犊报告
+
+		analysisRoute.POST("/disease/cure/report", analysis.DiseaseCureReport)                        // 疾病治疗报告
+		analysisRoute.POST("/sale/cow/report", analysis.SaleCowReport)                                // 销售牛牛报告
 		analysisRoute.POST("/single/factor/pregnant/report", analysis.SingleFactorInfantSurvivalRate) // 单因素受胎率
-		analysisRoute.POST("/multi/factor/pregnant/report", analysis.MultiFactorInfantSurvivalRate)   // 多因素受胎率
 
-		analysisRoute.POST("/pen/behavior", analysis.PenBehaviorAnalysis)                  // 栏舍行为数据
-		analysisRoute.POST("/pen/behavior/monitor", analysis.PenBehaviorDaily)             // 栏舍饲喂监测
-		analysisRoute.POST("/cow/behavior/distribution", analysis.CowBehaviorDistribution) // 牛只行为分布
+		analysisRoute.POST("/multi/factor/pregnant/report", analysis.MultiFactorInfantSurvivalRate) // 多因素受胎率
+		analysisRoute.POST("/pen/behavior", analysis.PenBehaviorAnalysis)                           // 栏舍行为数据
+		analysisRoute.POST("/pen/behavior/monitor", analysis.PenBehaviorDaily)                      // 栏舍饲喂监测
+		analysisRoute.POST("/cow/behavior/distribution", analysis.CowBehaviorDistribution)          // 牛只行为分布
 	}
 }

+ 1 - 1
http/route/files_api.go

@@ -14,7 +14,7 @@ func FilesManageAPI(opts ...func(engine *gin.Engine)) func(s *gin.Engine) {
 		// upload API 组  上传文件
 		uploadRoute := authRouteGroup(s, "/api/v1/upload/")
 		uploadRoute.POST("/photos", upload.Photos)
-		uploadRoute.POST("/files", upload.Files2)
+		uploadRoute.POST("/files", upload.Files)
 
 		// 获取文件列表
 		//ossRoute := authRouteGroup(s, "/api/v1/oss/")

+ 2 - 0
http/route/test_api.go

@@ -19,5 +19,7 @@ func TestAPI(opts ...func(engine *gin.Engine)) func(s *gin.Engine) {
 		testRoute.GET("/data/warning", handler.DataWarning)
 		testRoute.GET("/neck_ring_original/sync", handler.NeckRingOriginalAsync)
 		testRoute.GET("/pasture/init", handler.PastureInit)
+		testRoute.GET("/calving/age", handler.CalvingAge)
+		testRoute.GET("/admission/age", handler.AdmissionAge)
 	}
 }

+ 17 - 15
model/cow.go

@@ -78,18 +78,18 @@ func (c *Cow) TableName() string {
 
 // EventUpdate 牛只基本信息维护
 func (c *Cow) EventUpdate(weeklyActive int32) {
-	c.DayAge = c.GetDayAge()
-	c.CalvingAge = c.GetCalvingAge()
-	c.PregnancyAge = c.GetDaysPregnant()
-	c.AdmissionAge = c.GetAdmissionAge()
-	c.AbortionAge = c.GetAbortionAge()
+	c.DayAge = c.GetDayAge()             // 日龄
+	c.CalvingAge = c.GetCalvingAge()     // 产后天数
+	c.PregnancyAge = c.GetDaysPregnant() // 怀孕天数
+	c.AdmissionAge = c.GetAdmissionAge() // 入场天数
+	c.AbortionAge = c.GetAbortionAge()   // 流产天数
+	c.WeeklyActive = weeklyActive        // 周活动量
+	c.LactationAge = c.GetLactationAge() // 泌乳天数
+	c.DryMilkAge = c.GetDryMilkAge()     // 干奶天数
+	c.MatingAge = c.GetMatingAge()       // 配后天数
 	if c.DayAge == 60 {
 		c.CowType = pasturePb.CowType_Weaned_Calf
 	}
-	c.WeeklyActive = weeklyActive
-	c.LactationAge = c.GetLactationAge()
-	c.DryMilkAge = c.GetDryMilkAge()
-	c.MatingAge = c.GetMatingAge()
 }
 
 // EventCalvingUpdate 产犊更新
@@ -171,6 +171,9 @@ func (c *Cow) EventDeathUpdate(eventAt int64) {
 
 // EventSaleUpdate 更新牛只销售信息
 func (c *Cow) EventSaleUpdate(eventSale *EventSale) {
+	c.DepartureAt = eventSale.SaleAt
+	c.NeckRingNumber = ""
+	c.DeparturePrice = float32(eventSale.SalePrice)
 	if eventSale.SaleKind == pasturePb.SalesType_Out {
 		c.HealthStatus = pasturePb.HealthStatus_Out
 		c.AdmissionStatus = pasturePb.AdmissionStatus_Out
@@ -178,9 +181,6 @@ func (c *Cow) EventSaleUpdate(eventSale *EventSale) {
 	if eventSale.SaleKind == pasturePb.SalesType_Sales {
 		c.AdmissionStatus = pasturePb.AdmissionStatus_Sale
 	}
-	c.DepartureAt = eventSale.SaleAt
-	c.NeckRingNumber = ""
-	c.DeparturePrice = float32(eventSale.SalePrice)
 	if eventSale.SaleCowCount > 0 {
 		c.DepartureAvgWeight = eventSale.SaleAllWeight / eventSale.SaleCowCount
 	}
@@ -189,12 +189,12 @@ func (c *Cow) EventSaleUpdate(eventSale *EventSale) {
 // EventMatingUpdate 配种更新
 func (c *Cow) EventMatingUpdate(matingAt int64, bullNumber string, isReMating bool) {
 	c.LastMatingAt = matingAt
-	if c.FirstMatingAt <= 0 {
-		c.FirstMatingAt = matingAt
-	}
 	c.LastBullNumber = bullNumber
 	c.IsPregnant = pasturePb.IsShow_No
 	c.BreedStatus = pasturePb.BreedStatus_Breeding
+	if c.FirstMatingAt <= 0 {
+		c.FirstMatingAt = matingAt
+	}
 	if !isReMating {
 		c.MatingTimes += 1
 		c.AllMatingTimes += 1
@@ -822,4 +822,6 @@ type CowBehaviorCurveData struct {
 	RuminaChange     []int32                                 `json:"ruminaChange"`     // 反刍变化
 	LowActivity      int32                                   `json:"lowActivity"`      // 低活动量参数
 	MiddleActivity   int32                                   `json:"middleActivity"`   // 中活动量行数
+	IQR1             []int32                                 `json:"IQR1"`
+	IQR3             []int32                                 `json:"IQR3"`
 }

+ 90 - 0
model/cow_calving.go

@@ -0,0 +1,90 @@
+package model
+
+import pasturePb "gitee.com/xuyiping_admin/go_proto/proto/go/backend/cow"
+
+type CowCalving struct {
+	Id                int32                  `json:"id"`
+	PastureId         int64                  `json:"pastureId"`
+	DateTime          string                 `json:"dateTime"`
+	CowId             int64                  `json:"cowId"`
+	Lact              int32                  `json:"lact"`
+	EarNumber         string                 `json:"earNumber"`
+	NeckRingNumber    string                 `json:"neckRingNumber"`
+	CowType           pasturePb.CowType_Kind `json:"cowType"`
+	CowKind           pasturePb.CowKind_Kind `json:"cowKind"`
+	CalvingAge        int32                  `json:"calvingAge"`
+	MatingAge         int32                  `json:"matingAge"`
+	IsMating          pasturePb.IsShow_Kind  `json:"isMating"`
+	IsPregnantCheck   pasturePb.IsShow_Kind  `json:"isPregnantCheck"`
+	PregnantCheckDate string                 `json:"pregnantCheckDate"`
+	IsAbortion        pasturePb.IsShow_Kind  `json:"isAbortion"`
+	IsDeparture       pasturePb.IsShow_Kind  `json:"isDeparture"`
+	IsForbidden       pasturePb.IsShow_Kind  `json:"isForbidden"`
+	CreatedAt         int64                  `json:"createdAt"`
+	UpdatedAt         int64                  `json:"updatedAt"`
+}
+
+func (e *CowCalving) TableName() string {
+	return "cow_calving"
+}
+
+func NewEveryDayCalving(pastureId int64, dateTime string, cowInfo *Cow) *CowCalving {
+	isMating, isPregnantCheck, isAbortion, isDeparture, isForbidden := pasturePb.IsShow_No, pasturePb.IsShow_No, pasturePb.IsShow_No, pasturePb.IsShow_No, pasturePb.IsShow_No
+	switch cowInfo.BreedStatus {
+	case pasturePb.BreedStatus_Abort:
+		isAbortion = pasturePb.IsShow_Ok
+	case pasturePb.BreedStatus_Breeding:
+		isMating = pasturePb.IsShow_Ok
+	case pasturePb.BreedStatus_Pregnant, pasturePb.BreedStatus_Empty:
+		isPregnantCheck = pasturePb.IsShow_Ok
+	case pasturePb.BreedStatus_No_Mating:
+		isPregnantCheck = pasturePb.IsShow_Ok
+	}
+
+	if cowInfo.AdmissionStatus != pasturePb.AdmissionStatus_Admission {
+		isDeparture = pasturePb.IsShow_Ok
+	}
+
+	return &CowCalving{
+		PastureId:         pastureId,
+		DateTime:          dateTime,
+		CowId:             cowInfo.Id,
+		Lact:              cowInfo.Lact,
+		EarNumber:         cowInfo.EarNumber,
+		NeckRingNumber:    cowInfo.NeckRingNumber,
+		CowType:           cowInfo.CowType,
+		CowKind:           cowInfo.CowKind,
+		CalvingAge:        cowInfo.CalvingAge,
+		MatingAge:         cowInfo.MatingAge,
+		IsMating:          isMating,
+		IsPregnantCheck:   isPregnantCheck,
+		PregnantCheckDate: "",
+		IsAbortion:        isAbortion,
+		IsDeparture:       isDeparture,
+		IsForbidden:       isForbidden,
+	}
+}
+
+func NewEveryDayCalvingList(pastureId int64, dateTime string, cowList []*Cow) []*CowCalving {
+	res := make([]*CowCalving, 0)
+	for _, cow := range cowList {
+		res = append(res, NewEveryDayCalving(pastureId, dateTime, cow))
+	}
+	return res
+}
+
+type CowCalvingSlice []*CowCalving
+
+func (c CowCalvingSlice) ToPB() []*pasturePb.TwentyOnePregnantItems {
+	res := make([]*pasturePb.TwentyOnePregnantItems, 0)
+	for _, v := range c {
+		res = append(res, &pasturePb.TwentyOnePregnantItems{
+			CowId:     int32(v.CowId),
+			Lact:      v.Lact,
+			EarNumber: v.EarNumber,
+			//CowTypeName: v.CowType,
+		})
+	}
+
+	return res
+}

+ 0 - 25
model/event_enter.go

@@ -130,28 +130,3 @@ func (e EventEnterSlice) ToPB(
 	}
 	return res
 }
-
-var PenMap = map[string]int32{
-	"101":  15,
-	"10号":  16,
-	"1101": 17,
-	"11号":  18,
-	"12号":  19,
-	"13号":  20,
-	"14号":  21,
-	"15号舍": 22,
-	"1号":   23,
-	"2号":   24,
-	"301":  25,
-	"3号":   26,
-	"4号":   27,
-	"501":  28,
-	"5号":   29,
-	"601":  30,
-	"6号":   31,
-	"701":  32,
-	"7号":   33,
-	"801":  34,
-	"8号":   35,
-	"9号":   36,
-}

+ 54 - 22
model/event_mating.go

@@ -182,6 +182,60 @@ func (e EventMatingSlice) ToPB(exposeEstrusTypeMap map[pasturePb.ExposeEstrusTyp
 	return res
 }
 
+func (e EventMatingSlice) ToPB2() []*pasturePb.CowList {
+	res := make([]*pasturePb.CowList, len(e))
+	for i, v := range e {
+		calvingAt, matingAtFormat := "", ""
+		if v.CalvingAt > 0 {
+			calvingAt = time.Unix(v.CalvingAt, 0).Local().Format(LayoutDate2)
+		}
+		if v.RealityDay > 0 {
+			matingAtFormat = time.Unix(v.RealityDay, 0).Local().Format(LayoutDate2)
+		}
+		res[i] = &pasturePb.CowList{
+			CowId:           int32(v.CowId),
+			DayAge:          int32(v.DayAge),
+			CalvingAge:      v.CalvingAge,
+			MatingAtFormat:  matingAtFormat,
+			CalvingAtFormat: calvingAt,
+			Lact:            int32(v.Lact),
+		}
+	}
+	return res
+}
+
+func (e EventMatingSlice) ToPB3(isMating bool, cowTypeMap map[pasturePb.CowType_Kind]string) []*pasturePb.TwentyOnePregnantItems {
+	res := make([]*pasturePb.TwentyOnePregnantItems, 0)
+	for _, v := range e {
+		if !isMating {
+			continue
+		}
+		res = append(res, &pasturePb.TwentyOnePregnantItems{
+			CowId:       int32(v.CowId),
+			EarNumber:   v.EarNumber,
+			CowTypeName: cowTypeMap[v.CowType],
+			Lact:        v.Lact,
+		})
+	}
+	return res
+}
+
+func (e EventMatingSlice) ToPB4(cowTypeMap map[pasturePb.CowType_Kind]string) []*pasturePb.TwentyOnePregnantItems {
+	res := make([]*pasturePb.TwentyOnePregnantItems, 0)
+	for _, v := range e {
+		if v.MatingResult != pasturePb.MatingResult_Abort {
+			continue
+		}
+		res = append(res, &pasturePb.TwentyOnePregnantItems{
+			CowId:       int32(v.CowId),
+			EarNumber:   v.EarNumber,
+			CowTypeName: cowTypeMap[v.CowType],
+			Lact:        v.Lact,
+		})
+	}
+	return res
+}
+
 type CowMatingBody struct {
 	Id              int64                      `json:"id"`
 	CowId           int64                      `json:"cowId"`
@@ -232,28 +286,6 @@ type MatingTimelyChart struct {
 	LactGroup  string `json:"lactGroup"`
 }
 
-func (e EventMatingSlice) ToPB2() []*pasturePb.CowList {
-	res := make([]*pasturePb.CowList, len(e))
-	for i, v := range e {
-		calvingAt, matingAtFormat := "", ""
-		if v.CalvingAt > 0 {
-			calvingAt = time.Unix(v.CalvingAt, 0).Local().Format(LayoutDate2)
-		}
-		if v.RealityDay > 0 {
-			matingAtFormat = time.Unix(v.RealityDay, 0).Local().Format(LayoutDate2)
-		}
-		res[i] = &pasturePb.CowList{
-			CowId:           int32(v.CowId),
-			DayAge:          int32(v.DayAge),
-			CalvingAge:      v.CalvingAge,
-			MatingAtFormat:  matingAtFormat,
-			CalvingAtFormat: calvingAt,
-			Lact:            int32(v.Lact),
-		}
-	}
-	return res
-}
-
 type MatingTimelyResponse struct {
 	Code int32             `json:"code"`
 	Msg  string            `json:"msg"`

+ 45 - 2
model/neck_active_habit.go

@@ -74,6 +74,14 @@ type NeckActiveHabit struct {
 	UpdatedAt            int64                 `json:"updatedAt"`
 }
 
+func (n *NeckActiveHabit) UnShardTableName() string {
+	return "neck_active_habit"
+}
+
+/*func (n *NeckActiveHabit) TableName() string {
+	return fmt.Sprintf("%s_%06d", n.UnShardTableName(), n.PastureId)
+}*/
+
 func (n *NeckActiveHabit) TableName() string {
 	return "neck_active_habit"
 }
@@ -138,6 +146,8 @@ func (n NeckActiveHabitSlice) ToPB(curveName string) *CowBehaviorCurveData {
 		EventList:        make([]*pasturePb.CowEvent, 0),
 		EventMap:         make(map[pasturePb.EventType_Kind]string),
 		RuminaChange:     make([]int32, 0),
+		IQR1:             make([]int32, 0),
+		IQR3:             make([]int32, 0),
 	}
 	initFrameId := int32(0)
 	dateFrameMap := make(map[string][]int32)
@@ -220,7 +230,7 @@ func (n NeckActiveHabitSlice) ToPB(curveName string) *CowBehaviorCurveData {
 	return res
 }
 
-func (n NeckActiveHabitSlice) ToPB2(dataBetween []string) *pasturePb.CowBehaviorRateData {
+func (n NeckActiveHabitSlice) ToPB2(dataBetween []string, groupNeckActiveHabitList []*NeckActiveHabit) *pasturePb.CowBehaviorRateData {
 	data := &pasturePb.CowBehaviorRateData{
 		DateTime:     dataBetween,
 		RuminaRate:   make([]float32, 0),
@@ -231,7 +241,24 @@ func (n NeckActiveHabitSlice) ToPB2(dataBetween []string) *pasturePb.CowBehavior
 
 	neckActiveHabitMap := make(map[string]*NeckActiveHabit)
 	for _, v := range n {
-		neckActiveHabitMap[v.HeatDate] = v
+		if v.HeatDate == "" {
+			continue
+		}
+
+		if _, ok := neckActiveHabitMap[v.HeatDate]; !ok {
+			neckActiveHabitMap[v.HeatDate] = v
+		}
+	}
+
+	groupNeckActiveHabitMap := make(map[string]*NeckActiveHabit)
+	for _, v := range groupNeckActiveHabitList {
+		if v.HeatDate == "" {
+			continue
+		}
+
+		if _, ok := groupNeckActiveHabitMap[v.HeatDate]; !ok {
+			groupNeckActiveHabitMap[v.HeatDate] = v
+		}
 	}
 
 	for _, t := range dataBetween {
@@ -250,6 +277,22 @@ func (n NeckActiveHabitSlice) ToPB2(dataBetween []string) *pasturePb.CowBehavior
 		data.IntakeRate = append(data.IntakeRate, intakeRate)
 		data.InactiveRate = append(data.InactiveRate, inactiveRate)
 		data.GaspRate = append(data.GaspRate, gaspRate)
+
+		groupRuminaRate, groupIntakeRate, groupInactiveRate, groupGaspRate := float32(0), float32(0), float32(0), float32(0)
+		if v, ok := groupNeckActiveHabitMap[t]; ok {
+			groupSum := v.Rumina + v.Intake + v.Inactive + v.Gasp
+			if groupSum > 0 {
+				// 保留小数点后两位
+				groupRuminaRate = float32(math.Round(float64(v.Rumina)/float64(groupSum)*100) / 100)
+				groupIntakeRate = float32(math.Round(float64(v.Intake)/float64(groupSum)*100) / 100)
+				groupInactiveRate = float32(math.Round(float64(v.Inactive)/float64(groupSum)*100) / 100)
+				groupGaspRate = float32(math.Round(float64(v.Gasp)/float64(groupSum)*100) / 100)
+			}
+		}
+		data.GroupRuminaRate = append(data.GroupRuminaRate, groupRuminaRate)
+		data.GroupIntakeRate = append(data.GroupIntakeRate, groupIntakeRate)
+		data.GroupInactiveRate = append(data.GroupInactiveRate, groupInactiveRate)
+		data.GroupGaspRate = append(data.GroupGaspRate, groupGaspRate)
 	}
 
 	return data

+ 13 - 12
model/neck_ring_configure.go

@@ -3,18 +3,19 @@ package model
 import pasturePb "gitee.com/xuyiping_admin/go_proto/proto/go/backend/cow"
 
 const (
-	High            = "high"
-	Rumina          = "rumina"
-	WeeklyActive    = "weekly_active"
-	XRuminaDisc     = "x_rumina_disc"
-	XChangeDiscount = "x_change_discount"
-	ActiveLow       = "active_low"
-	ActiveMiddle    = "active_middle"
-	ActiveHigh      = "active_high"
-	MaxHabit        = "max_habit"
-	HealthWarning   = "health_warning"
-	MinWeeklyActive = "min_weekly_active"
-	MaxPenBehavior  = "pen_behavior"
+	High              = "high"
+	Rumina            = "rumina"
+	WeeklyActive      = "weekly_active"
+	XRuminaDisc       = "x_rumina_disc"
+	XChangeDiscount   = "x_change_discount"
+	ActiveLow         = "active_low"
+	ActiveMiddle      = "active_middle"
+	ActiveHigh        = "active_high"
+	MaxHabit          = "max_habit"
+	HealthWarning     = "health_warning"
+	MinWeeklyActive   = "min_weekly_active"
+	MaxPenBehavior    = "pen_behavior"
+	BeforeDayNeckRing = "before_day_neck_ring"
 )
 
 type NeckRingConfigure struct {

+ 8 - 0
model/neck_ring_health.go

@@ -27,6 +27,10 @@ type NeckRingHealth struct {
 	MinChew            int32                      `json:"minChew"`
 	MinInactive        int32                      `json:"minInactive"`
 	Score              int32                      `json:"score"`
+	FilterMilk         int32                      `json:"filterMilk"`
+	IsTransferGroup    pasturePb.IsShow_Kind      `json:"isTransferGroup"`
+	IsDryMilk          pasturePb.IsShow_Kind      `json:"isDryMilk"`
+	IsImmunization     pasturePb.IsShow_Kind      `json:"isImmunization"`
 	IsWorse            pasturePb.IsShow_Kind      `json:"isWorse"`
 	CheckResult        pasturePb.CheckResult_Kind `json:"checkResult"`
 	CheckUserId        int64                      `json:"checkUserId"`
@@ -61,7 +65,11 @@ func NewNeckRingHealth(habit *NeckActiveHabit, sumChew, chew3dago int32) *NeckRi
 		MinChew:            getAbleInt(habit.SumMinChew),
 		MinInactive:        getAbleInt(habit.SumInactive),
 		Score:              habit.Score,
+		FilterMilk:         0,
 		IsWorse:            0,
+		IsTransferGroup:    pasturePb.IsShow_No,
+		IsDryMilk:          pasturePb.IsShow_No,
+		IsImmunization:     pasturePb.IsShow_No,
 		CheckResult:        pasturePb.CheckResult_Pending,
 		IsShow:             pasturePb.IsShow_Ok,
 	}

+ 4 - 3
model/neck_ring_health_warning.go

@@ -34,8 +34,8 @@ func NewNeckRingHealthWarning(pastureId int64, neckRingHealth *NeckRingHealth, c
 	}
 
 	return &NeckRingHealthWarning{
-		NeckRingHealthId:   pastureId,
-		PastureId:          neckRingHealth.Id,
+		NeckRingHealthId:   neckRingHealth.Id,
+		PastureId:          pastureId,
 		CowId:              cow.Id,
 		EarNumber:          cow.EarNumber,
 		NeckRingNumber:     cow.NeckRingNumber,
@@ -76,10 +76,11 @@ func (n NeckRingHealthWarningSlice) ToPB(
 			MinChew:                v.MinChew,
 			MinIntake:              v.MinIntake,
 			SumChew:                v.ChewSum,
-			BeforeThreeDaysSumChew: v.BeforeThreeSumChew,
+			BeforeThreeDaysSumChew: v.ChewSum - v.BeforeThreeSumChew,
 			LastBreedEventDetails:  "",
 			Level:                  v.Level,
 			LevelName:              levelName,
+			ChangeChewTime:         v.ChewSum - v.BeforeThreeSumChew,
 		}
 
 		if cow, ok := cowMap[v.CowId]; ok {

+ 1 - 0
model/pen_behavior.go

@@ -62,6 +62,7 @@ func NewPenBehavior(data *PenBehaviorData, activeTime string) *PenBehavior {
 		IntakeRate: data.IntakeRate,
 		RestRate:   data.RestRate,
 		GaspRate:   data.GaspRate,
+		IsShow:     pasturePb.IsShow_No,
 	}
 }
 

+ 1 - 126
module/backend/analysis.go

@@ -9,9 +9,7 @@ import (
 	"time"
 
 	pasturePb "gitee.com/xuyiping_admin/go_proto/proto/go/backend/cow"
-	"gitee.com/xuyiping_admin/pkg/logger/zaplog"
 	"gitee.com/xuyiping_admin/pkg/xerr"
-	"go.uber.org/zap"
 )
 
 // WeightScatterPlot 体重散点图 获取图表数据
@@ -40,11 +38,7 @@ func (s *StoreEntry) WeightScatterPlot(ctx context.Context, req *pasturePb.Searc
 		pref.Where("admission_at BETWEEN ? AND ?", t0.Unix(), t1.Unix()+86399)
 	}
 
-	var count int64
-	if err = pref.Count(&count).
-		Limit(int(pagination.PageSize)).
-		Offset(int(pagination.PageOffset)).
-		Find(&cowList).Error; err != nil {
+	if err = pref.Find(&cowList).Error; err != nil {
 		return nil, err
 	}
 	if err != nil {
@@ -460,122 +454,3 @@ func (s *StoreEntry) AbortionRate(ctx context.Context, req *pasturePb.AbortionRa
 		},
 	}, nil
 }
-
-func (s *StoreEntry) TwentyOnePregnantRate(ctx context.Context, req *pasturePb.TwentyOnePregnantRateRequest) (*pasturePb.TwentyOnePregnantRateResponse, error) {
-	userModel, err := s.GetUserModel(ctx)
-	if err != nil {
-		return nil, xerr.WithStack(err)
-	}
-	startUnix := util.TimeParseLocalUnix(req.StartDate)
-	endUnix := util.TimeParseLocalUnix(req.EndDate)
-
-	if startUnix > endUnix {
-		return nil, xerr.Customf("开始时间不能大于结束时间: %s ~ %d", req.StartDate, req.EndDate)
-	}
-
-	nowDateTime := time.Now().Local()
-	if endUnix > nowDateTime.Unix() {
-		return nil, xerr.Customf("结束时间不能大于当前时间: %s ~ %s", req.EndDate, nowDateTime.Format(model.LayoutDate2))
-	}
-
-	dataRange, err := util.Get21DayPeriods(req.StartDate, req.EndDate)
-	if err != nil {
-		return nil, xerr.WithStack(err)
-	}
-	chart := &pasturePb.TwentyOnePregnantRateChart{
-		Header:       make([]string, 0),
-		PregnantRate: make([]float32, 0),
-		MatingRate:   make([]float32, 0),
-	}
-
-	// 牛只主动停配期
-	systemBasicName := ""
-	switch req.CowType {
-	case pasturePb.CowType_Breeding_Calf:
-		systemBasicName = model.ProactivelyStopBreedingForAdult
-	case pasturePb.CowType_Reserve_Calf:
-		systemBasicName = model.ProactivelyStopBreedingForBackup
-	default:
-		return nil, xerr.Customf("不支持的牛只类型: %d", req.CowType)
-	}
-
-	systemBasic, err := s.GetSystemBasicByName(ctx, userModel.AppPasture.Id, systemBasicName)
-	if err != nil {
-		return nil, xerr.WithStack(err)
-	}
-
-	stopBreedingDay := systemBasic.MinValue * 86400
-	dateCowList := make([][]*model.Cow, len(dataRange))
-
-	twentyOnePregnantRateList := make([]*pasturePb.TwentyOnePregnantRateList, 0)
-	for i, v := range dataRange {
-		middleDay, err := util.GetRangeDayMiddleDay(v, 11)
-		if err != nil {
-			return nil, xerr.WithStack(err)
-		}
-		middleDayUnix := util.TimeParseLocalEndUnix(middleDay)
-		chart.Header = append(chart.Header, fmt.Sprintf("%s ~ %s", v[0], v[1]))
-		cowList := s.TwentyOnePregnantCowList(userModel.AppPasture.Id, req.CowType, stopBreedingDay, middleDayUnix, []int64{})
-		twentyOnePregnantRateList = append(twentyOnePregnantRateList, &pasturePb.TwentyOnePregnantRateList{
-			StartDay:             v[0],
-			EndDay:               v[1],
-			ShouldBreedCount:     int32(len(cowList)),
-			RealityBreedCount:    0,
-			BreedRate:            0,
-			ShouldPregnantCount:  0,
-			RealityPregnantCount: 0,
-			PregnantRate:         0,
-			RealityAbortionCount: 0,
-			AbortionRate:         0,
-		})
-		dateCowList[i] = cowList
-	}
-
-	return &pasturePb.TwentyOnePregnantRateResponse{
-		Code: http.StatusOK,
-		Msg:  "ok",
-		Data: &pasturePb.TwentyOnePregnantRateData{
-			Chart: chart,
-			Table: &pasturePb.TwentyOnePregnantRateTable{
-				List:  twentyOnePregnantRateList,
-				Total: int32(len(dataRange)),
-			},
-		},
-	}, nil
-}
-
-// TwentyOnePregnantCowList 21天牛只停配期牛只列表
-func (s *StoreEntry) TwentyOnePregnantCowList(
-	pastureId int64,
-	cowType pasturePb.CowType_Kind,
-	stopBreedingDay int32,
-	middleDay int64,
-	notInCow []int64,
-) []*model.Cow {
-	cowList := make([]*model.Cow, 0)
-	switch cowType {
-	case pasturePb.CowType_Reserve_Calf:
-		pref := s.DB.Model(new(model.Cow)).
-			Where("pasture_id = ?", pastureId).
-			Where("cow_type = ?", cowType).
-			Where("admission_status = ?", pasturePb.AdmissionStatus_Admission).
-			Where("is_pregnant = ?", pasturePb.IsShow_No).
-			Where("lact = ?", 0).
-			Where("birth_at + ? < ?", stopBreedingDay, middleDay)
-		if len(notInCow) > 0 {
-			pref = pref.Where("id NOT IN ?", notInCow)
-		}
-		if err := pref.Find(&cowList).Error; err != nil {
-			zaplog.Error("TwentyOnePregnantCowList",
-				zap.Any("cowType", cowType),
-				zap.Any("stopBreedingDay", stopBreedingDay),
-				zap.Any("middleDay", middleDay),
-				zap.Any("notInCow", notInCow),
-			)
-		}
-	case pasturePb.CowType_Breeding_Calf:
-
-	}
-
-	return cowList
-}

+ 255 - 0
module/backend/analysis_cow.go

@@ -0,0 +1,255 @@
+package backend
+
+import (
+	"context"
+	"fmt"
+	"kpt-pasture/model"
+	"kpt-pasture/util"
+	"math"
+	"net/http"
+	"time"
+
+	pasturePb "gitee.com/xuyiping_admin/go_proto/proto/go/backend/cow"
+	"gitee.com/xuyiping_admin/pkg/xerr"
+)
+
+func (s *StoreEntry) TwentyOnePregnantRate(ctx context.Context, req *pasturePb.TwentyOnePregnantRateRequest) (*pasturePb.TwentyOnePregnantRateResponse, error) {
+	userModel, err := s.GetUserModel(ctx)
+	if err != nil {
+		return nil, xerr.WithStack(err)
+	}
+
+	startUnix := util.TimeParseLocalUnix(req.StartDate)
+	endUnix := util.TimeParseLocalUnix(req.EndDate)
+
+	if startUnix > endUnix {
+		return nil, xerr.Customf("开始时间不能大于结束时间: %s ~ %d", req.StartDate, req.EndDate)
+	}
+
+	nowDateTime := time.Now().Local()
+	if endUnix > nowDateTime.Unix() {
+		return nil, xerr.Customf("结束时间不能大于当前时间: %s ~ %s", req.EndDate, nowDateTime.Format(model.LayoutDate2))
+	}
+
+	dataRange, err := util.Get21DayPeriods(req.StartDate, req.EndDate)
+	if err != nil {
+		return nil, xerr.WithStack(err)
+	}
+
+	chart := &pasturePb.TwentyOnePregnantRateChart{
+		Header:       make([]string, 0),
+		PregnantRate: make([]float32, 0),
+		MatingRate:   make([]float32, 0),
+	}
+
+	// 牛只主动停配期
+	systemBasicName := ""
+	switch req.CowType {
+	case pasturePb.CowType_Breeding_Calf:
+		systemBasicName = model.ProactivelyStopBreedingForAdult
+	case pasturePb.CowType_Reserve_Calf:
+		systemBasicName = model.ProactivelyStopBreedingForBackup
+	default:
+		return nil, xerr.Customf("不支持的牛只类型: %d", req.CowType)
+	}
+
+	systemBasic, err := s.GetSystemBasicByName(ctx, userModel.AppPasture.Id, systemBasicName)
+	if err != nil {
+		return nil, xerr.WithStack(err)
+	}
+
+	stopBreedingDay := systemBasic.MinValue
+
+	twentyOnePregnantRateList := make([]*pasturePb.TwentyOnePregnantRateList, 0)
+	for _, v := range dataRange {
+		middleDay, err := util.GetRangeDayMiddleDay(v, 11)
+		if err != nil {
+			return nil, xerr.WithStack(err)
+		}
+
+		_, shouldBreedCount := s.TwentyOnePregnantShouldBreedList(userModel.AppPasture.Id, req.CowType, stopBreedingDay, middleDay)
+		realityBreedCowList, realityBreedCount := s.TwentyOnePregnantRealityBreedList(userModel.AppPasture.Id, req.CowType, v[0], v[1])
+
+		breedRate, abortionRate, realityPregnantRate := float32(0), float32(0), float32(0)
+		if realityBreedCount > 0 && shouldBreedCount > 0 {
+			breedRate = float32(math.Round(float64(realityBreedCount)/float64(shouldBreedCount)*100) / 100)
+		}
+
+		realityPregnantCount, shouldPregnantCount, realityAbortionCount := int32(0), int32(0), int32(0)
+		for _, eventMating := range realityBreedCowList {
+			if eventMating.MatingResult == pasturePb.MatingResult_Pregnant {
+				realityPregnantCount++
+			}
+
+			if eventMating.MatingResult == pasturePb.MatingResult_Abort {
+				realityAbortionCount++
+			}
+
+			if s.IsDeparture(ctx, userModel.AppPasture.Id, eventMating.CowId, 35) {
+				shouldPregnantCount++
+			}
+		}
+
+		if realityPregnantCount > 0 && shouldPregnantCount > 0 {
+			realityPregnantRate = float32(math.Round(float64(realityPregnantCount)/float64(shouldPregnantCount)*100) / 100)
+		}
+
+		if realityAbortionCount > 0 && realityPregnantCount > 0 {
+			abortionRate = float32(math.Round(float64(realityAbortionCount)/float64(realityPregnantCount)*100) / 100)
+		}
+
+		chart.Header = append(chart.Header, fmt.Sprintf("%s ~ %s", v[0][5:], v[1][5:]))
+		chart.PregnantRate = append(chart.PregnantRate, realityPregnantRate)
+		chart.MatingRate = append(chart.MatingRate, breedRate)
+
+		twentyOnePregnantRateList = append(twentyOnePregnantRateList, &pasturePb.TwentyOnePregnantRateList{
+			StartDay:             v[0],
+			EndDay:               v[1],
+			ShouldBreedCount:     shouldBreedCount,     // 应配种
+			RealityBreedCount:    realityBreedCount,    // 实际配种
+			BreedRate:            breedRate,            // 配种率
+			ShouldPregnantCount:  shouldPregnantCount,  // 应怀孕
+			RealityPregnantCount: realityPregnantCount, // 实际怀孕
+			PregnantRate:         realityPregnantRate,  // 怀孕率
+			RealityAbortionCount: realityAbortionCount, // 实际流产
+			AbortionRate:         abortionRate,         // 流产率
+		})
+	}
+
+	return &pasturePb.TwentyOnePregnantRateResponse{
+		Code: http.StatusOK,
+		Msg:  "ok",
+		Data: &pasturePb.TwentyOnePregnantRateData{
+			Chart: chart,
+			Table: &pasturePb.TwentyOnePregnantRateTable{
+				List:  twentyOnePregnantRateList,
+				Total: int32(len(dataRange)),
+			},
+		},
+	}, nil
+}
+
+// TwentyOnePregnantShouldBreedList 21天牛应配牛只列表
+func (s *StoreEntry) TwentyOnePregnantShouldBreedList(pastureId int64, cowType pasturePb.CowType_Kind, stopBreedingDay int32, middleDay string) ([]*model.CowCalving, int32) {
+	everyDayCalvingList := make([]*model.CowCalving, 0)
+	if err := s.DB.Model(new(model.CowCalving)).
+		Where("pasture_id = ?", pastureId).
+		Where("cow_type = ?", cowType).
+		Where("date_time = ?", middleDay).
+		Where("calving_age >= ?", stopBreedingDay).
+		Where("is_abortion = ?", pasturePb.IsShow_No).
+		Where("is_departure = ?", pasturePb.IsShow_No).
+		Where("is_forbidden = ?", pasturePb.IsShow_No).
+		Find(&everyDayCalvingList).Error; err != nil {
+		return everyDayCalvingList, 0
+	}
+
+	return everyDayCalvingList, int32(len(everyDayCalvingList))
+}
+
+func (s *StoreEntry) TwentyOnePregnantRealityBreedList(pastureId int64, cowType pasturePb.CowType_Kind, startDate, endDate string) ([]*model.EventMating, int32) {
+	eventMatingList := make([]*model.EventMating, 0)
+	if err := s.DB.Model(new(model.EventMating)).
+		Where("pasture_id = ?", pastureId).
+		Where("cow_type = ?", cowType).
+		Where("reality_day BETWEEN ? AND ?", util.TimeParseLocalUnix(startDate), util.TimeParseLocalEndUnix(endDate)).
+		Where("status = ?", pasturePb.IsShow_Ok).
+		Find(&eventMatingList).Error; err != nil {
+		return eventMatingList, 0
+	}
+	return eventMatingList, int32(len(eventMatingList))
+}
+
+// IsDeparture 是否离场并且在配种后35天
+func (s *StoreEntry) IsDeparture(ctx context.Context, pastureId, cowId int64, days int32) bool {
+	cowInfo := &model.Cow{}
+	if err := s.DB.Model(new(model.Cow)).
+		Where("pasture_id = ?", pastureId).
+		Where("sex = ?", pasturePb.Genders_Female).
+		Where("id = ?", cowId).First(cowInfo).Error; err != nil {
+		return false
+	}
+
+	matingUnix := time.Unix(cowInfo.LastMatingAt, 0).Local().AddDate(0, 0, int(days)).Unix()
+	departureAt := cowInfo.DepartureAt
+	if departureAt > 0 && matingUnix >= matingUnix {
+		return true
+	}
+	return false
+}
+
+func (s *StoreEntry) TwentyOnePregnantDetail(ctx context.Context, req *pasturePb.TwentyOnePregnantDetailsRequest) (*pasturePb.TwentyOnePregnantDetailsResponse, error) {
+	userModel, err := s.GetUserModel(ctx)
+	if err != nil {
+		return nil, xerr.WithStack(err)
+	}
+	pastureId := userModel.AppPasture.Id
+	list := make([]*pasturePb.TwentyOnePregnantItems, 0)
+
+	// 牛只主动停配期
+	systemBasicName := ""
+	switch req.CowType {
+	case pasturePb.CowType_Breeding_Calf:
+		systemBasicName = model.ProactivelyStopBreedingForAdult
+	case pasturePb.CowType_Reserve_Calf:
+		systemBasicName = model.ProactivelyStopBreedingForBackup
+	default:
+		return nil, xerr.Customf("不支持的牛只类型: %d", req.CowType)
+	}
+
+	systemBasic, err := s.GetSystemBasicByName(ctx, userModel.AppPasture.Id, systemBasicName)
+	if err != nil {
+		return nil, xerr.WithStack(err)
+	}
+	stopBreedingDay := systemBasic.MinValue
+
+	middleDay, err := util.GetRangeDayMiddleDay([]string{req.StartDate, req.EndDate}, 11)
+	if err != nil {
+		return nil, xerr.WithStack(err)
+	}
+
+	cowTypeMap := s.CowTypeMap()
+	switch req.Type {
+	case pasturePb.TwentyOnePregnantType_ShouldBreed:
+		shouldBreedCowList, _ := s.TwentyOnePregnantShouldBreedList(pastureId, req.CowType, stopBreedingDay, middleDay)
+		list = model.CowCalvingSlice(shouldBreedCowList).ToPB()
+	case pasturePb.TwentyOnePregnantType_RealityBreed:
+		realityBreedCowList, _ := s.TwentyOnePregnantRealityBreedList(userModel.AppPasture.Id, req.CowType, req.StartDate, req.EndDate)
+		list = model.EventMatingSlice(realityBreedCowList).ToPB3(false, cowTypeMap)
+	case pasturePb.TwentyOnePregnantType_ShouldPregnant:
+		realityBreedCowList, _ := s.TwentyOnePregnantRealityBreedList(userModel.AppPasture.Id, req.CowType, req.StartDate, req.EndDate)
+		newShouldBreedCowList := make([]*model.EventMating, 0)
+		for _, v := range realityBreedCowList {
+			if s.IsDeparture(ctx, v.PastureId, v.CowId, stopBreedingDay) {
+				newShouldBreedCowList = append(newShouldBreedCowList, v)
+			}
+		}
+		list = model.EventMatingSlice(newShouldBreedCowList).ToPB3(false, cowTypeMap)
+	case pasturePb.TwentyOnePregnantType_RealityPregnant:
+		realityBreedCowList, _ := s.TwentyOnePregnantRealityBreedList(userModel.AppPasture.Id, req.CowType, req.StartDate, req.EndDate)
+		list = model.EventMatingSlice(realityBreedCowList).ToPB3(true, cowTypeMap)
+	case pasturePb.TwentyOnePregnantType_RealityAbortion:
+		realityBreedCowList, _ := s.TwentyOnePregnantRealityBreedList(userModel.AppPasture.Id, req.CowType, req.StartDate, req.EndDate)
+		list = model.EventMatingSlice(realityBreedCowList).ToPB4(cowTypeMap)
+	}
+	return &pasturePb.TwentyOnePregnantDetailsResponse{
+		Code: http.StatusOK,
+		Msg:  "ok",
+		Data: &pasturePb.TwentyOnePregnantData{
+			List: list,
+			Header: map[string]string{
+				"earNumber":                    "牛号",
+				"lact":                         "胎次",
+				"matingDateFormat":             "配种日期",
+				"matingTimes":                  "配次",
+				"pregnantCheckDateFormat":      "孕检日期",
+				"isMating":                     "是否有胎",
+				"abortionDateFormat":           "流产日期",
+				"departureDateFormat":          "离场日期",
+				"expectedProductionDateFormat": "预产日期",
+			},
+			HeaderSort: []string{"earNumber", "lact", "matingDateFormat", "matingTimes", "pregnantCheckDateFormat",
+				"isMating", "abortionDateFormat", "departureDateFormat", "expectedProductionDateFormat"},
+		},
+	}, nil
+}

+ 113 - 0
module/backend/analysis_more.go

@@ -70,6 +70,7 @@ func (s *StoreEntry) PenBehaviorDaily(ctx context.Context, req *pasturePb.BarnMo
 		}
 		headers = append(headers, "方差")
 	}
+
 	penBehaviorDayModelList := make([]*model.PenBehaviorDayModel, 0)
 	pref := s.DB.Model(new(model.PenBehaviorDay)).
 		Select(`distinct(heat_date) as heat_date,pen_id,pen_name,rumina_std,cow_count,day_rumina,day_intake,
@@ -137,6 +138,30 @@ func (s *StoreEntry) CowBehaviorDistribution(ctx context.Context, req *pasturePb
 		Breed:      make([]*pasturePb.CowBehaviorData, 0),
 		Pregnant:   make([]*pasturePb.CowBehaviorData, 0),
 		Empty:      make([]*pasturePb.CowBehaviorData, 0),
+		UnBreedIQR: &pasturePb.IQR{
+			MaxY: 0,
+			MinY: 0,
+			MaxX: 0,
+			MinX: 0,
+		},
+		BreedIQR: &pasturePb.IQR{
+			MaxY: 0,
+			MinY: 0,
+			MaxX: 0,
+			MinX: 0,
+		},
+		PregnantIQR: &pasturePb.IQR{
+			MaxY: 0,
+			MinY: 0,
+			MaxX: 0,
+			MinX: 0,
+		},
+		EmptyIQR: &pasturePb.IQR{
+			MaxY: 0,
+			MinY: 0,
+			MaxX: 0,
+			MinX: 0,
+		},
 	}
 
 	breedStatus := s.BreedStatusEnumList()
@@ -221,24 +246,83 @@ func (s *StoreEntry) CowBehaviorDistribution(ctx context.Context, req *pasturePb
 		data.MedianLine["breed"] = float32(getMedian(data.Breed, func(p *pasturePb.CowBehaviorData) int {
 			return int(p.DayData)
 		}))
+		data.BreedIQR = &pasturePb.IQR{
+			MaxY: getIQR3(data.Breed, func(p *pasturePb.CowBehaviorData) int {
+				return int(p.DayData)
+			}),
+			MinY: getIQR1(data.Breed, func(p *pasturePb.CowBehaviorData) int {
+				return int(p.DayData)
+			}),
+			MaxX: getIQR3(data.Breed, func(p *pasturePb.CowBehaviorData) int {
+				return int(p.CalvingAge)
+			}),
+			MinX: getIQR1(data.Breed, func(p *pasturePb.CowBehaviorData) int {
+				return int(p.CalvingAge)
+			}),
+		}
 	}
 
 	if len(data.Pregnant) > 0 {
 		data.MedianLine["pregnant"] = float32(getMedian(data.Pregnant, func(p *pasturePb.CowBehaviorData) int {
 			return int(p.DayData)
 		}))
+
+		data.PregnantIQR = &pasturePb.IQR{
+			MaxY: getIQR3(data.Pregnant, func(p *pasturePb.CowBehaviorData) int {
+				return int(p.DayData)
+			}),
+			MinY: getIQR1(data.Pregnant, func(p *pasturePb.CowBehaviorData) int {
+				return int(p.DayData)
+			}),
+			MaxX: getIQR3(data.Pregnant, func(p *pasturePb.CowBehaviorData) int {
+				return int(p.CalvingAge)
+			}),
+			MinX: getIQR1(data.Pregnant, func(p *pasturePb.CowBehaviorData) int {
+				return int(p.CalvingAge)
+			}),
+		}
 	}
 
 	if len(data.Empty) > 0 {
 		data.MedianLine["empty"] = float32(getMedian(data.Empty, func(p *pasturePb.CowBehaviorData) int {
 			return int(p.DayData)
 		}))
+
+		data.EmptyIQR = &pasturePb.IQR{
+			MaxY: getIQR3(data.Empty, func(p *pasturePb.CowBehaviorData) int {
+				return int(p.DayData)
+			}),
+			MinY: getIQR1(data.Empty, func(p *pasturePb.CowBehaviorData) int {
+				return int(p.DayData)
+			}),
+			MaxX: getIQR3(data.Empty, func(p *pasturePb.CowBehaviorData) int {
+				return int(p.CalvingAge)
+			}),
+			MinX: getIQR1(data.Empty, func(p *pasturePb.CowBehaviorData) int {
+				return int(p.CalvingAge)
+			}),
+		}
 	}
 
 	if len(data.UnBreed) > 0 {
 		data.MedianLine["unBreed"] = float32(getMedian(data.UnBreed, func(p *pasturePb.CowBehaviorData) int {
 			return int(p.DayData)
 		}))
+
+		data.UnBreedIQR = &pasturePb.IQR{
+			MaxY: getIQR3(data.UnBreed, func(p *pasturePb.CowBehaviorData) int {
+				return int(p.DayData)
+			}),
+			MinY: getIQR1(data.UnBreed, func(p *pasturePb.CowBehaviorData) int {
+				return int(p.DayData)
+			}),
+			MaxX: getIQR3(data.UnBreed, func(p *pasturePb.CowBehaviorData) int {
+				return int(p.CalvingAge)
+			}),
+			MinX: getIQR1(data.UnBreed, func(p *pasturePb.CowBehaviorData) int {
+				return int(p.CalvingAge)
+			}),
+		}
 	}
 
 	return &pasturePb.CowBehaviorDistributionResponse{
@@ -270,3 +354,32 @@ func getMedian(dataList []*pasturePb.CowBehaviorData, getField func(*pasturePb.C
 	}
 	return float64(values[n/2-1]+values[n/2]) / 2.0
 }
+
+func getIQR3(dataList []*pasturePb.CowBehaviorData, getField func(*pasturePb.CowBehaviorData) int) int32 {
+	values := make([]int, len(dataList))
+	for i, p := range dataList {
+		values[i] = getField(p)
+	}
+	sort.Ints(values)
+	n := len(values)
+	if n < 3 {
+		return 0
+	}
+	index := (n + 1) * 3 / 4
+
+	return int32(values[index])
+}
+
+func getIQR1(dataList []*pasturePb.CowBehaviorData, getField func(*pasturePb.CowBehaviorData) int) int32 {
+	values := make([]int, len(dataList))
+	for i, p := range dataList {
+		values[i] = getField(p)
+	}
+	sort.Ints(values)
+	n := len(values)
+	if n < 3 {
+		return 0
+	}
+	index := (n + 1) / 4
+	return int32(values[index])
+}

+ 137 - 10
module/backend/cow.go

@@ -7,6 +7,7 @@ import (
 	"kpt-pasture/model"
 	"kpt-pasture/util"
 	"net/http"
+	"sort"
 	"strings"
 	"time"
 
@@ -23,10 +24,17 @@ func (s *StoreEntry) Detail(ctx context.Context, req *pasturePb.SearchEventReque
 		return nil, xerr.WithStack(err)
 	}
 
+	if req.EarNumber == "" && req.NeckRingNumber == "" {
+		return nil, xerr.Custom("请输入牛号或项圈号")
+	}
+
 	cowInfo := &model.Cow{}
 	pref := s.DB.Model(new(model.Cow)).
-		Where("pasture_id = ?", userModel.AppPasture.Id).
-		Where("ear_number = ?", req.EarNumber)
+		Where("pasture_id = ?", userModel.AppPasture.Id)
+
+	if req.EarNumber != "" {
+		pref.Where("ear_number = ?", req.EarNumber)
+	}
 
 	if req.NeckRingNumber != "" {
 		pref.Where("neck_ring_number = ?", req.NeckRingNumber)
@@ -180,7 +188,7 @@ func (s *StoreEntry) EventList(ctx context.Context, req *pasturePb.SearchCowEven
 		pref.Where("event_type = ?", req.EventCategoryKind)
 	}
 
-	if err = pref.Order("id desc").
+	if err = pref.Order("event_at DESC").
 		Limit(int(pagination.PageSize)).
 		Offset(int(pagination.PageOffset)).
 		Find(&eventCowLogList).Error; err != nil {
@@ -215,6 +223,15 @@ func (s *StoreEntry) BehaviorCurve(ctx context.Context, req *pasturePb.CowBehavi
 	endDataTime := nowTime.Format(model.LayoutDate2)
 	startDataTime := nowTime.AddDate(0, 0, -30).Format(model.LayoutDate2)
 
+	dayRange, err := util.GetDaysBetween(startDataTime, endDataTime)
+	if err != nil {
+		return nil, xerr.WithStack(err)
+	}
+
+	if len(dayRange) <= 0 {
+		return nil, xerr.Customf("错误的日期范围")
+	}
+
 	// 行为曲线数据
 	neckActiveHabitList := make([]*model.NeckActiveHabit, 0)
 	if err = s.DB.Table(new(model.NeckActiveHabit).TableName()).
@@ -222,13 +239,16 @@ func (s *StoreEntry) BehaviorCurve(ctx context.Context, req *pasturePb.CowBehavi
 		Where("pasture_id = ?", userModel.AppPasture.Id).
 		Where("is_show = ?", pasturePb.IsShow_Ok).
 		Where("cow_id > ?", 0).
-		Where("heat_date BETWEEN ? AND ?", startDataTime, endDataTime).
+		Where("heat_date IN (?)", dayRange).
 		Order("heat_date, frameid").
 		Find(&neckActiveHabitList).Error; err != nil {
 		return nil, xerr.WithStack(err)
 	}
 
 	data := model.NeckActiveHabitSlice(neckActiveHabitList).ToPB(req.CurveName)
+	q1, q3 := s.CowIQR(ctx, cowInfo, req.CurveName, dayRange, data.DateTimeList)
+	data.IQR3 = q3
+	data.IQR1 = q1
 	eventMapList := s.EventTypeMap()
 	for k, v := range eventMapList {
 		if k == pasturePb.EventType_Enter || k == pasturePb.EventType_Body_Score || k == pasturePb.EventType_Birth ||
@@ -303,6 +323,92 @@ func (s *StoreEntry) BehaviorCurve(ctx context.Context, req *pasturePb.CowBehavi
 	}, nil
 }
 
+func (s *StoreEntry) CowIQR(ctx context.Context, cowInfo *model.Cow, curveName string, dayRange []string, dateTimeList []string) ([]int32, []int32) {
+	q1, q3 := make([]int32, 0), make([]int32, 0)
+	if curveName == "" || curveName == "active" || curveName == "behavior" || len(dateTimeList) <= 0 {
+		return q1, q3
+	}
+
+	penId := cowInfo.PenId
+	cowList := make([]*model.Cow, 0)
+	if err := s.DB.Table(new(model.Cow).TableName()).
+		Where("pen_id = ?", penId).
+		Where("pasture_id = ?", cowInfo.PastureId).
+		Where("neck_ring_number != ?", "").
+		Find(&cowList).Error; err != nil {
+		return q1, q3
+	}
+
+	cowIds := make([]int64, 0)
+	for _, cow := range cowList {
+		cowIds = append(cowIds, cow.Id)
+	}
+
+	// 行为曲线数据
+	neckActiveHabitList := make([]*model.NeckActiveHabit, 0)
+	if err := s.DB.Table(new(model.NeckActiveHabit).TableName()).
+		Select("rumina,intake,inactive,gasp,high,active,active_time").
+		Where("pasture_id = ?", cowInfo.PastureId).
+		Where("is_show = ?", pasturePb.IsShow_Ok).
+		Where("cow_id IN (?)", cowIds).
+		Where("heat_date BETWEEN ? AND ?", dayRange[0], dayRange[len(dayRange)-1]).
+		Find(&neckActiveHabitList).Error; err != nil {
+		return q1, q3
+	}
+
+	penOriginal := make(map[string][]int32)
+	for _, dt := range dateTimeList {
+		var info bool
+		for _, habit := range neckActiveHabitList {
+			if !strings.Contains(habit.ActiveTime, dt) {
+				continue
+			}
+			info = true
+
+			switch curveName {
+			case "rumina":
+				penOriginal[dt] = append(penOriginal[dt], habit.Rumina)
+			case "intake":
+				penOriginal[dt] = append(penOriginal[dt], habit.Intake)
+			case "inactive":
+				penOriginal[dt] = append(penOriginal[dt], habit.Inactive)
+			case "chew":
+				penOriginal[dt] = append(penOriginal[dt], habit.Rumina+habit.Intake)
+			case "immobility":
+				penOriginal[dt] = append(penOriginal[dt], 120-habit.Active)
+			}
+		}
+		if !info {
+			penOriginal[dt] = append(penOriginal[dt], int32(0))
+		}
+	}
+
+	if len(penOriginal) > 0 {
+		for _, dataList := range penOriginal {
+			dl := len(dataList)
+			if dl < 4 {
+				q1 = append(q1, int32(0))
+				q3 = append(q3, int32(0))
+				continue
+			}
+
+			sort.Slice(dataList, func(i, j int) bool {
+				return dataList[i] < dataList[j]
+			})
+
+			v1 := (len(dataList) + 1) / 4
+			// 防止下标溢出panic
+			s1 := float64(dataList[v1-1]) + 0.25*float64(dataList[v1]-dataList[v1-1])
+			v3 := v1 * 3
+			s3 := float64(dataList[v3-1]) + 0.75*float64(dataList[v3]-dataList[v3-1])
+
+			q1 = append(q1, int32(s1))
+			q3 = append(q3, int32(s3))
+		}
+	}
+	return q1, q3
+}
+
 func (s *StoreEntry) CowGrowthCurve(ctx context.Context, req *pasturePb.CowGrowthCurveRequest) (*pasturePb.CowGrowthCurveResponse, error) {
 	userModel, err := s.GetUserModel(ctx)
 	if err != nil {
@@ -421,7 +527,7 @@ func (s *StoreEntry) BehaviorRate(ctx context.Context, req *pasturePb.CowBehavio
 
 	cowInfo, err := s.GetCowInfoByEarNumber(ctx, userModel.AppPasture.Id, req.EarNumber)
 	if err != nil {
-		return nil, xerr.Customf("错误的牛只信息: %d", req.EarNumber)
+		return nil, xerr.Customf("错误的牛只信息: %s", req.EarNumber)
 	}
 
 	if req.EndAt <= 0 || req.StartAt <= 0 || req.EndAt < req.StartAt {
@@ -436,10 +542,6 @@ func (s *StoreEntry) BehaviorRate(ctx context.Context, req *pasturePb.CowBehavio
 		return nil, xerr.WithStack(err)
 	}
 
-	if cowInfo.NeckRingNumber == "" {
-		return nil, xerr.Customf("该牛只未佩戴脖环: %s", req.EarNumber)
-	}
-
 	neckActiveHabitList := make([]*model.NeckActiveHabit, 0)
 	if err = s.DB.Model(new(model.NeckActiveHabit)).
 		Select("heat_date,SUM(rumina) as rumina,SUM(intake) as intake,SUM(inactive) as inactive,SUM(gasp) AS gasp").
@@ -452,9 +554,34 @@ func (s *StoreEntry) BehaviorRate(ctx context.Context, req *pasturePb.CowBehavio
 		Find(&neckActiveHabitList).Error; err != nil {
 	}
 
+	cowList := make([]*model.Cow, 0)
+	if err = s.DB.Model(new(model.Cow)).
+		Where("neck_ring_number != ?", "").
+		Where("pasture_id = ?", userModel.AppPasture.Id).
+		Where("pen_id = ?", cowInfo.PenId).
+		Find(&cowList).Error; err != nil {
+	}
+
+	neckRingNumbers := make([]string, 0)
+	for _, v := range cowList {
+		neckRingNumbers = append(neckRingNumbers, v.NeckRingNumber)
+	}
+
+	groupNeckActiveHabitList := make([]*model.NeckActiveHabit, 0)
+	if err = s.DB.Model(new(model.NeckActiveHabit)).
+		Select("heat_date,SUM(rumina) as rumina,SUM(intake) as intake,SUM(inactive) as inactive,SUM(gasp) AS gasp").
+		Where("neck_ring_number IN ?", neckRingNumbers).
+		Where("pasture_id = ?", userModel.AppPasture.Id).
+		Where("cow_id > ?", 0).
+		Where("heat_date BETWEEN ? AND ?", t1, t2).
+		Order("heat_date").
+		Group("heat_date").
+		Find(&groupNeckActiveHabitList).Error; err != nil {
+	}
+
 	return &pasturePb.CowBehaviorRateResponse{
 		Code: http.StatusOK,
 		Msg:  "ok",
-		Data: model.NeckActiveHabitSlice(neckActiveHabitList).ToPB2(dataBetween),
+		Data: model.NeckActiveHabitSlice(neckActiveHabitList).ToPB2(dataBetween, groupNeckActiveHabitList),
 	}, nil
 }

+ 7 - 4
module/backend/dashboard.go

@@ -83,7 +83,7 @@ func (s *StoreEntry) NeckRingWarning(ctx context.Context) (*pasturePb.IndexNeckR
 	}
 
 	healthWarningNumber := int64(0)
-	if err = s.DB.Model(new(model.NeckRingHealth)).
+	if err = s.DB.Model(new(model.NeckRingHealthWarning)).
 		Where("pasture_id = ?", userModel.AppPasture.Id).
 		Group("cow_id").
 		Count(&healthWarningNumber).Error; err != nil {
@@ -256,13 +256,13 @@ func (s *StoreEntry) DataWarningList(ctx context.Context) (*pasturePb.IndexDataW
 		userDataWarning = defaultDataWarning
 	}
 
-	newTime := time.Now().Local().Unix()
+	//newTime := time.Now().Local().Unix()
 	needUpdateWarningIds := make([]int64, 0)
 	for _, warningData := range userDataWarning {
 		// 如果预警数据更新时间大于预警条件更新时间,并且更新时间距离当前时间小于2小时,则跳过
-		if warningData.DataUpdateAt > warningData.ConditionUpdateAt && newTime-warningData.DataUpdateAt < int64(2*time.Hour) {
+		/*if warningData.DataUpdateAt > warningData.ConditionUpdateAt && newTime-warningData.DataUpdateAt < int64(2*time.Hour) {
 			continue
-		}
+		}*/
 		needUpdateWarningIds = append(needUpdateWarningIds, warningData.Id)
 	}
 
@@ -551,6 +551,9 @@ func (s *StoreEntry) UpdateWarningData(ctx context.Context, pastureId int64, nee
 		if len(query) == 0 || len(params) == 0 {
 			continue
 		}
+
+		zaplog.Info("UpdateWarningData", zap.Any("query", query), zap.Any("params", params))
+
 		var count int64
 		if err = s.DB.Model(new(model.Cow)).
 			Where("pasture_id = ?", pastureId).

+ 4 - 0
module/backend/goods.go

@@ -245,6 +245,10 @@ func (s *StoreEntry) NeckRingList(ctx context.Context, req *pasturePb.SearchNeck
 		pref.Where("a.neck_ring_number like ?", fmt.Sprintf("%s%s%s", "%", req.Number, "%"))
 	}
 
+	if req.PenId > 0 {
+		pref.Where("b.pen_id = ?", req.PenId)
+	}
+
 	if err = pref.Order("a.id desc").
 		Count(&count).
 		Limit(int(pagination.PageSize)).

+ 4 - 0
module/backend/interface.go

@@ -288,6 +288,7 @@ type AnalyseService interface {
 	PenWeight(ctx context.Context, req *pasturePb.PenWeightRequest, pagination *pasturePb.PaginationModel) (*pasturePb.PenWeightResponse, error)
 	AbortionRate(ctx context.Context, req *pasturePb.AbortionRateRequest) (*pasturePb.AbortionRateResponse, error)
 	TwentyOnePregnantRate(ctx context.Context, req *pasturePb.TwentyOnePregnantRateRequest) (*pasturePb.TwentyOnePregnantRateResponse, error)
+	TwentyOnePregnantDetail(ctx context.Context, req *pasturePb.TwentyOnePregnantDetailsRequest) (*pasturePb.TwentyOnePregnantDetailsResponse, error)
 	PregnancyReport(ctx context.Context, req *pasturePb.PregnancyReportRequest, pagination *pasturePb.PaginationModel) (*pasturePb.PregnancyReportResponse, error)
 	CalvingReport(ctx context.Context, req *pasturePb.CalvingReportRequest) (*pasturePb.CalvingReportResponse, error)
 	DiseaseCureReport(ctx context.Context, req *pasturePb.DiseaseCureRateRequest) (*pasturePb.DiseaseCureRateResponse, error)
@@ -347,6 +348,7 @@ type MilkHallService interface {
 type UploadService interface {
 	Photos(ctx context.Context, files []*multipart.FileHeader) ([]string, error)
 	ImportExcel(ctx context.Context, data [][]string) error
+	ImportExcel2(ctx context.Context, data [][]string, excelHeader []string) error
 }
 
 type TestService interface {
@@ -356,4 +358,6 @@ type TestService interface {
 	TestDataWaring(ctx context.Context, userId int64) error
 	NeckRingOriginalAsync(ctx context.Context, pastureId int64, pagination *pasturePb.PaginationModel) error
 	PastureInit(ctx context.Context) error
+	AdmissionAge(ctx context.Context) error
+	CalvingAge(ctx context.Context) error
 }

+ 5 - 1
module/backend/neck_ring_warning.go

@@ -94,7 +94,11 @@ func (s *StoreEntry) NeckRingWarningHealthCowList(ctx context.Context, req *past
 		return nil, xerr.WithStack(err)
 	}
 	neckWaringHealthList := make([]*model.NeckRingHealthWarning, 0)
+	var count int64
+
 	pref := s.DB.Table(fmt.Sprintf("%s as a", new(model.NeckRingHealthWarning).TableName())).
+		Select(`MAX(a.id) as id,a.cow_id,a.ear_number,a.neck_ring_number,a.score,a.heat_date,a.min_high,a.min_intake,
+		a.min_chew,a.chew_sum,a.before_three_sum_chew,a.level`).
 		Joins(fmt.Sprintf("JOIN cow AS b on a.cow_id = b.id")).
 		Where("a.score >= ?", 0).
 		Where("a.is_show = ?", pasturePb.IsShow_Ok).
@@ -111,8 +115,8 @@ func (s *StoreEntry) NeckRingWarningHealthCowList(ctx context.Context, req *past
 		pref.Where("a.level = ?", req.Level)
 	}
 
-	var count int64
 	if err = pref.Order("a.level DESC").
+		Group("a.cow_id").
 		Count(&count).
 		Limit(int(pagination.PageSize)).
 		Offset(int(pagination.PageOffset)).

+ 12 - 0
module/backend/sql.go

@@ -163,6 +163,18 @@ func (s *StoreEntry) PenMap(ctx context.Context, pastureId int64) map[int32]*mod
 	return penMap
 }
 
+func (s *StoreEntry) PenMap2(ctx context.Context, pastureId int64) map[string]*model.Pen {
+	penList, err := s.GetPenList(ctx, pastureId)
+	if err != nil {
+		zaplog.Error("GetPenList", zap.Any("err", err), zap.Any("pastureId", pastureId))
+	}
+	penMap := make(map[string]*model.Pen)
+	for _, v := range penList {
+		penMap[v.Name] = v
+	}
+	return penMap
+}
+
 func (s *StoreEntry) GetCowInfoByEarNumber(ctx context.Context, pastureId int64, earNumber string) (*model.Cow, error) {
 	cowInfo := &model.Cow{}
 	if err := s.DB.Model(new(model.Cow)).

+ 2996 - 0
module/backend/test_service.go

@@ -4,6 +4,7 @@ import (
 	"context"
 	"errors"
 	"kpt-pasture/model"
+	"kpt-pasture/util"
 
 	"gorm.io/gorm"
 
@@ -161,3 +162,2998 @@ func (s *StoreEntry) PastureInit(ctx context.Context) error {
 
 	return nil
 }
+
+func (s *StoreEntry) AdmissionAge(ctx context.Context) error {
+	admissionAgeMap := map[string]string{
+		"731268": "2020/9/5 4:20:48",
+		"049560": "2022/5/24 8:03:36",
+		"039676": "2022/5/24 9:17:18",
+		"061595": "2022/5/24 15:46:07",
+		"866100": "2024/10/5 10:02:00",
+		"772301": "2025/4/12 22:38:03",
+		"033000": "2021/1/1 18:53:43",
+		"044126": "2022/5/24 8:39:22",
+		"766740": "2024/9/10 16:46:58",
+		"869277": "2024/10/2 21:56:40",
+		"769579": "2024/6/19 20:36:18",
+		"731236": "2020/8/28 19:46:29",
+		"066786": "2022/7/31 0:00:00",
+		"830744": "2020/7/3 1:30:27",
+		"770745": "2024/9/14 11:58:00",
+		"770520": "2025/4/17 7:17:05",
+		"067126": "2022/5/24 17:37:31",
+		"769280": "2024/11/23 18:20:34",
+		"846286": "2022/6/1 23:10:15",
+		"058401": "2022/5/24 9:35:35",
+		"766704": "2024/9/7 19:16:53",
+		"771979": "2024/11/18 20:54:47",
+		"731014": "2020/7/2 6:05:25",
+		"731210": "2020/8/18 19:30:22",
+		"060257": "2022/5/24 16:50:38",
+		"043337": "2022/7/31 0:00:00",
+		"769286": "2024/11/24 18:43:04",
+		"871887": "2024/11/19 16:09:02",
+		"766458": "2024/8/28 19:49:39",
+		"034836": "2021/1/30 17:30:54",
+		"034884": "2021/2/15 16:24:22",
+		"122558": "2020/3/27 19:23:38",
+		"771935": "2024/10/22 22:49:06",
+		"770739": "2024/9/12 20:13:19",
+		"771917": "2024/10/19 22:36:59",
+		"182626": "2018/8/3 4:23:46",
+		"840540": "2022/1/9 20:06:36",
+		"766716": "2024/9/8 16:41:53",
+		"769256": "2024/11/2 19:02:35",
+		"771913": "2024/10/18 22:33:42",
+		"055258": "2022/7/31 0:00:00",
+		"621666": "2020/2/16 20:29:27",
+		"770707": "2024/10/14 18:14:07",
+		"770492": "2025/4/4 21:24:50",
+		"770805": "2024/9/21 21:00:54",
+		"060516": "2022/5/24 17:53:00",
+		"039251": "2022/5/24 17:33:20",
+		"765586": "2024/11/20 14:21:55",
+		"738360": "2021/6/30 21:15:03",
+		"043986": "2022/4/18 23:58:46",
+		"771945": "2024/10/24 22:53:03",
+		"830642": "2020/6/24 0:40:21",
+		"063236": "2022/5/24 16:04:08",
+		"865928": "2024/9/1 13:43:50",
+		"769212": "2024/10/20 22:44:48",
+		"766430": "2024/6/22 18:22:00",
+		"738976": "2021/9/4 21:56:38",
+		"770204": "2025/1/15 19:32:12",
+		"054857": "2022/5/24 10:50:38",
+		"128878": "2020/6/17 19:43:49",
+		"039582": "2022/5/24 11:05:45",
+		"766384": "2024/6/6 18:28:50",
+		"063481": "2022/5/24 17:04:04",
+		"622076": "2020/5/21 19:42:15",
+		"728108": "2020/5/22 8:55:56",
+		"420902": "2020/5/3 14:34:15",
+		"244842": "2022/4/12 13:20:59",
+		"049596": "2022/5/24 10:54:32",
+		"769236": "2024/10/25 22:56:29",
+		"127118": "2020/5/16 20:23:35",
+		"128490": "2020/6/13 6:25:00",
+		"906652": "2020/1/22 19:45:51",
+		"063510": "2022/5/24 10:58:12",
+		"766404": "2024/6/12 15:03:55",
+		"058645": "2022/7/31 0:00:00",
+		"425994": "2020/5/24 12:10:11",
+		"036988": "2021/3/21 15:56:01",
+		"030641": "2022/5/24 17:44:57",
+		"043418": "2022/7/31 0:00:00",
+		"769827": "2024/8/27 18:39:43",
+		"768748": "2024/10/12 10:06:35",
+		"769869": "2024/9/4 16:48:40",
+		"769336": "2024/12/16 22:40:25",
+		"772043": "2025/1/5 23:55:40",
+		"830622": "2020/6/22 23:11:03",
+		"770787": "2024/9/17 18:59:17",
+		"181662": "2018/6/9 21:38:58",
+		"425964": "2020/5/21 0:10:29",
+		"036880": "2021/3/10 17:43:46",
+		"425936": "2020/5/18 1:08:40",
+		"768732": "2024/9/29 16:15:15",
+		"827918": "2020/6/15 22:00:24",
+		"831738": "2020/10/20 7:33:53",
+		"769067": "2024/11/3 19:32:17",
+		"766382": "2024/6/6 18:28:22",
+		"409156": "2019/10/22 8:58:24",
+		"765568": "2024/11/12 19:18:21",
+		"736448": "2021/4/4 15:53:29",
+		"731360": "2020/9/28 12:10:15",
+		"043972": "2022/4/14 17:12:06",
+		"769232": "2024/10/25 22:55:18",
+		"869164": "2024/11/10 19:01:18",
+		"766466": "2024/8/29 19:39:09",
+		"001579": "2022/7/31 0:00:00",
+		"023998": "2020/2/19 20:22:20",
+		"771991": "2024/11/18 20:55:31",
+		"846276": "2022/6/1 23:11:37",
+		"769555": "2024/6/10 16:42:27",
+		"772001": "2024/11/20 14:20:10",
+		"766756": "2024/9/12 9:40:50",
+		"128810": "2020/5/19 20:36:23",
+		"827840": "2020/6/10 13:40:22",
+		"606412": "2019/12/8 18:21:15",
+		"038020": "2022/5/24 10:15:06",
+		"731130": "2020/7/20 22:07:34",
+		"023331": "2022/5/24 8:17:05",
+		"038695": "2022/7/31 0:00:00",
+		"769260": "2024/11/12 19:18:03",
+		"769563": "2024/6/12 19:45:36",
+		"770518": "2025/4/16 22:48:08",
+		"026556": "2020/5/14 18:50:54",
+		"822286": "2020/6/1 13:50:54",
+		"770536": "2025/4/23 23:08:18",
+		"606450": "2019/12/15 20:20:45",
+		"063132": "2022/5/24 16:27:48",
+		"772187": "2025/2/27 23:40:16",
+		"770496": "2025/4/4 21:25:59",
+		"768760": "2024/10/13 18:28:33",
+		"182972": "2018/10/7 0:33:23",
+		"434312": "2021/4/10 14:09:56",
+		"728098": "2020/6/30 14:21:26",
+		"043984": "2022/4/17 10:49:11",
+		"725764": "2020/5/3 8:27:47",
+		"770464": "2025/3/10 22:29:33",
+		"772287": "2025/4/11 22:58:01",
+		"772151": "2025/1/31 15:47:47",
+		"827808": "2020/6/6 12:32:32",
+		"769314": "2024/12/11 23:33:41",
+		"766330": "2024/5/19 11:25:04",
+		"728050": "2020/6/21 17:05:18",
+		"728320": "2020/5/23 21:05:50",
+		"067067": "2022/5/24 8:30:57",
+		"768790": "2024/10/15 20:04:27",
+		"768791": "2024/11/12 19:16:51",
+		"731184": "2020/8/8 23:42:30",
+		"066076": "2022/5/24 18:50:43",
+		"728114": "2020/5/22 22:55:54",
+		"621998": "2020/4/5 23:00:17",
+		"431820": "2020/7/21 16:11:58",
+		"731240": "2020/8/30 13:58:59",
+		"043992": "2022/4/19 16:38:58",
+		"060613": "2022/5/24 17:23:16",
+		"035034": "2021/3/4 18:16:51",
+		"731038": "2020/7/4 18:25:29",
+		"770526": "2025/4/19 10:55:00",
+		"766474": "2024/8/31 19:13:52",
+		"825368": "2020/5/6 12:23:38",
+		"725824": "2020/5/14 21:16:24",
+		"771961": "2024/10/28 22:59:32",
+		"026480": "2020/5/8 19:31:17",
+		"039667": "2022/5/24 18:04:07",
+		"825338": "2020/5/3 16:30:22",
+		"144038": "2022/3/22 21:12:43",
+		"830770": "2020/7/6 1:30:26",
+		"770394": "2025/1/21 20:21:24",
+		"770667": "2024/9/26 10:17:58",
+		"044414": "2022/7/31 0:00:00",
+		"869285": "2024/10/5 9:58:47",
+		"772181": "2025/2/25 21:58:56",
+		"728080": "2020/6/26 20:00:02",
+		"772263": "2025/3/30 21:27:41",
+		"768782": "2024/10/14 16:35:23",
+		"026374": "2020/4/29 18:41:00",
+		"611028": "2019/12/21 16:36:39",
+		"049605": "2022/5/24 11:00:17",
+		"425940": "2020/5/18 11:22:40",
+		"770767": "2024/9/15 20:43:00",
+		"769515": "2024/6/1 20:11:19",
+		"224540": "2020/2/15 2:50:28",
+		"766470": "2024/8/31 19:12:15",
+		"825354": "2020/5/5 12:44:57",
+		"769230": "2024/10/23 22:52:46",
+		"063175": "2022/5/24 8:46:00",
+		"770733": "2024/9/12 9:51:12",
+		"770490": "2025/4/1 20:21:17",
+		"771921": "2024/10/19 22:39:28",
+		"038016": "2022/7/31 0:00:00",
+		"739438": "2021/10/19 10:30:59",
+		"769891": "2024/9/9 16:21:20",
+		"182711": "2018/8/7 19:18:15",
+		"825356": "2020/5/5 13:37:09",
+		"772113": "2025/1/12 20:07:42",
+		"036892": "2021/3/10 17:53:05",
+		"128514": "2020/6/18 3:51:10",
+		"766784": "2024/9/14 15:32:12",
+		"049160": "2022/5/24 18:58:37",
+		"769551": "2024/6/9 14:42:38",
+		"770530": "2025/4/20 23:35:13",
+		"210888": "2019/12/31 21:03:19",
+		"770703": "2024/10/12 18:15:00",
+		"765576": "2024/11/14 20:02:12",
+		"710680": "2019/10/7 8:12:43",
+		"060120": "2022/5/24 9:21:07",
+		"060117": "2022/7/31 0:00:00",
+		"038773": "2022/5/24 8:41:48",
+		"827974": "2020/6/20 4:25:05",
+		"771975": "2024/11/18 20:54:27",
+		"770789": "2024/9/18 15:53:14",
+		"058402": "2022/5/24 17:00:31",
+		"066266": "2022/5/24 17:06:16",
+		"049675": "2022/5/24 17:31:12",
+		"037068": "2021/3/30 16:58:29",
+		"027516": "2020/6/9 17:48:39",
+		"039602": "2022/5/24 8:18:08",
+		"769298": "2024/12/2 22:48:56",
+		"772063": "2024/12/9 19:32:27",
+		"063172": "2022/7/31 0:00:00",
+		"767755": "2024/11/2 18:30:26",
+		"766454": "2024/8/25 19:55:38",
+		"772239": "2025/3/12 23:11:25",
+		"767733": "2024/10/31 20:37:07",
+		"766780": "2024/9/14 12:18:12",
+		"827894": "2020/6/14 1:57:39",
+		"771925": "2024/10/20 22:44:07",
+		"739426": "2021/10/1 16:38:55",
+		"766446": "2024/8/22 22:48:12",
+		"768768": "2024/10/13 18:38:45",
+		"611130": "2019/12/27 17:37:25",
+		"731314": "2020/9/18 5:21:27",
+		"827958": "2020/6/19 5:40:21",
+		"739416": "2021/9/23 8:00:49",
+		"768718": "2024/9/21 21:03:33",
+		"770430": "2025/2/26 21:17:08",
+		"611164": "2019/12/30 19:55:03",
+		"830724": "2020/7/1 3:25:15",
+		"063115": "2022/5/24 8:42:47",
+		"769292": "2024/11/27 23:19:55",
+		"772231": "2025/2/28 22:47:58",
+		"030869": "2022/7/31 0:00:00",
+		"038043": "2022/7/31 0:00:00",
+		"769354": "2024/12/25 9:10:26",
+		"770807": "2024/9/22 18:16:26",
+		"058581": "2022/5/24 8:41:57",
+		"034776": "2021/1/22 19:24:22",
+		"772303": "2025/4/13 23:20:17",
+		"039106": "2022/5/24 16:10:21",
+		"039577": "2022/5/24 15:35:50",
+		"059041": "2022/5/24 17:03:28",
+		"869275": "2024/10/1 17:05:35",
+		"825374": "2020/5/7 12:40:32",
+		"773317": "2025/4/23 23:07:45",
+		"769350": "2024/12/22 23:53:27",
+		"038577": "2022/5/24 8:37:49",
+		"869182": "2024/11/10 19:00:05",
+		"769893": "2024/9/9 16:21:46",
+		"026546": "2020/5/14 18:44:46",
+		"127076": "2020/5/9 21:43:15",
+		"773315": "2025/4/22 22:25:53",
+		"022164": "2022/5/24 8:57:17",
+		"034998": "2021/3/1 18:54:59",
+		"731200": "2020/8/12 12:56:47",
+		"766774": "2024/9/14 11:59:34",
+		"038436": "2022/5/24 17:33:38",
+		"771949": "2024/10/24 22:54:55",
+		"769322": "2024/12/14 20:29:46",
+		"122610": "2020/4/8 20:11:32",
+		"182683": "2018/8/12 15:29:27",
+		"060560": "2022/7/31 0:00:00",
+		"035006": "2021/3/2 17:13:58",
+		"038717": "2022/5/24 15:48:58",
+		"772093": "2024/12/21 21:18:53",
+		"039215": "2022/5/24 8:35:19",
+		"725894": "2020/5/20 22:42:34",
+		"772165": "2025/2/8 21:48:21",
+		"130920": "2020/7/27 20:55:07",
+		"738938": "2021/8/9 16:30:14",
+		"039274": "2022/5/24 17:15:49",
+		"831678": "2020/7/29 20:09:31",
+		"770506": "2025/4/9 23:12:01",
+		"039685": "2022/5/24 13:38:06",
+		"768801": "2024/11/12 19:19:09",
+		"766692": "2024/9/5 14:51:53",
+		"769370": "2025/1/3 23:05:44",
+		"822230": "2020/5/24 20:51:11",
+		"831664": "2020/7/26 19:48:01",
+		"766478": "2024/9/1 17:30:22",
+		"769061": "2024/10/30 23:03:43",
+		"770478": "2025/4/11 23:00:27",
+		"772179": "2025/2/23 22:55:50",
+		"067021": "2022/5/24 10:11:03",
+		"769899": "2024/9/9 16:23:20",
+		"731340": "2020/9/24 20:06:40",
+		"060567": "2022/7/31 0:00:00",
+		"210864": "2019/12/24 19:51:05",
+		"038080": "2022/5/24 16:29:28",
+		"731304": "2020/9/16 13:10:11",
+		"063099": "2022/5/24 11:01:38",
+		"770757": "2024/9/14 18:32:09",
+		"770713": "2024/9/10 16:44:22",
+		"766772": "2024/9/12 9:52:08",
+		"731182": "2020/8/8 16:58:28",
+		"027490": "2020/6/3 18:25:42",
+		"037438": "2021/5/5 17:21:20",
+		"770470": "2025/3/24 23:44:08",
+		"772261": "2025/3/27 23:38:50",
+		"830632": "2020/6/23 17:40:55",
+		"738924": "2021/8/8 1:21:56",
+		"054413": "2022/7/31 0:00:00",
+		"772039": "2025/1/3 23:07:04",
+		"766362": "2024/5/29 18:10:56",
+		"830654": "2020/6/24 11:20:06",
+		"766736": "2024/9/10 16:43:55",
+		"737762": "2021/5/25 19:09:27",
+		"769059": "2024/11/9 23:29:51",
+		"769250": "2024/10/31 20:36:56",
+		"830768": "2020/7/5 23:11:02",
+		"731160": "2020/7/26 22:47:56",
+		"065137": "2022/5/24 9:08:57",
+		"769845": "2024/8/31 19:13:07",
+		"047444": "2022/5/24 18:36:06",
+		"728010": "2020/6/16 21:24:54",
+		"770705": "2024/10/13 18:36:04",
+		"023986": "2020/2/18 20:17:00",
+		"128838": "2020/5/28 19:50:45",
+		"772155": "2025/2/2 15:49:12",
+		"728148": "2020/5/26 18:10:37",
+		"769340": "2024/12/17 23:45:02",
+		"031488": "2022/5/24 14:44:25",
+		"066041": "2022/5/24 18:29:04",
+		"759252": "2024/10/31 21:03:18",
+		"822254": "2020/5/27 10:58:35",
+		"838554": "2021/9/2 22:45:07",
+		"843216": "2022/3/19 23:35:18",
+		"044652": "2022/5/10 9:35:23",
+		"038763": "2022/5/24 17:10:00",
+		"772189": "2025/2/28 22:48:26",
+		"770480": "2025/3/28 22:13:30",
+		"768726": "2024/9/26 15:38:24",
+		"768722": "2024/9/22 18:17:39",
+		"429362": "2020/7/9 1:18:52",
+		"772271": "2025/4/1 21:20:46",
+		"830688": "2020/6/27 22:30:00",
+		"772005": "2024/10/31 21:03:06",
+		"772053": "2025/1/9 22:09:30",
+		"045398": "2022/7/31 0:00:00",
+		"733540": "2020/12/28 15:00:48",
+		"044823": "2022/5/24 8:03:19",
+		"055507": "2022/5/24 15:31:37",
+		"247202": "2022/6/23 12:20:45",
+		"772297": "2025/4/12 22:36:26",
+		"066218": "2022/7/31 0:00:00",
+		"731232": "2020/8/26 6:30:09",
+		"137532": "2021/5/5 21:37:22",
+		"731230": "2020/8/25 0:25:04",
+		"000936": "2022/7/31 0:00:00",
+		"770759": "2024/9/14 18:31:44",
+		"058582": "2022/7/31 0:00:00",
+		"027536": "2020/6/14 17:40:54",
+		"059558": "2022/5/24 17:37:29",
+		"768788": "2024/10/15 20:05:10",
+		"770781": "2024/9/17 16:42:17",
+		"769903": "2024/9/9 16:24:36",
+		"053943": "2022/7/31 0:00:00",
+		"245494": "2022/6/8 2:15:04",
+		"827964": "2020/6/19 11:30:02",
+		"031519": "2022/5/24 17:38:30",
+		"038248": "2022/5/24 8:54:13",
+		"766460": "2024/8/28 19:57:27",
+		"866094": "2024/10/4 20:34:42",
+		"146168": "2022/6/3 22:51:48",
+		//"0006577":"2022/7/31 0:00:00",
+		"038720": "2022/5/24 8:10:06",
+		"831606": "2020/8/1 19:52:54",
+		"770406": "2025/2/2 15:48:46",
+		"022908": "2022/5/24 9:33:38",
+		"768716": "2024/9/21 21:01:53",
+		"210868": "2019/12/25 18:54:19",
+		"769372": "2025/1/3 23:06:18",
+		"769192": "2024/10/18 21:35:37",
+		"770659": "2024/9/22 16:56:23",
+		"034770": "2021/1/22 19:17:36",
+		"708392": "2019/8/7 8:40:23",
+		"767747": "2024/10/29 23:01:50",
+		"055256": "2022/5/24 9:12:09",
+		"066666": "2022/5/24 11:01:08",
+		"710610": "2019/10/14 8:29:24",
+		"769867": "2024/9/6 14:03:28",
+		"047400": "2022/5/24 10:09:57",
+		"760689": "2024/10/3 9:35:34",
+		"039635": "2022/5/24 8:13:07",
+		"769445": "2024/4/30 14:53:33",
+		"768805": "2024/11/14 20:03:16",
+		"767737": "2024/11/3 19:33:34",
+		"725864": "2020/5/18 23:55:50",
+		"065780": "2022/5/24 17:27:37",
+		"210846": "2019/12/20 20:25:14",
+		"026600": "2020/5/19 18:42:27",
+		"228758": "2020/6/12 14:20:07",
+		"728066": "2020/6/23 21:45:13",
+		"770418": "2025/2/15 23:45:46",
+		"057067": "2022/5/24 18:51:11",
+		"061649": "2022/5/24 18:47:02",
+		"425992": "2020/5/24 10:55:52",
+		"843212": "2022/3/16 11:31:45",
+		"772279": "2025/4/5 22:53:21",
+		"746406": "2022/6/21 17:10:28",
+		"066631": "2022/5/24 10:36:45",
+		"130460": "2020/8/5 19:37:12",
+		"772051": "2025/1/7 21:52:19",
+		"770482": "2025/3/30 21:33:50",
+		"770420": "2025/2/20 22:45:53",
+		"830844": "2020/7/23 21:02:35",
+		"825352": "2020/5/5 12:18:30",
+		"044642": "2022/5/4 0:31:20",
+		"728198": "2020/6/2 1:50:15",
+		"061767": "2022/5/24 11:23:22",
+		"731244": "2020/8/31 12:40:02",
+		"044422": "2022/5/24 16:13:13",
+		"770677": "2024/9/28 15:40:19",
+		"770436": "2025/3/10 22:30:13",
+		"923066": "2020/2/11 5:56:32",
+		"039297": "2022/5/24 10:59:30",
+		"769312": "2024/12/10 13:33:57",
+		"034724": "2021/1/18 18:38:18",
+		"769843": "2024/8/29 23:59:44",
+		"731242": "2020/8/31 8:12:07",
+		"731290": "2020/9/11 10:25:25",
+		"043964": "2022/4/13 13:05:26",
+		"838216": "2021/6/4 16:00:53",
+		"769837": "2024/8/30 18:50:13",
+		"772243": "2025/3/18 22:59:42",
+		"731090": "2020/7/13 12:52:36",
+		"058206": "2022/5/24 9:10:55",
+		"066239": "2022/5/24 16:16:45",
+		"027550": "2020/6/19 17:27:40",
+		"731066": "2020/7/10 2:13:25",
+		"061607": "2022/5/24 15:56:55",
+		"766432": "2024/6/23 15:53:20",
+		"128818": "2020/5/23 20:55:59",
+		"043892": "2022/3/30 7:38:53",
+		"622026": "2020/5/11 23:36:27",
+		"061268": "2022/5/24 8:10:03",
+		"026454": "2020/5/5 17:40:53",
+		"769835": "2024/8/29 19:41:14",
+		"039752": "2022/5/24 8:34:28",
+		"770735": "2024/9/12 18:52:48",
+		"771941": "2024/10/23 22:52:12",
+		"825316": "2020/4/28 14:30:21",
+		"846970": "2022/7/27 20:21:54",
+		"128450": "2020/6/1 22:05:57",
+		"865934": "2024/10/1 17:03:00",
+		"838532": "2021/8/12 22:09:10",
+		"728048": "2020/6/21 14:30:21",
+		"772245": "2025/3/18 23:00:27",
+		"060201": "2022/5/24 17:27:44",
+		"124284": "2020/5/18 20:51:46",
+		"043343": "2022/7/31 0:00:00",
+		"060805": "2022/5/24 9:08:19",
+		"770701": "2024/10/12 18:10:20",
+		"767731": "2024/10/30 23:03:29",
+		"770456": "2025/3/8 22:56:24",
+		"827926": "2020/6/16 8:28:05",
+		"772229": "2025/3/10 22:30:27",
+		"039028": "2022/5/24 16:15:27",
+		"049637": "2022/5/24 15:48:20",
+		"766452": "2024/8/23 16:31:47",
+		"037470": "2021/5/23 16:38:20",
+		"865930": "2024/9/30 20:50:41",
+		"606470": "2019/12/16 23:54:22",
+		"830714": "2020/6/30 6:10:38",
+		"869184": "2024/11/10 18:27:54",
+		"038139": "2022/5/24 17:43:39",
+		"766720": "2024/9/8 16:49:30",
+		"838584": "2021/10/24 23:05:47",
+		"066628": "2022/7/31 0:00:00",
+		"770440": "2025/3/8 22:58:55",
+		"766420": "2024/6/18 23:31:23",
+		"732436": "2020/10/8 6:26:43",
+		"769300": "2024/12/3 21:50:25",
+		"838512": "2021/8/5 21:15:09",
+		"770709": "2024/9/10 16:43:00",
+		"769264": "2024/11/12 19:18:52",
+		"210850": "2019/12/21 20:06:20",
+		"768799": "2024/11/12 19:17:49",
+		"772227": "2025/3/10 22:30:01",
+		"772145": "2025/1/28 15:46:48",
+		"439088": "2021/10/2 22:30:06",
+		"770404": "2025/1/29 15:45:16",
+		"766448": "2024/8/23 16:35:35",
+		"769220": "2024/10/21 22:47:51",
+		"770799": "2024/9/20 18:45:36",
+		"026564": "2020/5/15 18:38:58",
+		"066034": "2022/5/24 15:47:48",
+		"838576": "2021/9/24 23:05:14",
+		"770725": "2024/9/11 9:50:36",
+		"030848": "2022/5/24 16:01:43",
+		"768752": "2024/10/12 18:09:02",
+		"769304": "2024/12/8 14:27:28",
+		"731206": "2020/8/14 23:43:45",
+		"027556": "2020/6/23 17:56:49",
+		"830898": "2020/7/17 4:45:37",
+		"731282": "2020/9/8 11:45:53",
+		"768754": "2024/10/12 18:11:44",
+		"039286": "2022/5/24 13:30:10",
+		"063531": "2022/5/24 18:12:23",
+		"772017": "2024/11/28 22:18:24",
+		"772255": "2025/3/26 23:45:02",
+		"759334": "2023/12/5 20:32:50",
+		"831694": "2020/7/31 18:50:17",
+		"034886": "2021/2/16 17:09:24",
+		"733536": "2020/12/24 19:14:26",
+		"060076": "2022/5/24 9:09:44",
+		"772283": "2025/4/8 20:41:59",
+		"768714": "2024/9/20 18:44:13",
+		"043990": "2022/4/19 7:45:30",
+		"725892": "2020/5/20 22:41:33",
+		"065757": "2022/7/31 0:00:00",
+		"236524": "2021/5/1 16:20:20",
+		"769226": "2024/10/22 22:50:46",
+		"772023": "2024/11/29 20:56:54",
+		"772071": "2024/12/14 19:27:22",
+		"772163": "2025/2/5 20:42:45",
+		"049508": "2022/5/24 16:50:56",
+		"211336": "2020/1/9 19:05:01",
+		"731074": "2020/7/11 14:35:11",
+		"065986": "2022/5/24 9:37:07",
+		"066320": "2022/5/24 10:49:59",
+		"431908": "2020/8/4 5:06:29",
+		"772129": "2025/1/21 20:22:16",
+		"745778": "2022/6/19 10:00:03",
+		"047458": "2022/7/31 0:00:00",
+		"038364": "2022/5/24 7:39:39",
+		"770699": "2024/10/11 17:56:19",
+		"766790": "2024/9/15 15:41:00",
+		"770512": "2025/4/13 23:21:28",
+		"831704": "2020/9/3 23:51:51",
+		"227002": "2020/5/15 16:30:19",
+		"732480": "2020/12/3 7:25:07",
+		"766488": "2024/9/4 16:49:05",
+		"772135": "2025/1/24 20:26:08",
+		"770502": "2025/4/9 23:10:33",
+		"738988": "2021/9/8 20:34:36",
+		"766706": "2024/9/7 19:17:55",
+		"771947": "2024/10/24 22:54:32",
+		"825314": "2020/4/27 18:30:23",
+		"732416": "2020/9/30 12:26:04",
+		"766788": "2024/9/15 15:34:21",
+		"055968": "2022/7/31 0:00:00",
+		"769366": "2024/12/29 19:11:19",
+		"127090": "2020/5/12 23:12:55",
+		"731140": "2020/7/22 21:30:09",
+		"057043": "2022/5/24 9:48:10",
+		"770484": "2025/3/31 20:36:27",
+		"923130": "2020/2/17 20:05:07",
+		"768734": "2024/9/29 19:50:49",
+		"245476": "2022/5/30 22:10:28",
+		"768728": "2024/9/27 9:42:13",
+		"736462": "2021/4/12 15:30:42",
+		"827904": "2020/6/14 15:50:21",
+		"731246": "2020/8/31 15:45:14",
+		"731276": "2020/9/7 12:50:33",
+		"771959": "2024/10/27 22:58:55",
+		"063501": "2022/5/24 9:31:37",
+		"827944": "2020/6/18 2:10:05",
+		"061829": "2022/5/24 8:04:49",
+		"769839": "2024/8/30 18:53:58",
+		"053312": "2023/1/2 18:51:47",
+		"772045": "2025/1/5 23:55:26",
+		"728298": "2020/6/13 5:50:47",
+		"772247": "2025/3/18 23:01:01",
+		"725770": "2020/5/3 18:38:47",
+		"766124": "2024/10/17 21:03:13",
+		"027570": "2020/7/15 7:22:57",
+		"182133": "2018/7/26 23:12:06",
+		"772061": "2024/12/8 14:26:18",
+		"144430": "2022/3/31 21:01:05",
+		"771987": "2024/11/18 20:51:40",
+		"049168": "2022/5/24 17:36:45",
+		"769905": "2024/9/10 16:34:52",
+		"731102": "2020/7/16 11:05:39",
+		"038795": "2022/5/24 17:09:13",
+		"827874": "2020/6/12 13:40:33",
+		"045287": "2022/5/24 18:13:27",
+		"054086": "2022/5/24 15:34:17",
+		"728162": "2020/5/28 14:15:52",
+		"830878": "2020/7/15 18:10:34",
+		"766322": "2024/5/17 18:09:48",
+		"765570": "2024/11/12 19:16:31",
+		"772143": "2025/1/28 15:45:49",
+		"770522": "2025/4/17 10:19:22",
+		"772167": "2025/2/9 21:01:29",
+		"737914": "2021/6/14 16:40:48",
+		"766724": "2024/9/9 16:22:55",
+		"710624": "2019/10/19 8:33:53",
+		"769573": "2024/6/18 16:13:25",
+		"038566": "2022/5/24 16:45:48",
+		"728046": "2020/6/21 12:05:56",
+		"126806": "2020/4/25 21:28:40",
+		"822272": "2020/5/30 14:19:09",
+		"228766": "2020/6/14 4:25:58",
+		"054032": "2022/5/24 15:43:35",
+		"768744": "2024/10/11 17:57:16",
+		"769278": "2024/11/21 23:50:38",
+		"739422": "2021/9/27 20:37:07",
+		"224520": "2020/2/13 14:20:44",
+		"728042": "2020/6/21 1:40:48",
+		"035072": "2021/3/6 16:57:40",
+		"772037": "2025/1/2 23:40:25",
+		"059551": "2022/5/24 16:56:33",
+		"728026": "2020/6/19 8:45:12",
+		"846974": "2022/7/27 20:25:53",
+		"772035": "2025/1/1 22:25:13",
+		"770532": "2025/4/20 23:35:49",
+		"766770": "2024/9/12 9:51:38",
+		"058149": "2022/7/31 0:00:00",
+		"037474": "2021/5/24 16:23:43",
+		"772219": "2025/3/8 22:55:20",
+		"770438": "2025/2/28 22:47:47",
+		"725832": "2020/5/15 9:30:15",
+		"732474": "2020/11/30 6:15:15",
+		"043435": "2022/5/24 16:08:26",
+		"827906": "2020/6/14 20:10:51",
+		"058177": "2022/7/31 0:00:00",
+		"731316": "2020/9/18 9:37:30",
+		"830738": "2020/7/2 11:08:18",
+		"731320": "2020/9/19 12:20:36",
+		"830836": "2020/7/22 20:48:10",
+		"737942": "2021/6/20 3:45:42",
+		"770711": "2024/9/10 16:43:28",
+		"770444": "2025/3/3 21:05:42",
+		"769326": "2024/12/14 19:32:17",
+		"731328": "2020/9/22 2:30:02",
+		"770793": "2024/9/18 15:59:15",
+		"066627": "2022/5/24 17:19:08",
+		"027574": "2020/9/8 21:20:55",
+		"731026": "2020/7/2 23:48:23",
+		"770803": "2024/9/20 18:46:12",
+		"733514": "2020/12/7 1:30:59",
+		"769194": "2024/10/18 22:33:27",
+		"731342": "2020/9/24 20:28:18",
+		"871889": "2024/11/10 19:02:42",
+		"725810": "2020/5/13 11:54:55",
+		"061664": "2022/5/24 9:47:32",
+		"825320": "2020/4/28 17:14:53",
+		"768696": "2024/9/16 15:42:21",
+		"769382": "2025/1/11 21:06:04",
+		"769234": "2024/10/25 22:55:33",
+		"772031": "2024/12/3 21:49:37",
+		"771923": "2024/10/20 22:43:46",
+		"731266": "2020/9/4 16:42:53",
+		"039404": "2022/5/24 15:16:47",
+		"731188": "2020/8/10 10:33:32",
+		"057790": "2022/5/24 16:48:44",
+		"769541": "2024/6/7 17:36:32",
+		"772259": "2025/3/27 23:43:16",
+		"027440": "2020/5/25 17:38:19",
+		"772217": "2025/3/8 22:56:54",
+		"731128": "2020/7/19 23:35:25",
+		"056409": "2022/5/24 9:38:12",
+		"772281": "2025/4/7 22:14:07",
+		"211324": "2020/1/5 19:09:04",
+		"066058": "2022/7/31 0:00:00",
+		"044970": "2022/5/24 10:58:06",
+		"766782": "2024/9/14 15:31:44",
+		"039280": "2022/5/24 11:04:34",
+		"732466": "2020/11/28 7:35:01",
+		"022965": "2022/5/24 8:25:48",
+		"771931": "2024/10/21 22:46:21",
+		"731308": "2020/9/17 6:35:36",
+		"022482": "2022/5/24 11:19:43",
+		"830676": "2020/6/25 15:39:25",
+		"030852": "2022/5/24 16:34:33",
+		"026470": "2020/5/8 19:15:06",
+		"731292": "2020/9/12 10:50:29",
+		"037306": "2021/4/3 17:24:35",
+		"838506": "2021/8/5 21:15:03",
+		"065092": "2022/5/24 10:27:40",
+		"053630": "2023/2/24 15:00:55",
+		"027510": "2020/6/7 18:40:26",
+		"766766": "2024/9/12 9:47:13",
+		"827924": "2020/6/16 2:03:51",
+		"827886": "2020/6/13 17:30:23",
+		"044916": "2022/5/24 8:48:14",
+		"066184": "2022/5/24 14:32:33",
+		"062371": "2022/5/24 15:36:59",
+		"057120": "2022/5/24 19:00:28",
+		"053524": "2023/1/29 16:58:12",
+		"768694": "2024/9/15 16:12:23",
+		"769901": "2024/9/9 16:23:46",
+		"869287": "2024/10/8 17:11:30",
+		"770695": "2024/10/10 19:53:43",
+		"738978": "2021/9/6 22:12:53",
+		"031511": "2022/5/24 16:39:03",
+		"846294": "2022/5/29 21:24:49",
+		"768708": "2024/9/17 19:00:55",
+		"769853": "2024/9/2 14:40:31",
+		"768698": "2024/9/16 15:46:38",
+		"770494": "2025/4/4 21:25:26",
+		"773311": "2025/4/21 22:08:38",
+		"065573": "2022/5/24 18:02:58",
+		"770717": "2024/9/10 16:47:39",
+		"060045": "2022/7/31 0:00:00",
+		"846252": "2022/6/3 21:22:03",
+		"725876": "2020/5/19 16:15:21",
+		"026468": "2020/5/7 17:32:55",
+		"769453": "2024/5/4 9:05:07",
+		"770396": "2025/1/22 23:22:39",
+		"065500": "2022/5/24 8:53:28",
+		"611128": "2019/12/27 17:39:36",
+		"062448": "2022/5/24 9:21:34",
+		"066353": "2022/5/24 9:31:54",
+		"731116": "2020/7/18 1:05:10",
+		"766394": "2024/6/9 21:12:54",
+		"770685": "2024/10/2 8:34:01",
+		"737910": "2021/6/14 6:30:43",
+		"065639": "2022/5/24 7:25:52",
+		"063012": "2022/5/24 8:03:03",
+		"059447": "2022/5/24 9:36:53",
+		"770446": "2025/3/10 22:28:10",
+		"027484": "2020/6/2 19:13:36",
+		"122494": "2020/3/9 20:22:26",
+		"769202": "2024/10/18 22:36:43",
+		"038251": "2022/5/24 18:48:49",
+		"906644": "2020/1/21 19:20:52",
+		"611002": "2019/12/20 15:19:18",
+		"866118": "2024/10/9 16:49:57",
+		"770785": "2024/9/17 18:57:27",
+		"054959": "2022/5/24 8:50:32",
+		"771809": "2024/11/19 0:14:09",
+		"66694":  "2024/9/5 14:55:20",
+		"770428": "2025/2/25 21:58:24",
+		"128498": "2020/6/15 12:01:53",
+		"766760": "2024/9/11 9:50:48",
+		"830778": "2020/7/7 2:00:36",
+		"725860": "2020/5/18 10:30:53",
+		"036888": "2021/3/10 17:48:34",
+		"063331": "2022/5/24 8:30:34",
+		"027558": "2020/6/24 18:45:54",
+		"770743": "2024/9/13 12:57:26",
+		"027436": "2020/5/24 19:24:12",
+		"772029": "2024/12/1 21:42:50",
+		"838536": "2021/8/16 20:45:18",
+		"769575": "2024/6/18 16:15:34",
+		"769877": "2024/9/5 17:10:18",
+		"772273": "2025/4/1 21:21:49",
+		"766456": "2024/8/26 20:10:53",
+		"769240": "2024/10/28 23:00:17",
+		"728024": "2020/6/19 2:10:51",
+		"728220": "2020/6/4 23:44:51",
+		"825392": "2020/5/10 23:10:04",
+		"825334": "2020/5/3 13:52:13",
+		"770681": "2024/9/28 15:42:40",
+		"043419": "2022/5/24 16:29:37",
+		"182641": "2018/8/5 1:01:05",
+		"127114": "2020/5/14 20:20:46",
+		"770442": "2025/3/3 21:06:19",
+		"728268": "2020/6/9 8:21:44",
+		"772021": "2024/11/28 22:23:42",
+		"067181": "2022/5/24 8:39:25",
+		"728250": "2020/6/8 4:40:51",
+		"027482": "2020/6/2 19:11:14",
+		"128888": "2020/6/26 19:23:44",
+		"034868": "2021/2/12 17:08:41",
+		"869269": "2024/9/16 14:43:14",
+		"822266": "2020/5/29 19:39:36",
+		"038011": "2022/5/24 9:04:27",
+		"236238": "2021/1/31 3:40:38",
+		"771983": "2024/11/15 20:24:36",
+		"038604": "2022/5/24 9:28:52",
+		"039238": "2022/5/24 10:12:49",
+		"065397": "2022/5/24 15:31:23",
+		"865932": "2024/9/30 20:56:42",
+		"846234": "2022/6/10 22:59:10",
+		"830754": "2020/7/3 22:30:56",
+		"030880": "2022/5/24 8:19:56",
+		"771995": "2024/11/18 20:55:15",
+		"765572": "2024/11/13 21:59:26",
+		"770534": "2025/4/21 22:08:04",
+		"065105": "2022/5/24 17:15:17",
+		"827902": "2020/6/14 14:30:56",
+		"770693": "2024/10/9 19:43:10",
+		"049216": "2022/5/24 16:07:38",
+		"060059": "2022/5/24 9:49:43",
+		"769881": "2024/9/8 16:42:16",
+		"772147": "2025/2/7 21:52:13",
+		"770679": "2024/9/28 15:41:31",
+		"770801": "2024/9/20 21:20:09",
+		"770398": "2025/1/23 23:31:10",
+		"733526": "2020/12/10 3:40:02",
+		"770528": "2025/4/19 15:10:01",
+		"770474": "2025/3/26 23:45:52",
+		"769310": "2024/12/10 13:04:32",
+		"766410": "2024/6/14 10:36:23",
+		"769423": "2024/4/25 21:51:44",
+		"771951": "2024/10/26 22:57:22",
+		"036860": "2021/3/7 19:08:19",
+		"772213": "2025/3/3 21:06:04",
+		"026424": "2020/5/3 20:47:46",
+		"027538": "2020/6/15 17:09:44",
+		"771993": "2024/11/2 18:27:29",
+		"769603": "2024/8/25 19:49:27",
+		"768710": "2024/9/18 15:57:28",
+		"050171": "2022/5/24 7:52:00",
+		"770208": "2025/1/16 23:40:21",
+		"769897": "2024/9/9 16:22:30",
+		"731180": "2020/8/8 2:33:44",
+		"838514": "2021/8/5 21:15:42",
+		"768770": "2024/10/13 18:40:39",
+		"065106": "2022/5/24 10:18:53",
+		"866096": "2024/10/4 20:32:49",
+		"769833": "2024/8/29 19:37:02",
+		"831736": "2020/10/18 23:12:40",
+		"769851": "2024/9/2 18:09:57",
+		"728006": "2020/6/14 23:40:48",
+		"830602": "2020/6/21 0:35:12",
+		"731196": "2020/8/11 19:48:50",
+		"827990": "2020/6/20 14:48:51",
+		"728060": "2020/6/22 23:35:21",
+		"731104": "2020/7/16 12:10:41",
+		"768784": "2024/10/14 16:11:36",
+		"871893": "2024/11/19 19:13:26",
+		"035058": "2021/3/5 18:31:09",
+		"869271": "2024/9/30 21:06:04",
+		"728286": "2020/6/10 23:10:53",
+		"138270": "2021/7/6 20:24:56",
+		"772267": "2025/3/30 21:34:48",
+		"769297": "2024/10/17 20:57:26",
+		"771977": "2024/11/18 20:52:51",
+		"728138": "2020/5/25 20:26:35",
+		"061725": "2022/5/24 8:52:59",
+		"770466": "2025/3/3 21:05:54",
+		"838226": "2021/6/13 12:35:31",
+		"772285": "2025/4/8 20:43:23",
+		"772171": "2025/2/12 23:10:25",
+		"769376": "2025/1/8 20:51:17",
+		"066132": "2022/7/31 0:00:00",
+		"065587": "2022/5/24 15:27:38",
+		"766718": "2024/9/8 16:49:07",
+		"770498": "2025/4/6 18:52:37",
+		"731224": "2020/8/22 3:09:54",
+		"769855": "2024/9/2 14:43:23",
+		"766764": "2024/9/11 9:50:20",
+		"769599": "2024/7/2 10:30:21",
+		"772265": "2025/3/30 21:33:07",
+		"210852": "2019/12/22 19:18:25",
+		"865938": "2024/10/3 16:44:48",
+		"047364": "2022/5/24 10:36:44",
+		"831760": "2020/11/19 20:09:08",
+		"128834": "2020/5/27 20:22:54",
+		"065107": "2022/5/24 15:49:15",
+		"827830": "2020/6/8 10:44:43",
+		"027412": "2020/5/21 18:12:34",
+		"057854": "2022/5/24 17:33:24",
+		"766416": "2024/6/17 17:49:42",
+		"66700":  "2024/9/5 14:59:41",
+		"732450": "2020/10/13 8:17:19",
+		"036882": "2021/3/10 17:46:20",
+		"772003": "2024/11/20 14:21:03",
+		"122636": "2020/4/13 20:44:26",
+		"043379": "2022/5/24 15:16:45",
+		"728228": "2020/6/5 13:45:43",
+		"731054": "2020/7/7 4:50:35",
+		"771985": "2024/11/18 20:51:12",
+		"728018": "2020/6/17 14:15:42",
+		"769198": "2024/10/18 22:34:12",
+		"738912": "2021/8/5 13:35:26",
+		"769248": "2024/10/31 20:36:16",
+		"772291": "2025/4/11 22:59:28",
+		"766768": "2024/9/12 9:48:28",
+		"770454": "2025/2/28 22:48:11",
+		"772069": "2024/12/11 23:32:51",
+		"061832": "2022/7/31 0:00:00",
+		"728136": "2020/5/25 3:05:56",
+		"065619": "2022/5/24 18:04:33",
+		"210862": "2019/12/24 19:46:27",
+		"731110": "2020/7/16 22:30:12",
+		"772237": "2025/3/12 23:10:48",
+		"710696": "2019/10/7 7:12:34",
+		"769863": "2024/9/4 16:50:43",
+		"768772": "2024/10/13 18:42:59",
+		"771963": "2024/10/28 23:00:54",
+		"769344": "2024/12/21 21:18:14",
+		"769244": "2024/10/28 23:01:15",
+		"769589": "2024/6/23 15:48:01",
+		"725854": "2020/5/17 22:05:03",
+		"770769": "2024/9/16 15:43:59",
+		"822202": "2020/5/12 13:12:58",
+		"026350": "2020/4/27 19:48:22",
+		"766368": "2024/6/1 14:47:51",
+		"728290": "2020/6/11 15:45:39",
+		"053957": "2022/5/24 9:11:11",
+		"737902": "2021/6/12 10:45:04",
+		"036928": "2021/3/13 17:23:08",
+		"022934": "2022/5/24 16:42:32",
+		"039677": "2022/5/24 17:24:19",
+		"825378": "2020/5/7 22:01:14",
+		"027524": "2020/6/11 17:30:35",
+		"731310": "2020/9/17 23:40:53",
+		"866108": "2024/10/7 18:48:42",
+		"725878": "2020/5/19 23:04:59",
+		"869273": "2024/9/30 21:04:36",
+		"769859": "2024/9/3 18:25:53",
+		"869281": "2024/10/3 16:41:59",
+		"043948": "2022/4/9 12:50:43",
+		"409182": "2020/1/3 11:01:19",
+		"831636": "2020/8/6 20:19:15",
+		"027402": "2020/5/20 19:46:17",
+		"772013": "2024/11/25 21:29:02",
+		"027590": "2020/11/5 9:55:35",
+		"039649": "2022/5/24 10:44:49",
+		"770516": "2025/4/15 23:20:01",
+		"830842": "2020/7/23 21:01:43",
+		"039296": "2022/5/24 15:29:33",
+		"030694": "2022/5/24 8:34:23",
+		"022972": "2022/5/24 16:27:20",
+		"426024": "2020/5/30 10:09:28",
+		"766490": "2024/9/3 16:50:34",
+		"771967": "2024/10/30 23:02:05",
+		"827806": "2020/6/5 17:35:43",
+		"731228": "2020/8/23 22:42:54",
+		"023992": "2020/2/19 20:16:57",
+		"731260": "2020/9/3 5:50:49",
+		"770458": "2025/3/29 20:22:51",
+		"731250": "2020/9/1 0:12:08",
+		"844562": "2022/4/28 23:04:37",
+		"766332": "2024/5/20 21:15:21",
+		"725900": "2020/5/22 9:00:14",
+		"830604": "2020/6/21 8:06:44",
+		"772075": "2024/12/14 19:33:03",
+		"827804": "2020/6/5 16:10:02",
+		"731238": "2020/8/30 4:25:48",
+		"770514": "2025/4/14 22:20:08",
+		"745764": "2022/6/9 4:00:17",
+		"731118": "2020/7/18 2:51:58",
+		"027498": "2020/6/5 17:48:00",
+		"768706": "2024/9/17 16:48:46",
+		"831686": "2020/7/30 17:21:13",
+		"771933": "2024/10/22 22:48:23",
+		"831722": "2020/9/24 21:17:42",
+		"731262": "2020/9/3 6:20:08",
+		"136086": "2021/4/12 18:14:34",
+		"846928": "2022/7/19 20:00:26",
+		"769895": "2024/9/9 16:22:07",
+		"737758": "2021/5/24 7:03:00",
+		"770661": "2024/9/23 16:53:51",
+		"772131": "2025/1/22 23:23:32",
+		"066316": "2022/5/24 10:45:25",
+		"766778": "2024/9/14 18:33:32",
+		"772275": "2025/4/4 21:24:12",
+		"731270": "2020/9/5 11:30:03",
+		"770524": "2025/4/19 0:04:52",
+		"766406": "2024/6/12 15:04:55",
+		"772209": "2025/3/3 21:05:29",
+		"066583": "2022/5/24 8:06:57",
+		"773313": "2025/4/22 22:24:30",
+		"871905": "2024/11/10 19:02:12",
+		"869279": "2024/10/3 16:39:30",
+		"769324": "2024/12/14 23:43:31",
+		"033734": "2020/12/28 18:54:20",
+		"770468": "2025/3/23 23:18:32",
+		"838248": "2021/6/30 0:40:29",
+		"769228": "2024/10/22 22:51:52",
+		"038574": "2022/5/24 10:59:32",
+		"769063": "2024/11/7 20:11:17",
+		"772081": "2024/12/17 23:45:07",
+		"065859": "2022/5/24 15:47:11",
+		"738948": "2021/8/13 1:12:41",
+		"769887": "2024/9/8 16:49:51",
+		"769306": "2024/12/8 14:28:34",
+		"053752": "2022/5/24 18:35:10",
+		"054044": "2022/5/24 18:58:34",
+		"768766": "2024/10/13 18:34:35",
+		"738954": "2021/8/14 12:50:27",
+		"770504": "2025/4/9 23:11:18",
+		"771989": "2024/11/19 0:14:47",
+		"769218": "2024/10/21 22:47:38",
+		"725886": "2020/5/20 12:50:24",
+		"772223": "2025/3/8 22:57:40",
+		"831680": "2020/7/29 20:10:12",
+		"822236": "2020/5/25 17:11:27",
+		"770452": "2025/3/8 22:54:55",
+		"771909": "2024/10/18 22:32:41",
+		"066280": "2022/5/24 16:56:08",
+		"772269": "2025/3/30 21:35:39",
+		"061685": "2022/7/31 0:00:00",
+		"822268": "2020/5/29 19:45:25",
+		"769386": "2025/1/13 19:16:32",
+		"037448": "2021/5/14 17:14:47",
+		"738974": "2021/9/2 5:30:41",
+		"772127": "2025/1/21 20:20:50",
+		"184746": "2018/11/2 17:25:21",
+		"773309": "2025/4/19 21:08:35",
+		"769829": "2024/8/28 19:52:46",
+		"731186": "2020/8/10 3:50:31",
+		"710450": "2019/9/12 8:09:41",
+		"038813": "2022/5/24 17:41:54",
+		"830624": "2020/6/22 23:00:44",
+		"211346": "2020/1/15 19:18:41",
+		"769238": "2024/10/26 22:58:00",
+		"044688": "2022/8/26 22:00:00",
+		"606468": "2019/12/16 23:45:41",
+		"822258": "2020/5/28 5:10:05",
+		"770727": "2024/9/11 9:50:18",
+		"182706": "2018/8/16 18:30:32",
+		"037100": "2021/4/2 17:25:21",
+		"769272": "2024/11/15 20:21:15",
+		"769601": "2024/8/25 19:46:54",
+		"767723": "2024/11/5 21:42:22",
+		"027448": "2020/5/26 18:35:53",
+		"026542": "2020/5/14 18:43:05",
+		"731272": "2020/9/5 15:30:30",
+		"034730": "2021/1/19 18:17:54",
+		"772015": "2024/11/27 23:17:15",
+		"736484": "2021/4/29 6:53:53",
+		"770488": "2025/4/1 20:20:05",
+		"772007": "2024/11/3 19:32:39",
+		"770460": "2025/3/10 22:29:10",
+		"127120": "2020/5/17 19:45:25",
+		"022896": "2022/5/24 18:52:15",
+		"731092": "2020/7/13 14:40:10",
+		"247210": "2022/6/30 1:20:01",
+		"047453": "2022/5/24 10:54:37",
+		"770765": "2024/9/15 15:36:50",
+		"065158": "2022/7/31 0:00:00",
+		"058964": "2022/5/24 18:59:53",
+		"432060": "2020/12/8 1:41:58",
+		"062254": "2022/5/24 9:05:10",
+		"838540": "2021/8/25 9:50:03",
+		"770392": "2025/1/21 20:20:10",
+		"769889": "2024/9/9 16:20:50",
+		"770500": "2025/4/8 20:42:35",
+		"769567": "2024/6/15 15:06:35",
+		"770262": "2025/1/20 20:49:50",
+		"772183": "2025/2/26 21:16:00",
+		"054863": "2022/5/24 16:18:29",
+		"061749": "2022/5/24 18:33:17",
+		"768776": "2024/10/13 18:50:13",
+		"772073": "2024/12/14 19:30:38",
+		"026596": "2020/5/19 18:38:46",
+		"770400": "2025/1/23 23:32:23",
+		"053983": "2022/5/24 18:31:22",
+		"037430": "2021/5/3 17:27:12",
+		"034970": "2021/2/27 17:25:29",
+		"772225": "2025/3/8 22:58:12",
+		"869289": "2024/10/9 16:43:53",
+		"767751": "2024/11/4 18:34:24",
+		"031232": "2022/5/24 10:50:25",
+		"728204": "2020/6/2 18:20:01",
+		"769547": "2024/6/8 16:15:01",
+		"038330": "2022/5/24 15:10:41",
+		"766130": "2024/10/17 21:24:10",
+		"038788": "2022/5/24 11:01:44",
+		"827816": "2020/6/6 16:58:51",
+		"769849": "2024/9/2 17:34:28",
+		"059358": "2022/5/24 18:31:04",
+		"731198": "2020/8/12 8:21:47",
+		"728128": "2020/5/24 11:25:26",
+		"769258": "2024/11/18 20:58:00",
+		"771953": "2024/10/31 21:02:05",
+		"827980": "2020/6/20 13:19:24",
+		"838228": "2021/6/15 7:00:29",
+		"057064": "2022/5/24 18:02:07",
+		"770414": "2025/2/19 21:27:16",
+		"033431": "2022/7/31 0:00:00",
+		"059270": "2022/5/24 9:13:02",
+		"244062": "2022/3/18 12:30:35",
+		"066152": "2022/5/24 18:37:23",
+		"049808": "2022/5/24 9:00:04",
+		"769374": "2025/1/8 20:51:05",
+		"731330": "2020/9/23 11:47:28",
+		"035088": "2021/3/7 17:36:10",
+		"728244": "2020/6/7 13:00:47",
+		"772123": "2025/1/18 22:56:53",
+		"708882": "2019/8/10 15:33:02",
+		"771919": "2024/10/19 22:39:13",
+		"769378": "2025/1/9 22:09:18",
+		"062363": "2022/5/24 10:38:35",
+		"770675": "2024/9/28 15:39:00",
+		"059940": "2022/5/24 16:20:04",
+		"731068": "2020/7/10 3:07:38",
+		"432004": "2020/10/12 16:33:19",
+		"066350": "2022/5/24 9:19:10",
+		"759332": "2023/12/5 20:31:13",
+		"769380": "2025/1/9 22:09:47",
+		"059374": "2022/5/24 16:53:18",
+		"766722": "2024/9/9 16:20:23",
+		"768692": "2024/9/15 15:42:15",
+		"732464": "2020/11/20 15:00:06",
+		"770697": "2024/10/10 19:54:29",
+		"768756": "2024/10/12 18:12:46",
+		"772079": "2024/12/16 22:55:07",
+		"043954": "2022/4/12 15:48:45",
+		"066580": "2022/5/24 15:41:37",
+		"047598": "2022/5/24 18:18:21",
+		"838592": "2021/10/26 23:25:19",
+		"769857": "2024/9/3 18:24:52",
+		"843266": "2022/3/29 17:19:31",
+		"770669": "2024/9/26 10:20:06",
+		"822296": "2020/6/4 17:53:04",
+		"030762": "2022/5/24 18:35:04",
+		"796282": "2024/11/24 18:04:33",
+		"769823": "2024/8/27 18:36:37",
+		"039632": "2022/5/24 16:53:56",
+		"038093": "2022/7/31 0:00:00",
+		"728106": "2020/5/21 18:05:05",
+		"830616": "2020/6/22 14:29:32",
+		"771969": "2024/10/30 23:03:17",
+		"769338": "2024/12/16 22:48:29",
+		"731168": "2020/7/30 6:00:43",
+		"769364": "2024/12/29 19:10:40",
+		"769065": "2024/10/31 20:37:21",
+		"033662": "2020/12/15 17:27:59",
+		"044996": "2022/7/31 0:00:00",
+		"061625": "2022/5/24 15:35:36",
+		"026544": "2020/5/14 18:43:57",
+		"772299": "2025/4/12 22:37:11",
+		"037378": "2021/4/16 17:08:10",
+		"769883": "2024/9/8 16:47:58",
+		"034942": "2021/2/25 16:55:04",
+		"731302": "2020/9/16 3:20:05",
+		"770741": "2024/9/13 12:50:44",
+		"771973": "2024/11/18 20:52:27",
+		"061662": "2022/5/24 15:16:15",
+		"606196": "2019/12/20 15:11:54",
+		"038257": "2022/5/24 17:41:17",
+		"827890": "2020/6/13 22:00:03",
+		"769875": "2024/9/5 14:59:20",
+		"771937": "2024/10/22 22:51:05",
+		"738386": "2021/7/16 7:20:36",
+		"731326": "2020/9/19 20:50:03",
+		"765574": "2024/11/13 21:00:56",
+		"830660": "2020/6/24 16:40:18",
+		"770755": "2024/9/14 18:32:34",
+		"771955": "2024/10/27 22:58:24",
+		"906642": "2020/1/20 22:20:52",
+		"766450": "2024/7/3 15:50:02",
+		"766738": "2024/9/10 16:45:26",
+		"039660": "2022/7/31 0:00:00",
+		"431828": "2020/7/22 7:18:07",
+		"768740": "2024/10/2 15:32:33",
+		"766412": "2024/6/15 15:05:31",
+		"059184": "2022/5/24 19:19:37",
+		"772109": "2025/1/10 20:56:50",
+		"769318": "2024/12/14 19:28:10",
+		"768702": "2024/9/17 16:44:08",
+		"869291": "2024/10/9 16:47:16",
+		"745756": "2022/6/3 16:14:09",
+		"044650": "2022/5/8 23:02:44",
+		"063544": "2022/5/24 10:34:07",
+		"769320": "2024/12/14 21:29:07",
+		"772085": "2024/12/18 15:04:06",
+		"047012": "2022/5/24 8:47:36",
+		"039879": "2022/5/24 7:51:43",
+		"731286": "2020/9/9 3:40:14",
+		"058598": "2022/5/24 8:53:20",
+		"772293": "2025/4/11 23:01:40",
+		"066150": "2022/5/24 10:40:13",
+		"865940": "2024/10/3 16:45:32",
+		"772105": "2024/12/26 19:22:13",
+		"054489": "2022/5/24 15:21:07",
+		"772305": "2025/4/13 23:22:12",
+		"027414": "2020/5/21 18:13:24",
+		"766712": "2024/9/7 19:18:58",
+		"770737": "2024/9/12 18:54:39",
+		"766352": "2024/5/27 19:56:33",
+		"038432": "2022/5/24 10:07:20",
+		"830890": "2020/7/16 21:10:20",
+		"737916": "2021/6/15 7:13:46",
+		"067163": "2022/5/24 14:43:19",
+		"770719": "2024/9/10 16:48:03",
+		"831750": "2020/11/14 21:01:18",
+		"838502": "2021/7/25 18:14:00",
+		"728078": "2020/6/26 4:45:18",
+		"738962": "2021/8/23 13:45:22",
+		"731252": "2020/9/1 6:21:43",
+		"043966": "2022/4/14 7:45:17",
+		"725808": "2020/5/12 11:11:21",
+		"838238": "2021/6/19 23:00:10",
+		"769368": "2025/1/2 23:40:02",
+		"137232": "2021/4/24 16:32:57",
+		"030690": "2022/5/24 9:09:29",
+		"772249": "2025/3/22 23:45:31",
+		"769200": "2024/10/18 23:04:58",
+		"728178": "2020/5/30 21:30:19",
+		"034972": "2021/2/27 17:26:14",
+		"772125": "2025/1/18 22:57:10",
+		"054908": "2022/5/24 15:21:30",
+		"825380": "2020/5/8 21:10:15",
+		"738994": "2021/9/14 19:58:33",
+		"766354": "2024/5/27 19:57:03",
+		"770797": "2024/9/20 18:45:04",
+		"036906": "2021/3/11 17:45:11",
+		"058387": "2022/5/24 16:59:00",
+		"838524": "2021/8/6 21:22:10",
+		"770206": "2025/1/15 19:32:55",
+		"060568": "2022/7/31 0:00:00",
+		"060533": "2022/5/24 15:41:06",
+		"830822": "2020/7/20 3:05:43",
+		"122634": "2020/4/13 20:51:44",
+		"728074": "2020/6/25 8:00:33",
+		"772221": "2025/3/8 22:56:40",
+		"735642": "2021/1/14 23:00:23",
+		"059461": "2022/7/31 0:00:00",
+		"769847": "2024/9/1 17:35:11",
+		"769346": "2024/12/21 21:19:46",
+		"058152": "2022/7/31 0:00:00",
+		"035040": "2021/3/5 18:15:10",
+		"037316": "2021/4/4 17:24:40",
+		"766484": "2024/9/3 16:50:01",
+		"766400": "2024/6/11 11:12:31",
+		"769362": "2024/12/27 20:56:20",
+		"769841": "2024/8/30 18:56:18",
+		"731356": "2020/9/27 15:42:16",
+		"127092": "2020/5/12 23:11:33",
+		"769388": "2025/1/13 19:20:49",
+		"728256": "2020/6/8 8:05:35",
+		"710616": "2019/10/16 16:17:39",
+		"838574": "2021/9/18 23:45:09",
+		"769246": "2024/10/30 23:13:14",
+		"766128": "2024/10/17 21:06:43",
+		"710618": "2019/10/17 9:57:52",
+		"772177": "2025/2/23 22:55:27",
+		"869190": "2024/11/13 16:06:09",
+		"760687": "2024/10/3 8:34:57",
+		"731278": "2020/9/7 20:40:58",
+		"769204": "2024/10/19 22:37:18",
+		"770795": "2024/9/19 19:51:14",
+		"770783": "2024/9/17 16:47:29",
+		"056217": "2022/5/24 17:14:57",
+		"830880": "2020/7/15 18:40:32",
+		"044945": "2022/5/24 10:04:09",
+		"732448": "2020/10/12 2:37:20",
+		"039294": "2022/5/24 18:52:33",
+		"772295": "2025/4/12 22:35:22",
+		"772257": "2025/3/26 23:45:42",
+		"772087": "2024/12/20 22:51:31",
+		"055970": "2022/7/31 0:00:00",
+		"770432": "2025/2/27 19:06:45",
+		"770771": "2024/9/16 16:40:29",
+		"027542": "2020/6/17 17:32:58",
+		"738916": "2021/8/6 13:30:46",
+		"771915": "2024/10/18 22:35:48",
+		"923004": "2020/2/5 6:25:24",
+		"065125": "2022/5/24 15:54:11",
+		"725840": "2020/5/16 11:55:52",
+		"871885": "2024/11/10 18:59:45",
+		"769208": "2024/10/19 22:43:11",
+		"768750": "2024/10/12 10:07:49",
+		"728054": "2020/6/22 5:11:09",
+		"772211": "2025/2/28 22:48:36",
+		"611094": "2019/12/27 22:21:16",
+		"030887": "2022/5/24 16:39:44",
+		"769873": "2024/9/5 14:57:32",
+		"766730": "2024/9/10 16:35:54",
+		"038749": "2022/5/24 8:33:24",
+		"772235": "2025/3/12 23:10:05",
+		"051746": "2022/12/30 15:05:13",
+		"770424": "2025/2/23 22:55:05",
+		"036974": "2021/3/18 22:14:18",
+		"047675": "2022/5/24 18:22:59",
+		"772097": "2024/12/22 23:52:50",
+		"043974": "2022/4/16 0:16:20",
+		"866106": "2024/10/6 17:39:33",
+		"066055": "2022/5/24 11:05:13",
+		"728292": "2020/6/12 23:15:43",
+		"725836": "2020/5/16 22:18:42",
+		"728210": "2020/6/3 16:00:00",
+		"770749": "2024/9/14 18:35:44",
+		"843246": "2022/3/25 17:37:37",
+		"122598": "2020/4/4 21:34:20",
+		"869283": "2024/10/3 16:46:18",
+		"138168": "2021/6/21 1:48:04",
+		"844530": "2022/4/25 20:20:37",
+		"869293": "2024/11/4 10:50:57",
+		"065380": "2022/5/24 18:06:34",
+		"735654": "2021/3/13 13:35:12",
+		"843206": "2022/3/10 16:50:01",
+		"770510": "2025/4/13 23:20:58",
+		"065028": "2022/5/24 17:17:35",
+		"770412": "2025/2/10 21:40:31",
+		"731192": "2020/8/10 18:00:18",
+		"767725": "2024/11/9 23:30:29",
+		"838208": "2021/6/3 8:30:17",
+		"770747": "2024/9/14 18:36:14",
+		"831716": "2020/9/19 20:08:49",
+		"772121": "2025/1/15 19:30:56",
+		"731152": "2020/7/24 22:30:44",
+		"770508": "2025/4/9 23:12:33",
+		"182695": "2018/8/14 18:50:51",
+		"026370": "2020/4/29 18:39:14",
+		"770775": "2024/9/16 16:44:33",
+		"128812": "2020/5/20 19:22:44",
+		"768764": "2024/10/13 18:32:37",
+		"045401": "2022/5/24 17:48:51",
+		"772175": "2025/2/18 22:26:27",
+		"061746": "2022/5/24 17:10:22",
+		"425968": "2020/5/21 8:13:58",
+		"731076": "2020/7/11 15:35:37",
+		"732402": "2020/9/28 23:21:21",
+		"771943": "2024/10/23 22:52:26",
+		"771939": "2024/10/22 22:51:34",
+		"768807": "2024/11/15 20:23:54",
+		"768724": "2024/9/25 15:39:12",
+		"038363": "2022/5/24 16:11:25",
+		"770416": "2025/2/14 23:40:02",
+		"728174": "2020/5/30 20:35:17",
+		"739432": "2021/10/9 7:30:20",
+		"765566": "2024/11/12 19:18:38",
+		"772089": "2024/12/21 21:16:57",
+		"066270": "2022/5/24 7:56:35",
+		"060550": "2022/5/24 15:21:00",
+		"725804": "2020/5/12 11:08:23",
+		"228734": "2020/6/8 10:30:47",
+		"431926": "2020/8/9 0:18:22",
+		"770761": "2024/9/14 18:31:15",
+		"770462": "2025/3/8 22:57:57",
+		"766486": "2024/9/4 16:50:13",
+		"766444": "2024/8/18 18:50:49",
+		"026442": "2020/5/4 17:54:08",
+		"830684": "2020/6/26 23:05:47",
+		"058460": "2022/5/24 8:29:01",
+		"768795": "2024/11/12 19:17:29",
+		"772289": "2025/4/11 22:58:49",
+		"036984": "2021/3/20 22:00:48",
+		"728282": "2020/6/10 17:45:25",
+		"062401": "2022/5/24 9:17:57",
+		"739414": "2021/9/22 19:07:51",
+		"769595": "2024/6/29 23:49:09",
+		"768778": "2024/10/14 16:04:50",
+		"768780": "2024/10/14 16:08:53",
+		"772057": "2024/12/5 23:45:17",
+		"769871": "2024/9/4 16:48:17",
+		"838590": "2021/10/26 23:23:03",
+		"728234": "2020/6/5 20:20:10",
+		"906628": "2020/1/19 6:10:44",
+		"771965": "2024/10/29 23:01:29",
+		"738382": "2021/7/11 18:13:36",
+		"825306": "2020/4/22 1:15:22",
+		"182924": "2018/8/23 10:20:00",
+		"768704": "2024/9/17 16:45:24",
+		"768774": "2024/10/13 18:49:27",
+		"831620": "2020/8/3 20:13:04",
+		"766126": "2024/10/17 21:05:33",
+		"045308": "2022/5/24 15:53:06",
+		"770779": "2024/9/17 16:40:54",
+		"049144": "2022/5/24 7:56:00",
+		"769334": "2024/12/15 22:59:57",
+		"038153": "2022/7/31 0:00:00",
+		"728064": "2020/6/23 11:40:24",
+		"770486": "2025/3/31 20:36:55",
+		"838526": "2021/8/6 21:22:36",
+		"822264": "2020/5/28 23:30:37",
+		"866098": "2024/10/5 10:00:04",
+		"043890": "2022/3/30 6:32:35",
+		"770715": "2024/9/10 16:44:47",
+		"766472": "2024/8/31 19:12:42",
+		"770472": "2025/3/25 23:54:30",
+		"772095": "2024/12/22 23:51:14",
+		"771911": "2024/10/18 22:33:00",
+		"065213": "2022/5/24 9:50:11",
+		"053643": "2022/7/31 0:00:00",
+		"769276": "2024/11/14 19:58:21",
+		"768742": "2024/10/11 17:03:52",
+		"739442": "2021/10/23 13:30:12",
+		"831714": "2020/9/16 7:30:34",
+		"768700": "2024/9/17 16:38:00",
+		"770448": "2025/3/8 22:53:59",
+		"766426": "2024/6/21 18:20:53",
+		"769242": "2024/10/28 23:00:40",
+		"766710": "2024/9/7 19:18:36",
+		"767745": "2024/11/3 19:32:58",
+		"733528": "2020/12/19 12:55:24",
+		"054412": "2022/5/24 17:09:49",
+		"247216": "2022/7/2 22:30:34",
+		"728284": "2020/6/10 22:55:38",
+		"728112": "2020/5/22 20:50:30",
+		"731220": "2020/8/21 6:10:06",
+		"766698": "2024/9/5 15:00:06",
+		"827862": "2020/6/11 14:20:36",
+		"770450": "2025/3/8 22:54:23",
+		"738330": "2021/6/25 6:15:43",
+		"732428": "2020/10/5 5:03:31",
+		"825322": "2020/4/29 12:20:32",
+		"059205": "2022/5/24 8:47:18",
+		"728038": "2020/6/20 14:05:58",
+		"770671": "2024/9/26 15:40:22",
+		"772251": "2025/3/23 23:16:38",
+		"766734": "2024/9/10 16:42:05",
+		"827882": "2020/6/13 12:40:55",
+		"128866": "2020/6/9 19:58:25",
+		"039196": "2022/7/31 0:00:00",
+		"769577": "2024/6/18 20:36:37",
+		"735644": "2021/1/29 11:10:17",
+		"728032": "2020/6/19 20:30:03",
+		"033998": "2021/1/4 18:19:22",
+		"769907": "2024/9/10 16:42:29",
+		"766776": "2024/9/14 18:34:05",
+		"865936": "2024/10/2 21:59:27",
+		"769266": "2024/11/5 21:41:37",
+		"027514": "2020/6/9 17:46:32",
+		"731010": "2020/7/1 16:35:22",
+		"731298": "2020/9/15 13:05:04",
+		"725890": "2020/5/20 17:25:29",
+		"731258": "2020/9/2 18:59:56",
+		"058147": "2022/5/24 15:57:40",
+		"039022": "2022/5/24 9:43:14",
+		"731234": "2020/8/27 20:15:20",
+		"728140": "2020/5/25 21:55:19",
+		"746402": "2022/6/19 18:25:36",
+		"770200": "2025/1/15 19:31:34",
+		"772119": "2025/1/14 20:46:42",
+		"034918": "2021/2/20 16:49:08",
+		"728124": "2020/5/24 1:35:21",
+		"054390": "2022/5/24 10:56:18",
+		"765580": "2024/11/22 23:47:52",
+		"838206": "2021/6/3 7:30:06",
+		"247212": "2022/6/30 6:10:30",
+		"706208": "2019/7/13 19:25:10",
+		"053965": "2022/5/24 9:27:31",
+		"770426": "2025/2/25 21:57:46",
+		"182173": "2018/7/31 22:41:47",
+		"037486": "2021/5/28 17:02:13",
+		"767715": "2024/11/4 18:34:50",
+		"830850": "2020/7/24 20:23:49",
+		"027442": "2020/5/25 17:38:58",
+		"027560": "2020/6/29 19:10:23",
+		"732426": "2020/10/2 18:41:11",
+		"770264": "2025/1/20 20:50:32",
+		"036858": "2021/3/7 19:07:44",
+		"770773": "2024/9/16 16:41:50",
+		"871891": "2024/11/19 20:15:56",
+		"772049": "2025/1/6 23:52:28",
+		"038985": "2022/5/24 17:59:47",
+		"037368": "2021/4/13 18:57:48",
+		"731194": "2020/8/11 17:35:20",
+		"768712": "2024/9/18 10:25:57",
+		"766464": "2024/8/28 20:09:44",
+		"739434": "2021/10/10 7:30:29",
+		"866112": "2024/10/9 16:45:25",
+		"770476": "2025/3/27 23:42:27",
+		"037424": "2021/5/1 18:11:26",
+		"731046": "2020/7/5 20:35:02",
+		"228720": "2020/6/5 7:30:53",
+		"772139": "2025/1/26 23:13:37",
+		"770402": "2025/1/25 23:40:21",
+		"030598": "2022/5/24 16:51:49",
+		"831712": "2020/9/11 7:25:40",
+		"766714": "2024/9/8 16:41:28",
+		"038448": "2022/5/24 10:36:15",
+		"026588": "2020/5/18 18:33:19",
+		"733522": "2020/12/9 18:08:05",
+		"044986": "2022/5/24 17:46:29",
+		"772011": "2024/11/25 21:28:05",
+		"038888": "2022/5/24 14:35:40",
+		"431982": "2020/8/24 0:06:41",
+		"771811": "2024/11/19 0:14:26",
+		"772307": "2025/4/14 22:22:26",
+		"771999": "2024/11/20 14:17:23",
+		"130458": "2020/8/4 20:29:35",
+		"710480": "2019/9/23 9:33:21",
+		"838580": "2021/10/14 16:36:54",
+		"037472": "2021/5/24 16:23:03",
+		"766708": "2024/9/7 19:18:16",
+		"054986": "2022/7/31 0:00:00",
+		"036966": "2021/3/17 17:02:16",
+		"772185": "2025/2/26 21:16:38",
+		"182635": "2018/10/9 18:50:25",
+		"772277": "2025/4/5 22:52:42",
+		"766480": "2024/9/2 17:55:25",
+	}
+	for k, v := range admissionAgeMap {
+		cowInfo, err := s.GetCowInfoByEarNumber(ctx, 4, k)
+		if err != nil {
+			zaplog.Error("CalvingAge", zap.Any("k", k), zap.Any("v", v), zap.Any("err", err))
+			continue
+		}
+
+		admissionAt, _ := util.TimeParseLocal(model.LayoutTime2, v)
+		if !admissionAt.IsZero() {
+			cowInfo.AdmissionAt = admissionAt.Unix()
+			cowInfo.AdmissionAge = cowInfo.GetAdmissionAge()
+			if err = s.DB.Model(new(model.Cow)).
+				Where("id = ?", cowInfo.Id).
+				Updates(map[string]interface{}{
+					"admission_at":  cowInfo.AdmissionAt,
+					"admission_age": cowInfo.AdmissionAge,
+				}).Error; err != nil {
+				zaplog.Error("CalvingAge", zap.Any("err", err))
+			}
+		}
+	}
+	return nil
+}
+
+func (s *StoreEntry) CalvingAge(ctx context.Context) error {
+	calvingAgeMap := map[string]string{
+		"731268":   "2024/12/16 22:41:59",
+		"049560":   "2024/9/2 14:40:31",
+		"039676":   "2024/10/22 22:48:45",
+		"061595":   "2024/7/2 10:30:21",
+		"866100":   "",
+		"772301":   "",
+		"033000":   "2024/10/14 16:08:53",
+		"044126":   "2024/12/27 20:56:20",
+		"766740":   "",
+		"869277":   "",
+		"769579":   "",
+		"731236":   "2025/3/31 20:36:27",
+		"066786":   "2024/9/10 16:46:58",
+		"830744":   "2024/9/24 18:29:10",
+		"770745":   "",
+		"770520":   "",
+		"067126":   "2024/11/4 18:35:16",
+		"769280":   "",
+		"846286":   "2025/2/23 22:55:27",
+		"058401":   "2024/9/12 9:47:13",
+		"766704":   "",
+		"771979":   "",
+		"731014":   "2025/1/21 20:22:16",
+		"731210":   "2024/12/15 22:57:36",
+		"060257":   "2024/9/7 19:17:55",
+		"043337":   "2024/9/20 18:45:36",
+		"769286":   "",
+		"871887":   "",
+		"766458":   "",
+		"034836":   "2024/11/21 1:13:34",
+		"034884":   "2024/11/18 20:53:09",
+		"122558":   "2025/2/11 17:00:59",
+		"771935":   "",
+		"770739":   "",
+		"771917":   "",
+		"182626":   "2024/10/8 17:09:35",
+		"840540":   "2024/10/1 17:03:00",
+		"766716":   "",
+		"769256":   "",
+		"771913":   "",
+		"055258":   "2024/9/8 16:41:28",
+		"621666":   "2024/6/20 16:45:09",
+		"770707":   "",
+		"770492":   "",
+		"770805":   "",
+		"060516":   "2024/9/8 16:47:58",
+		"039251":   "2024/11/26 22:00:02",
+		"765586":   "",
+		"738360":   "2025/1/7 21:52:19",
+		"043986":   "2024/6/22 18:21:03",
+		"771945":   "",
+		"830642":   "2024/12/9 19:30:36",
+		"063236":   "2024/9/14 18:36:14",
+		"865928":   "",
+		"769212":   "",
+		"766430":   "",
+		"738976":   "2024/10/17 21:05:33",
+		"770204":   "",
+		"054857":   "2024/10/21 22:46:21",
+		"128878":   "2024/5/21 16:09:23",
+		"039582":   "2024/11/5 21:41:37",
+		"766384":   "",
+		"063481":   "2024/10/18 23:04:58",
+		"622076":   "2024/6/7 8:26:11",
+		"728108":   "2025/1/14 20:46:15",
+		"420902":   "2024/11/13 21:51:25",
+		"244842":   "2024/6/23 15:54:55",
+		"049596":   "2024/9/10 16:35:54",
+		"769236":   "",
+		"127118":   "2025/4/22 23:15:26",
+		"128490":   "2024/5/6 10:59:24",
+		"906652":   "2024/8/18 18:50:49",
+		"063510":   "2024/10/24 22:53:03",
+		"766404":   "",
+		"058645":   "2024/6/23 15:53:20",
+		"425994":   "2024/10/19 19:26:50",
+		"036988":   "2024/6/11 11:07:53",
+		"030641":   "2024/9/7 19:16:53",
+		"043418":   "2024/6/23 15:51:27",
+		"769827":   "",
+		"768748":   "",
+		"769869":   "",
+		"769336":   "",
+		"772043":   "",
+		"830622":   "2025/2/25 21:58:56",
+		"770787":   "",
+		"181662":   "2024/10/14 16:35:23",
+		"425964":   "2024/11/13 21:52:14",
+		"036880":   "2025/3/27 23:42:27",
+		"425936":   "2024/11/2 18:27:29",
+		"768732":   "",
+		"827918":   "2025/4/13 23:20:17",
+		"831738":   "2024/9/9 16:22:55",
+		"769067":   "",
+		"766382":   "",
+		"409156":   "2024/10/5 16:01:23",
+		"765568":   "",
+		"736448":   "2025/3/12 23:11:25",
+		"731360":   "2025/1/6 23:52:15",
+		"043972":   "2025/4/22 22:25:53",
+		"769232":   "",
+		"869164":   "",
+		"766466":   "",
+		"001579":   "2024/9/14 12:18:12",
+		"023998":   "2024/11/27 23:17:15",
+		"771991":   "",
+		"846276":   "2024/5/9 16:42:35",
+		"769555":   "",
+		"772001":   "",
+		"766756":   "",
+		"128810":   "2024/10/18 22:32:41",
+		"827840":   "2024/10/3 16:41:59",
+		"606412":   "2024/5/10 8:21:15",
+		"038020":   "2024/11/18 20:55:31",
+		"731130":   "2025/1/18 22:56:53",
+		"023331":   "2024/12/10 21:38:00",
+		"038695":   "2024/9/16 15:46:38",
+		"769260":   "",
+		"769563":   "",
+		"770518":   "",
+		"026556":   "2024/10/18 21:35:37",
+		"822286":   "2025/2/28 22:47:47",
+		"770536":   "",
+		"606450":   "2025/3/8 22:58:12",
+		"063132":   "2025/1/10 20:56:50",
+		"772187":   "",
+		"770496":   "",
+		"768760":   "",
+		"182972":   "2024/10/9 16:43:53",
+		"434312":   "2024/6/4 11:11:39",
+		"728098":   "2025/1/10 20:57:28",
+		"043984":   "2025/3/27 23:43:16",
+		"725764":   "2024/10/19 22:39:28",
+		"770464":   "",
+		"772287":   "",
+		"772151":   "",
+		"827808":   "2024/9/9 16:24:36",
+		"769314":   "",
+		"766330":   "",
+		"728050":   "2025/1/9 22:09:47",
+		"728320":   "2024/11/15 20:23:12",
+		"067067":   "2024/5/17 18:09:48",
+		"768790":   "",
+		"768791":   "",
+		"731184":   "2024/9/10 16:34:52",
+		"066076":   "2024/9/22 18:16:26",
+		"728114":   "2025/1/12 20:07:01",
+		"621998":   "2024/6/14 10:36:23",
+		"431820":   "2024/11/3 19:32:58",
+		"731240":   "2024/11/5 21:42:40",
+		"043992":   "2024/5/10 14:59:19",
+		"060613":   "2024/9/2 17:55:25",
+		"035034":   "2024/10/25 22:55:33",
+		"731038":   "2024/6/22 18:23:05",
+		"770526":   "",
+		"766474":   "",
+		"825368":   "2024/9/4 16:49:05",
+		"725824":   "2025/3/8 22:57:57",
+		"771961":   "",
+		"026480":   "2025/2/7 21:52:13",
+		"039667":   "2024/11/18 20:54:47",
+		"825338":   "2025/3/8 22:54:55",
+		"144038":   "2024/4/23 12:29:45",
+		"830770":   "2024/10/30 23:03:43",
+		"770394":   "",
+		"770667":   "",
+		"044414":   "2024/6/15 15:06:35",
+		"869285":   "",
+		"772181":   "",
+		"728080":   "2024/12/14 19:27:22",
+		"772263":   "",
+		"768782":   "",
+		"026374":   "2025/3/10 22:30:13",
+		"611028":   "2024/12/11 23:33:41",
+		"049605":   "2024/11/12 19:16:31",
+		"425940":   "2024/11/5 21:42:22",
+		"770767":   "",
+		"769515":   "",
+		"224540":   "2024/10/4 20:32:49",
+		"766470":   "",
+		"825354":   "2024/9/28 15:39:00",
+		"769230":   "",
+		"063175":   "2024/9/9 16:21:20",
+		"770733":   "",
+		"770490":   "",
+		"771921":   "",
+		"038016":   "2024/9/22 18:17:39",
+		"739438":   "2024/10/31 21:02:05",
+		"769891":   "",
+		"182711":   "2024/10/22 22:51:05",
+		"825356":   "2024/9/23 17:28:33",
+		"772113":   "",
+		"036892":   "2024/11/18 20:54:27",
+		"128514":   "2025/4/19 21:08:35",
+		"766784":   "",
+		"049160":   "2024/9/10 16:42:05",
+		"769551":   "",
+		"770530":   "",
+		"210888":   "2024/8/31 19:12:15",
+		"770703":   "",
+		"765576":   "",
+		"710680":   "2024/9/3 18:26:21",
+		"060120":   "2024/9/12 20:13:19",
+		"060117":   "2024/9/3 18:25:33",
+		"038773":   "2024/9/2 17:34:28",
+		"827974":   "2024/9/10 16:44:47",
+		"771975":   "",
+		"770789":   "",
+		"058402":   "2024/8/30 18:56:18",
+		"066266":   "2024/5/21 16:20:53",
+		"049675":   "2023/8/13 7:55:46",
+		"037068":   "2025/2/28 22:48:11",
+		"027516":   "2024/10/19 22:37:38",
+		"039602":   "2024/9/10 16:44:22",
+		"769298":   "",
+		"772063":   "",
+		"063172":   "2024/6/19 9:24:30",
+		"767755":   "",
+		"766454":   "",
+		"772239":   "",
+		"767733":   "",
+		"766780":   "",
+		"827894":   "2025/2/26 21:16:00",
+		"771925":   "",
+		"739426":   "2024/12/7 22:59:37",
+		"766446":   "",
+		"768768":   "",
+		"611130":   "2025/4/20 23:35:49",
+		"731314":   "2024/12/14 19:34:37",
+		"827958":   "2024/10/25 22:56:29",
+		"739416":   "2024/12/14 19:32:17",
+		"768718":   "",
+		"770430":   "",
+		"611164":   "2024/8/22 22:48:12",
+		"830724":   "2024/9/30 21:04:36",
+		"063115":   "2024/11/4 18:36:16",
+		"769292":   "",
+		"772231":   "",
+		"030869":   "2024/9/5 14:57:32",
+		"038043":   "2024/6/10 16:42:27",
+		"769354":   "",
+		"770807":   "",
+		"058581":   "2024/9/4 16:49:30",
+		"034776":   "2024/10/30 23:03:29",
+		"772303":   "",
+		"039106":   "2024/10/14 16:04:50",
+		"039577":   "2024/11/18 20:51:12",
+		"059041":   "2024/9/29 16:15:15",
+		"869275":   "",
+		"825374":   "2025/3/8 22:55:20",
+		"773317":   "",
+		"769350":   "",
+		"038577":   "2024/10/28 20:42:20",
+		"869182":   "",
+		"769893":   "",
+		"026546":   "2024/11/30 12:00:03",
+		"127076":   "2024/10/7 18:48:42",
+		"773315":   "",
+		"022164":   "2023/8/14 21:27:22",
+		"034998":   "2024/10/24 22:54:32",
+		"731200":   "2024/12/16 22:55:07",
+		"766774":   "",
+		"038436":   "2024/9/11 9:50:48",
+		"771949":   "",
+		"769322":   "",
+		"122610":   "2024/10/2 8:34:01",
+		"182683":   "2024/10/9 16:45:25",
+		"060560":   "2024/6/28 16:51:45",
+		"035006":   "2024/10/30 23:03:17",
+		"038717":   "2024/11/29 20:57:48",
+		"772093":   "",
+		"039215":   "2024/9/1 17:30:22",
+		"725894":   "2024/4/10 21:00:10",
+		"772165":   "",
+		"130920":   "2024/4/4 19:56:54",
+		"738938":   "2024/12/22 23:51:14",
+		"039274":   "2024/9/20 21:20:09",
+		"831678":   "2024/10/9 16:47:16",
+		"770506":   "",
+		"039685":   "2024/9/26 10:17:58",
+		"768801":   "",
+		"766692":   "",
+		"769370":   "",
+		"822230":   "2025/2/28 22:47:58",
+		"831664":   "2024/9/9 16:22:07",
+		"766478":   "",
+		"769061":   "",
+		"770478":   "",
+		"772179":   "",
+		"067021":   "2024/11/14 20:27:39",
+		"769899":   "",
+		"731340":   "2024/12/17 23:45:58",
+		"060567":   "2024/6/7 17:36:32",
+		"210864":   "2024/10/9 16:49:57",
+		"038080":   "2025/1/29 15:44:34",
+		"731304":   "2024/9/15 16:10:27",
+		"063099":   "2024/11/19 0:14:26",
+		"770757":   "",
+		"770713":   "",
+		"766772":   "",
+		"731182":   "2025/2/4 20:56:37",
+		"027490":   "2024/10/2 21:59:27",
+		"037438":   "2025/3/8 22:56:54",
+		"770470":   "",
+		"772261":   "",
+		"830632":   "2024/4/12 14:28:37",
+		"738924":   "2024/12/14 20:29:46",
+		"054413":   "2024/6/19 9:21:38",
+		"772039":   "",
+		"766362":   "",
+		"830654":   "2024/2/17 19:15:09",
+		"766736":   "",
+		"737762":   "2024/12/2 22:48:56",
+		"769059":   "",
+		"769250":   "",
+		"830768":   "2024/9/2 14:43:23",
+		"731160":   "2025/1/24 20:26:08",
+		"065137":   "2025/2/24 23:08:35",
+		"769845":   "",
+		"047444":   "2024/12/29 19:11:19",
+		"728010":   "2025/1/23 23:31:48",
+		"770705":   "",
+		"023986":   "2024/10/12 18:10:20",
+		"128838":   "2025/4/8 20:42:35",
+		"772155":   "",
+		"728148":   "2024/6/7 17:33:24",
+		"769340":   "",
+		"031488":   "2024/8/28 19:52:46",
+		"066041":   "2024/9/2 18:09:57",
+		"759252":   "",
+		"822254":   "2025/2/26 21:17:08",
+		"838554":   "2024/9/8 16:49:51",
+		"843216":   "2025/3/8 22:57:40",
+		"044652":   "2024/3/17 23:11:31",
+		"038763":   "2025/4/4 21:25:59",
+		"772189":   "",
+		"770480":   "",
+		"768726":   "",
+		"768722":   "",
+		"429362":   "2024/10/20 22:45:02",
+		"772271":   "",
+		"830688":   "2024/10/21 22:47:51",
+		"772005":   "",
+		"772053":   "",
+		"045398":   "2024/6/6 18:29:15",
+		"733540":   "2024/10/21 22:46:02",
+		"044823":   "2024/11/3 19:33:34",
+		"055507":   "2024/6/19 9:34:13",
+		"247202":   "2024/6/1 14:47:01",
+		"772297":   "",
+		"066218":   "2024/6/4 20:52:52",
+		"731232":   "2025/1/14 20:50:59",
+		"137532":   "2024/4/14 9:13:33",
+		"731230":   "2025/1/18 22:57:10",
+		"000936":   "2024/9/29 19:50:49",
+		"770759":   "",
+		"058582":   "2024/6/15 15:05:31",
+		"027536":   "2025/4/4 21:24:50",
+		"059558":   "2024/10/12 10:07:49",
+		"768788":   "",
+		"770781":   "",
+		"769903":   "",
+		"053943":   "2024/9/16 16:40:29",
+		"245494":   "2024/6/23 15:48:01",
+		"827964":   "2024/9/14 11:59:34",
+		"031519":   "2024/9/6 17:03:06",
+		"038248":   "2024/9/17 16:45:24",
+		"766460":   "",
+		"866094":   "",
+		"146168":   "2025/3/30 21:27:41",
+		"00065767": "2024/5/31 16:43:42",
+		"038720":   "2024/10/28 23:01:15",
+		"831606":   "2024/9/27 20:06:34",
+		"770406":   "",
+		"022908":   "2024/9/3 16:50:01",
+		"768716":   "",
+		"210868":   "2024/8/29 19:41:14",
+		"769372":   "",
+		"769192":   "",
+		"770659":   "",
+		"034770":   "2024/10/31 20:36:56",
+		"708392":   "2024/10/19 22:39:13",
+		"767747":   "",
+		"055256":   "2024/8/30 18:50:13",
+		"066666":   "2024/10/31 21:03:27",
+		"710610":   "2024/10/30 22:34:01",
+		"769867":   "",
+		"047400":   "2024/9/15 16:12:23",
+		"760689":   "",
+		"039635":   "2024/10/17 21:03:13",
+		"769445":   "",
+		"768805":   "",
+		"767737":   "",
+		"725864":   "2024/6/4 11:11:12",
+		"065780":   "2024/9/8 16:41:53",
+		"210846":   "2025/4/4 21:38:49",
+		"026600":   "2024/5/20 21:14:51",
+		"228758":   "2024/6/3 11:22:53",
+		"728066":   "2023/11/13 21:16:03",
+		"770418":   "",
+		"057067":   "2024/10/17 21:01:08",
+		"061649":   "2024/12/14 19:33:03",
+		"425992":   "2024/12/3 21:50:25",
+		"843212":   "2024/12/15 22:49:27",
+		"772279":   "",
+		"746406":   "2024/4/17 10:47:23",
+		"066631":   "2024/11/25 21:29:02",
+		"130460":   "2024/12/8 14:26:18",
+		"772051":   "",
+		"770482":   "",
+		"770420":   "",
+		"830844":   "2024/12/5 23:45:17",
+		"825352":   "2024/6/10 19:16:08",
+		"044642":   "2024/4/18 11:59:07",
+		"728198":   "2024/11/18 20:55:15",
+		"061767":   "2024/9/15 20:43:00",
+		"731244":   "2024/11/12 19:19:09",
+		"044422":   "2024/10/3 9:35:34",
+		"770677":   "",
+		"770436":   "",
+		"923066":   "2024/9/9 16:21:46",
+		"039297":   "2024/11/2 18:30:47",
+		"769312":   "",
+		"034724":   "2025/2/11 16:35:53",
+		"769843":   "",
+		"731242":   "2024/5/22 16:02:08",
+		"731290":   "2024/10/7 9:50:44",
+		"043964":   "2025/4/22 22:24:30",
+		"838216":   "2025/4/9 23:11:18",
+		"769837":   "",
+		"772243":   "",
+		"731090":   "2025/2/8 21:48:21",
+		"058206":   "2024/10/29 23:01:29",
+		"066239":   "2024/9/13 12:57:26",
+		"027550":   "2025/4/11 23:01:40",
+		"731066":   "2025/4/19 10:55:00",
+		"061607":   "2024/9/26 15:38:24",
+		"766432":   "",
+		"128818":   "2025/1/31 15:48:15",
+		"043892":   "2025/3/28 22:13:30",
+		"622026":   "2024/5/31 16:44:19",
+		"061268":   "2025/1/21 20:20:10",
+		"026454":   "2024/5/13 18:35:53",
+		"769835":   "",
+		"039752":   "2024/9/6 17:01:53",
+		"770735":   "",
+		"771941":   "",
+		"825316":   "2024/9/28 15:42:40",
+		"846970":   "2025/4/13 23:22:12",
+		"128450":   "2025/4/17 10:19:22",
+		"865934":   "",
+		"838532":   "2024/9/27 9:42:13",
+		"728048":   "2024/6/7 8:32:58",
+		"772245":   "",
+		"060201":   "2024/9/5 14:59:41",
+		"124284":   "2025/4/14 22:22:26",
+		"043343":   "2024/9/4 16:48:40",
+		"060805":   "2024/6/19 9:35:26",
+		"770701":   "",
+		"767731":   "",
+		"770456":   "",
+		"827926":   "2024/9/28 15:40:19",
+		"772229":   "",
+		"039028":   "2024/11/2 19:02:35",
+		"049637":   "2024/9/5 14:59:20",
+		"766452":   "",
+		"037470":   "2024/11/15 20:23:34",
+		"865930":   "",
+		"606470":   "2024/10/5 10:00:04",
+		"830714":   "2024/9/11 9:50:36",
+		"869184":   "",
+		"038139":   "2024/9/5 14:51:53",
+		"766720":   "",
+		"838584":   "2024/9/4 16:48:17",
+		"066628":   "2024/9/11 9:50:20",
+		"770440":   "",
+		"766420":   "",
+		"732436":   "2024/10/24 22:54:55",
+		"769300":   "",
+		"838512":   "2024/10/9 16:50:48",
+		"770709":   "",
+		"769264":   "",
+		"210850":   "2024/9/1 13:43:50",
+		"768799":   "",
+		"772227":   "",
+		"772145":   "",
+		"439088":   "2024/10/28 23:00:54",
+		"770404":   "",
+		"766448":   "",
+		"769220":   "",
+		"770799":   "",
+		"026564":   "2025/3/12 23:10:05",
+		"066034":   "2024/9/9 16:20:50",
+		"838576":   "2024/10/22 22:48:23",
+		"770725":   "",
+		"030848":   "2024/9/12 9:51:12",
+		"768752":   "",
+		"769304":   "",
+		"731206":   "2023/7/1 20:07:55",
+		"027556":   "2024/6/9 14:40:22",
+		"830898":   "2025/3/10 22:28:10",
+		"731282":   "2024/11/18 20:58:00",
+		"768754":   "",
+		"039286":   "2024/9/17 18:57:27",
+		"063531":   "2024/11/20 14:18:08",
+		"772017":   "",
+		"772255":   "",
+		"759334":   "",
+		"831694":   "2024/11/30 11:58:28",
+		"034886":   "2024/2/23 20:07:47",
+		"733536":   "2025/3/12 23:10:48",
+		"060076":   "2024/12/9 19:31:47",
+		"772283":   "",
+		"768714":   "",
+		"043990":   "2025/3/10 22:32:34",
+		"725892":   "2024/6/18 20:36:37",
+		"065757":   "2024/5/29 18:12:50",
+		"236524":   "2025/4/12 22:36:26",
+		"769226":   "",
+		"772023":   "",
+		"772071":   "",
+		"772163":   "",
+		"049508":   "2024/8/25 19:55:38",
+		"211336":   "2024/10/10 9:08:36",
+		"731074":   "2025/3/24 23:44:08",
+		"065986":   "2024/10/20 22:43:46",
+		"066320":   "2024/12/5 23:45:10",
+		"431908":   "2024/10/22 22:50:46",
+		"772129":   "",
+		"745778":   "2024/10/19 22:36:59",
+		"047458":   "2024/9/10 16:36:58",
+		"038364":   "2024/11/18 0:25:41",
+		"770699":   "",
+		"766790":   "",
+		"770512":   "",
+		"831704":   "2024/9/17 16:48:46",
+		"227002":   "2025/4/18 8:37:10",
+		"732480":   "2024/12/23 18:37:31",
+		"766488":   "",
+		"772135":   "",
+		"770502":   "",
+		"738988":   "2024/12/21 21:18:14",
+		"766706":   "",
+		"771947":   "",
+		"825314":   "2025/3/30 21:33:50",
+		"732416":   "2025/3/10 22:30:01",
+		"766788":   "",
+		"055968":   "2024/9/18 15:57:28",
+		"769366":   "",
+		"127090":   "2025/3/3 21:05:29",
+		"731140":   "2024/11/18 20:52:39",
+		"057043":   "2024/11/28 22:23:42",
+		"770484":   "",
+		"923130":   "2024/9/14 18:32:34",
+		"768734":   "",
+		"245476":   "2025/4/10 22:17:22",
+		"768728":   "",
+		"736462":   "2025/2/14 23:40:02",
+		"827904":   "2025/4/12 22:35:22",
+		"731246":   "2024/6/16 18:23:42",
+		"731276":   "2023/6/20 21:05:18",
+		"771959":   "",
+		"063501":   "2024/8/25 19:49:27",
+		"827944":   "2025/1/29 15:47:20",
+		"061829":   "2024/9/17 16:40:54",
+		"769839":   "",
+		"053312":   "2025/4/12 22:37:11",
+		"772045":   "",
+		"728298":   "2024/10/17 21:24:10",
+		"772247":   "",
+		"725770":   "2025/4/19 15:10:01",
+		"766124":   "",
+		"027570":   "2024/8/31 19:12:42",
+		"182133":   "2024/10/20 22:44:07",
+		"772061":   "",
+		"144430":   "2024/4/18 11:58:08",
+		"771987":   "",
+		"049168":   "2025/2/28 22:48:36",
+		"769905":   "",
+		"731102":   "2025/4/4 21:24:12",
+		"038795":   "2024/10/31 20:37:21",
+		"827874":   "2024/10/20 22:44:27",
+		"045287":   "2024/12/21 21:18:53",
+		"054086":   "2024/11/7 20:27:58",
+		"728162":   "2024/6/20 16:48:09",
+		"830878":   "2024/9/11 9:50:00",
+		"766322":   "",
+		"765570":   "",
+		"772143":   "",
+		"770522":   "",
+		"772167":   "",
+		"737914":   "2025/1/15 19:30:56",
+		"766724":   "",
+		"710624":   "2025/2/2 15:49:35",
+		"769573":   "",
+		"038566":   "2024/11/10 22:04:21",
+		"728046":   "2025/2/16 23:42:48",
+		"126806":   "2024/6/1 20:11:19",
+		"822272":   "2024/10/3 16:45:32",
+		"228766":   "2024/6/2 20:06:49",
+		"054032":   "2024/11/25 21:28:05",
+		"768744":   "",
+		"769278":   "",
+		"739422":   "2025/1/3 23:05:44",
+		"224520":   "2024/8/28 20:09:44",
+		"728042":   "2024/6/19 20:35:23",
+		"035072":   "2024/11/27 23:19:02",
+		"772037":   "",
+		"059551":   "2024/10/23 22:52:26",
+		"728026":   "2025/4/9 23:12:33",
+		"846974":   "2024/12/26 20:20:55",
+		"772035":   "",
+		"770532":   "",
+		"766770":   "",
+		"058149":   "2024/9/5 15:00:06",
+		"037474":   "2024/5/5 15:28:47",
+		"772219":   "",
+		"770438":   "",
+		"725832":   "2025/2/9 21:01:29",
+		"732474":   "2025/1/22 23:23:32",
+		"043435":   "2024/12/24 21:07:04",
+		"827906":   "2024/4/25 21:50:50",
+		"058177":   "2025/4/17 7:17:05",
+		"731316":   "2025/1/26 23:13:37",
+		"830738":   "2025/2/10 20:23:26",
+		"731320":   "2025/2/2 15:48:46",
+		"830836":   "2024/4/3 17:57:50",
+		"737942":   "2025/4/6 18:52:37",
+		"770711":   "",
+		"770444":   "",
+		"769326":   "",
+		"731328":   "2024/9/14 18:35:44",
+		"770793":   "",
+		"066627":   "2024/10/20 22:44:48",
+		"027574":   "2024/10/2 21:56:40",
+		"731026":   "2024/9/17 16:38:00",
+		"770803":   "",
+		"733514":   "2024/12/21 21:19:46",
+		"769194":   "",
+		"731342":   "2025/3/8 22:58:55",
+		"871889":   "",
+		"725810":   "2025/2/10 21:40:31",
+		"061664":   "2024/9/7 19:18:58",
+		"825320":   "2024/12/20 22:51:31",
+		"768696":   "",
+		"769382":   "",
+		"769234":   "",
+		"772031":   "",
+		"771923":   "",
+		"731266":   "2024/10/23 22:52:12",
+		"039404":   "2024/12/29 19:10:40",
+		"731188":   "2024/5/23 9:41:34",
+		"057790":   "2024/8/28 19:57:27",
+		"769541":   "",
+		"772259":   "",
+		"027440":   "2024/10/15 20:04:27",
+		"772217":   "",
+		"731128":   "2024/11/5 21:41:58",
+		"056409":   "2025/1/5 23:55:40",
+		"772281":   "",
+		"211324":   "2024/8/25 19:46:54",
+		"066058":   "2024/6/19 9:32:48",
+		"044970":   "2024/9/14 18:31:15",
+		"766782":   "",
+		"039280":   "2024/10/21 22:45:37",
+		"732466":   "2025/1/3 23:07:04",
+		"022965":   "2024/8/28 19:49:39",
+		"771931":   "",
+		"731308":   "2025/1/31 15:47:47",
+		"022482":   "2024/8/30 18:53:58",
+		"830676":   "2024/10/14 16:11:36",
+		"030852":   "2024/9/8 16:49:30",
+		"026470":   "2024/6/11 11:13:57",
+		"731292":   "2025/3/30 21:33:07",
+		"037306":   "2025/3/26 23:45:02",
+		"838506":   "2024/10/22 22:48:09",
+		"065092":   "2024/9/9 16:20:23",
+		"053630":   "2025/4/23 23:08:18",
+		"027510":   "2025/3/10 22:23:18",
+		"766766":   "",
+		"827924":   "2024/12/10 13:33:57",
+		"827886":   "2025/3/8 22:56:24",
+		"044916":   "2024/11/12 20:12:01",
+		"066184":   "2024/9/16 15:42:21",
+		"062371":   "2024/8/29 19:37:02",
+		"057120":   "2024/9/13 12:50:44",
+		"053524":   "2025/3/23 23:19:03",
+		"768694":   "",
+		"769901":   "",
+		"869287":   "",
+		"770695":   "",
+		"738978":   "2025/2/28 22:48:26",
+		"031511":   "2024/9/9 16:26:19",
+		"846294":   "2025/3/18 22:59:42",
+		"768708":   "",
+		"769853":   "",
+		"768698":   "",
+		"770494":   "",
+		"773311":   "",
+		"065573":   "2024/12/1 21:42:50",
+		"770717":   "",
+		"060045":   "2024/9/14 18:33:06",
+		"846252":   "2024/6/8 16:15:01",
+		"725876":   "2025/1/25 23:35:14",
+		"026468":   "2025/3/8 22:56:40",
+		"769453":   "",
+		"770396":   "",
+		"065500":   "2024/10/13 18:34:35",
+		"611128":   "2024/11/10 23:06:13",
+		"062448":   "2024/10/31 20:38:16",
+		"066353":   "2024/10/26 22:58:00",
+		"731116":   "2024/9/14 18:35:18",
+		"766394":   "",
+		"770685":   "",
+		"737910":   "2025/4/1 21:20:46",
+		"065639":   "2024/9/15 15:36:50",
+		"063012":   "2024/9/16 15:43:59",
+		"059447":   "2025/1/14 20:46:42",
+		"770446":   "",
+		"027484":   "2024/12/14 19:28:10",
+		"122494":   "2024/9/9 16:23:20",
+		"769202":   "",
+		"038251":   "2024/9/3 16:50:34",
+		"906644":   "2024/12/8 14:28:34",
+		"611002":   "2025/4/13 23:20:58",
+		"866118":   "",
+		"770785":   "",
+		"054959":   "2024/11/18 20:52:51",
+		"771809":   "",
+		"66694":    "",
+		"770428":   "",
+		"128498":   "2025/4/13 23:21:28",
+		"766760":   "",
+		"830778":   "2024/6/1 14:47:25",
+		"725860":   "2025/2/26 22:08:45",
+		"036888":   "2025/4/7 22:14:07",
+		"063331":   "2024/12/3 21:49:37",
+		"027558":   "2025/4/8 20:43:23",
+		"770743":   "",
+		"027436":   "2024/6/8 21:00:00",
+		"772029":   "",
+		"838536":   "2024/9/26 10:20:06",
+		"769575":   "",
+		"769877":   "",
+		"772273":   "",
+		"766456":   "",
+		"769240":   "",
+		"728024":   "2024/12/14 19:30:38",
+		"728220":   "2024/5/17 18:10:13",
+		"825392":   "2024/4/27 10:36:56",
+		"825334":   "2024/9/17 16:47:29",
+		"770681":   "",
+		"043419":   "2024/8/13 17:07:45",
+		"182641":   "2024/10/18 22:34:12",
+		"127114":   "2024/12/9 19:33:56",
+		"770442":   "",
+		"728268":   "2024/12/17 23:45:02",
+		"772021":   "",
+		"067181":   "2023/8/15 19:35:52",
+		"728250":   "2025/3/10 22:23:34",
+		"027482":   "2024/4/29 13:29:08",
+		"128888":   "2025/3/30 21:35:39",
+		"034868":   "2025/4/1 21:21:49",
+		"869269":   "",
+		"822266":   "2025/4/14 22:20:08",
+		"038011":   "2024/11/7 20:11:17",
+		"236238":   "2024/4/10 14:44:28",
+		"771983":   "",
+		"038604":   "2024/9/18 10:25:57",
+		"039238":   "2024/9/15 15:34:21",
+		"065397":   "2024/11/20 14:21:03",
+		"865932":   "",
+		"846234":   "2024/10/1 17:05:35",
+		"830754":   "2024/9/17 18:59:17",
+		"030880":   "2024/9/4 16:50:43",
+		"771995":   "",
+		"765572":   "",
+		"770534":   "",
+		"065105":   "2024/11/19 0:14:09",
+		"827902":   "2024/10/5 15:59:54",
+		"770693":   "",
+		"049216":   "2024/9/11 9:50:31",
+		"060059":   "2024/9/8 16:42:36",
+		"769881":   "",
+		"772147":   "",
+		"770679":   "",
+		"770801":   "",
+		"770398":   "",
+		"733526":   "2023/12/6 19:42:11",
+		"770528":   "",
+		"770474":   "",
+		"769310":   "",
+		"766410":   "",
+		"769423":   "",
+		"771951":   "",
+		"036860":   "2025/2/23 22:55:50",
+		"772213":   "",
+		"026424":   "2024/10/5 10:02:00",
+		"027538":   "2025/3/3 21:05:54",
+		"771993":   "",
+		"769603":   "",
+		"768710":   "",
+		"050171":   "2024/11/23 18:20:34",
+		"770208":   "",
+		"769897":   "",
+		"731180":   "2024/9/18 15:56:01",
+		"838514":   "2024/9/20 18:45:04",
+		"768770":   "",
+		"065106":   "2024/11/9 23:30:17",
+		"866096":   "",
+		"769833":   "",
+		"831736":   "2024/9/12 9:51:38",
+		"769851":   "",
+		"728006":   "2025/1/11 21:06:04",
+		"830602":   "2024/10/30 21:31:58",
+		"731196":   "2024/10/10 19:53:43",
+		"827990":   "2024/10/17 21:06:43",
+		"728060":   "2025/1/4 11:42:45",
+		"731104":   "2024/9/1 17:27:49",
+		"768784":   "",
+		"871893":   "",
+		"035058":   "2024/11/12 19:18:03",
+		"869271":   "",
+		"728286":   "2024/11/15 20:22:13",
+		"138270":   "2024/10/13 18:30:47",
+		"772267":   "",
+		"769297":   "",
+		"771977":   "",
+		"728138":   "2024/11/22 20:02:21",
+		"061725":   "2024/9/10 16:11:44",
+		"770466":   "",
+		"838226":   "2024/6/9 21:12:54",
+		"772285":   "",
+		"772171":   "",
+		"769376":   "",
+		"066132":   "2024/6/18 16:15:34",
+		"065587":   "2024/12/18 15:04:06",
+		"766718":   "",
+		"770498":   "",
+		"731224":   "2025/1/21 20:21:24",
+		"769855":   "",
+		"766764":   "",
+		"769599":   "",
+		"772265":   "",
+		"210852":   "2024/8/25 19:53:08",
+		"865938":   "",
+		"047364":   "2024/10/12 18:09:02",
+		"831760":   "2025/1/20 20:49:50",
+		"128834":   "2024/11/28 22:18:24",
+		"065107":   "2024/11/14 20:03:16",
+		"827830":   "2025/3/10 22:29:33",
+		"027412":   "2025/2/18 22:26:27",
+		"057854":   "2024/11/12 19:19:55",
+		"766416":   "",
+		"66700":    "",
+		"732450":   "2025/1/9 22:09:18",
+		"036882":   "2024/10/21 20:23:33",
+		"772003":   "",
+		"122636":   "2024/9/9 16:50:18",
+		"043379":   "2024/10/30 23:02:05",
+		"728228":   "2024/6/7 8:27:53",
+		"731054":   "2025/3/8 22:53:59",
+		"771985":   "",
+		"728018":   "2025/3/18 23:00:27",
+		"769198":   "",
+		"738912":   "2024/11/24 18:04:33",
+		"769248":   "",
+		"772291":   "",
+		"766768":   "",
+		"770454":   "",
+		"772069":   "",
+		"061832":   "2024/6/11 11:12:31",
+		"728136":   "2025/2/12 23:10:25",
+		"065619":   "2024/9/5 14:55:20",
+		"210862":   "2024/6/16 18:17:52",
+		"731110":   "2025/1/23 23:31:10",
+		"772237":   "",
+		"710696":   "2025/4/9 23:10:33",
+		"769863":   "",
+		"768772":   "",
+		"771963":   "",
+		"769344":   "",
+		"769244":   "",
+		"769589":   "",
+		"725854":   "2025/4/11 22:58:49",
+		"770769":   "",
+		"822202":   "2024/9/21 21:01:53",
+		"026350":   "2024/12/22 23:52:50",
+		"766368":   "",
+		"728290":   "2025/1/25 23:40:21",
+		"053957":   "2024/9/6 14:03:28",
+		"737902":   "2024/6/5 20:11:23",
+		"036928":   "2025/4/8 20:41:59",
+		"022934":   "2024/9/25 15:39:12",
+		"039677":   "2024/12/14 23:43:31",
+		"825378":   "2025/3/31 20:36:55",
+		"027524":   "2025/3/8 22:54:23",
+		"731310":   "2024/11/23 18:50:32",
+		"866108":   "",
+		"725878":   "2025/4/1 20:21:17",
+		"869273":   "",
+		"769859":   "",
+		"869281":   "",
+		"043948":   "2025/2/25 21:58:24",
+		"409182":   "2025/4/16 22:35:09",
+		"831636":   "2024/9/10 16:43:28",
+		"027402":   "2024/4/16 19:45:30",
+		"772013":   "",
+		"027590":   "2024/9/12 18:52:48",
+		"039649":   "2025/1/23 23:32:23",
+		"770516":   "",
+		"830842":   "2025/4/12 22:38:03",
+		"039296":   "2024/10/12 10:06:35",
+		"030694":   "2024/10/12 18:15:00",
+		"022972":   "2024/10/31 20:36:35",
+		"426024":   "2024/10/21 22:47:38",
+		"766490":   "",
+		"771967":   "",
+		"827806":   "2025/2/27 20:07:32",
+		"731228":   "2024/11/15 20:23:54",
+		"023992":   "2024/9/14 18:33:32",
+		"731260":   "2024/12/4 22:38:52",
+		"770458":   "",
+		"731250":   "2024/10/13 18:42:59",
+		"844562":   "2024/9/30 20:50:41",
+		"766332":   "",
+		"725900":   "2024/12/17 21:43:49",
+		"830604":   "2024/10/5 9:58:47",
+		"772075":   "",
+		"827804":   "2024/5/4 9:05:42",
+		"731238":   "2025/1/13 19:16:32",
+		"770514":   "",
+		"745764":   "2024/6/29 23:49:09",
+		"731118":   "2024/11/30 12:00:49",
+		"027498":   "2024/10/9 16:51:57",
+		"768706":   "",
+		"831686":   "2024/9/8 16:48:22",
+		"771933":   "",
+		"831722":   "2024/9/5 14:55:43",
+		"731262":   "2024/5/12 22:41:23",
+		"136086":   "2024/4/22 14:51:07",
+		"846928":   "2024/10/18 22:33:42",
+		"769895":   "",
+		"737758":   "2025/2/2 15:49:12",
+		"770661":   "",
+		"772131":   "",
+		"066316":   "2023/10/3 21:42:34",
+		"766778":   "",
+		"772275":   "",
+		"731270":   "2024/11/24 18:35:56",
+		"770524":   "",
+		"766406":   "",
+		"772209":   "",
+		"066583":   "2024/10/29 23:01:50",
+		"773313":   "",
+		"871905":   "",
+		"869279":   "",
+		"769324":   "",
+		"033734":   "2024/11/12 19:16:51",
+		"770468":   "",
+		"838248":   "2024/9/12 9:40:50",
+		"769228":   "",
+		"038574":   "2024/10/18 22:36:43",
+		"769063":   "",
+		"772081":   "",
+		"065859":   "2024/10/13 18:28:33",
+		"738948":   "2025/1/2 23:40:25",
+		"769887":   "",
+		"769306":   "",
+		"053752":   "2024/12/22 23:51:52",
+		"054044":   "2024/9/1 17:35:11",
+		"768766":   "",
+		"738954":   "2024/12/16 22:40:25",
+		"770504":   "",
+		"771989":   "",
+		"769218":   "",
+		"725886":   "2025/3/29 20:22:51",
+		"772223":   "",
+		"831680":   "2025/3/23 23:16:38",
+		"822236":   "2025/3/18 23:01:01",
+		"770452":   "",
+		"771909":   "",
+		"066280":   "2023/8/11 22:21:39",
+		"772269":   "",
+		"061685":   "2024/6/25 18:15:06",
+		"822268":   "2025/2/24 22:51:08",
+		"769386":   "",
+		"037448":   "2025/1/13 19:20:49",
+		"738974":   "2025/1/15 19:32:12",
+		"772127":   "",
+		"184746":   "2024/10/6 17:39:33",
+		"773309":   "",
+		"769829":   "",
+		"731186":   "2024/10/3 8:34:57",
+		"710450":   "2024/10/3 16:44:48",
+		"038813":   "2024/11/12 19:18:21",
+		"830624":   "2025/3/20 19:26:34",
+		"211346":   "2024/9/3 18:24:52",
+		"769238":   "",
+		"044688":   "2025/2/27 23:40:16",
+		"606468":   "2024/5/12 22:40:31",
+		"822258":   "2024/10/3 16:39:30",
+		"770727":   "",
+		"182706":   "2024/11/12 19:17:29",
+		"037100":   "2024/3/25 23:42:23",
+		"769272":   "",
+		"769601":   "",
+		"767723":   "",
+		"027448":   "2024/9/30 20:56:42",
+		"026542":   "2025/1/22 23:22:39",
+		"731272":   "2024/10/1 21:29:39",
+		"034730":   "2024/6/6 18:28:50",
+		"772015":   "",
+		"736484":   "2024/4/20 20:42:29",
+		"770488":   "",
+		"772007":   "",
+		"770460":   "",
+		"127120":   "2024/10/3 16:46:18",
+		"022896":   "2024/11/21 23:50:38",
+		"731092":   "2024/11/8 21:43:49",
+		"247210":   "2025/4/15 23:20:01",
+		"047453":   "2024/9/10 16:48:28",
+		"770765":   "",
+		"065158":   "2024/6/5 19:47:13",
+		"058964":   "2025/2/15 23:45:46",
+		"432060":   "2024/11/30 11:59:15",
+		"062254":   "2024/10/11 17:05:06",
+		"838540":   "2024/10/11 17:56:19",
+		"770392":   "",
+		"769889":   "",
+		"770500":   "",
+		"769567":   "",
+		"770262":   "",
+		"772183":   "",
+		"054863":   "2024/9/10 16:48:03",
+		"061749":   "2024/9/26 15:40:22",
+		"768776":   "",
+		"772073":   "",
+		"026596":   "2024/11/27 22:02:20",
+		"770400":   "",
+		"053983":   "2024/8/21 22:08:14",
+		"037430":   "2025/4/11 22:59:28",
+		"034970":   "2024/4/11 16:44:53",
+		"772225":   "",
+		"869289":   "",
+		"767751":   "",
+		"031232":   "2025/2/23 22:55:05",
+		"728204":   "2024/2/16 21:28:15",
+		"769547":   "",
+		"038330":   "2024/10/28 22:59:32",
+		"766130":   "",
+		"038788":   "2024/9/20 18:44:13",
+		"827816":   "2024/4/3 16:56:33",
+		"769849":   "",
+		"059358":   "2024/11/14 19:48:31",
+		"731198":   "2024/10/26 22:57:22",
+		"728128":   "2025/1/15 19:32:55",
+		"769258":   "",
+		"771953":   "",
+		"827980":   "2024/9/12 9:47:44",
+		"838228":   "2024/9/16 16:44:33",
+		"057064":   "2024/9/15 15:41:00",
+		"770414":   "",
+		"033431":   "2024/6/28 17:08:22",
+		"059270":   "2024/9/18 15:59:15",
+		"244062":   "2025/3/29 20:21:51",
+		"066152":   "2024/10/12 18:11:44",
+		"049808":   "2024/8/27 18:39:43",
+		"769374":   "",
+		"731330":   "2023/12/9 23:00:17",
+		"035088":   "2024/4/12 17:59:56",
+		"728244":   "2024/10/28 23:00:17",
+		"772123":   "",
+		"708882":   "2024/9/4 16:50:13",
+		"771919":   "",
+		"769378":   "",
+		"062363":   "2024/10/13 18:38:45",
+		"770675":   "",
+		"059940":   "2024/11/19 0:14:47",
+		"731068":   "2024/12/24 21:07:43",
+		"432004":   "2024/10/14 18:14:07",
+		"066350":   "2025/2/24 23:08:56",
+		"759332":   "",
+		"769380":   "",
+		"059374":   "2024/9/12 9:52:08",
+		"766722":   "",
+		"768692":   "",
+		"732464":   "2024/11/22 23:47:52",
+		"770697":   "",
+		"768756":   "",
+		"772079":   "",
+		"043954":   "2025/4/5 22:53:21",
+		"066580":   "2024/11/19 22:06:41",
+		"047598":   "2024/11/2 18:30:26",
+		"838592":   "2024/10/17 20:57:26",
+		"769857":   "",
+		"843266":   "2025/4/5 22:52:42",
+		"770669":   "",
+		"822296":   "2024/10/21 22:45:23",
+		"030762":   "2024/11/18 20:31:44",
+		"796282":   "",
+		"769823":   "",
+		"039632":   "2024/9/14 15:31:44",
+		"038093":   "2024/7/3 15:50:02",
+		"728106":   "2024/4/20 20:43:41",
+		"830616":   "2024/12/9 19:33:18",
+		"771969":   "",
+		"769338":   "",
+		"731168":   "2024/12/21 21:17:40",
+		"769364":   "",
+		"769065":   "",
+		"033662":   "2024/10/23 21:47:05",
+		"044996":   "2024/6/23 15:49:36",
+		"061625":   "2024/9/6 14:10:27",
+		"026544":   "2024/4/10 14:43:30",
+		"772299":   "",
+		"037378":   "2025/1/20 20:50:32",
+		"769883":   "",
+		"034942":   "2024/11/24 18:32:23",
+		"731302":   "2024/10/23 22:52:46",
+		"770741":   "",
+		"771973":   "",
+		"061662":   "2024/11/4 18:36:53",
+		"606196":   "2024/10/13 18:49:27",
+		"038257":   "2025/1/29 15:45:16",
+		"827890":   "2024/6/13 16:36:24",
+		"769875":   "",
+		"771937":   "",
+		"738386":   "2025/4/16 22:48:08",
+		"731326":   "2024/11/13 21:59:26",
+		"765574":   "",
+		"830660":   "2025/4/4 21:25:26",
+		"770755":   "",
+		"771955":   "",
+		"906642":   "2025/3/3 21:06:04",
+		"766450":   "",
+		"766738":   "",
+		"039660":   "2024/6/7 17:34:59",
+		"431828":   "2024/10/22 22:51:34",
+		"768740":   "",
+		"766412":   "",
+		"059184":   "2024/10/31 20:37:07",
+		"772109":   "",
+		"769318":   "",
+		"768702":   "",
+		"869291":   "",
+		"745756":   "2024/10/19 22:37:18",
+		"044650":   "2025/2/16 23:36:36",
+		"063544":   "2024/9/9 16:23:46",
+		"769320":   "",
+		"772085":   "",
+		"047012":   "2024/12/26 19:24:51",
+		"039879":   "2024/12/8 14:27:28",
+		"731286":   "2025/1/28 15:46:48",
+		"058598":   "2024/8/9 17:16:38",
+		"772293":   "",
+		"066150":   "2024/9/20 18:46:12",
+		"865940":   "",
+		"772105":   "",
+		"054489":   "2025/1/12 20:07:42",
+		"772305":   "",
+		"027414":   "2025/3/22 23:45:31",
+		"766712":   "",
+		"770737":   "",
+		"766352":   "",
+		"038432":   "2024/10/9 19:43:10",
+		"830890":   "2024/5/5 8:59:32",
+		"737916":   "2025/3/8 22:54:40",
+		"067163":   "2024/8/27 18:36:37",
+		"770719":   "",
+		"831750":   "2024/12/1 21:43:51",
+		"838502":   "2024/6/12 15:04:55",
+		"728078":   "2025/3/27 23:38:50",
+		"738962":   "2025/1/13 19:20:07",
+		"731252":   "2025/2/22 20:37:26",
+		"043966":   "2024/6/24 18:34:00",
+		"725808":   "2024/10/31 20:37:48",
+		"838238":   "2024/9/10 16:47:39",
+		"769368":   "",
+		"137232":   "2024/6/7 20:18:13",
+		"030690":   "2024/6/1 14:47:51",
+		"772249":   "",
+		"769200":   "",
+		"728178":   "2024/12/21 21:16:57",
+		"034972":   "2024/11/4 18:34:50",
+		"772125":   "",
+		"054908":   "2024/9/17 17:32:44",
+		"825380":   "2024/12/24 21:06:24",
+		"738994":   "2024/11/18 20:52:27",
+		"766354":   "",
+		"770797":   "",
+		"036906":   "2024/10/15 20:05:10",
+		"058387":   "2024/11/3 19:32:17",
+		"838524":   "2024/8/30 18:46:36",
+		"770206":   "",
+		"060568":   "2024/6/19 20:36:18",
+		"060533":   "2024/11/27 23:19:55",
+		"830822":   "2024/9/11 9:50:18",
+		"122634":   "2024/12/9 19:32:27",
+		"728074":   "2024/12/10 13:04:32",
+		"772221":   "",
+		"735642":   "2025/2/5 20:42:45",
+		"059461":   "2024/6/22 18:22:00",
+		"769847":   "",
+		"769346":   "",
+		"058152":   "2024/6/6 21:03:01",
+		"035040":   "2025/2/4 19:06:32",
+		"037316":   "2024/9/8 16:42:16",
+		"766484":   "",
+		"766400":   "",
+		"769362":   "",
+		"769841":   "",
+		"731356":   "2025/1/21 20:20:50",
+		"127092":   "2025/1/20 20:49:12",
+		"769388":   "",
+		"728256":   "2025/3/30 21:34:48",
+		"710616":   "2024/11/15 20:24:50",
+		"838574":   "2024/9/14 18:31:44",
+		"769246":   "",
+		"766128":   "",
+		"710618":   "2024/11/9 23:30:29",
+		"772177":   "",
+		"869190":   "",
+		"760687":   "",
+		"731278":   "2024/10/13 18:40:39",
+		"769204":   "",
+		"770795":   "",
+		"770783":   "",
+		"056217":   "2024/11/9 23:29:51",
+		"830880":   "2024/8/31 19:13:07",
+		"044945":   "2024/12/20 22:53:10",
+		"732448":   "2024/11/9 23:30:44",
+		"039294":   "2024/12/26 14:07:10",
+		"772295":   "",
+		"772257":   "",
+		"772087":   "",
+		"055970":   "2024/6/28 16:51:23",
+		"770432":   "",
+		"770771":   "",
+		"027542":   "2024/5/25 16:17:02",
+		"738916":   "2024/5/21 16:21:17",
+		"771915":   "",
+		"923004":   "2024/9/19 19:51:14",
+		"065125":   "2024/11/10 22:04:56",
+		"725840":   "2025/2/25 21:57:46",
+		"871885":   "",
+		"769208":   "",
+		"768750":   "",
+		"728054":   "2024/12/15 22:59:15",
+		"772211":   "",
+		"611094":   "2024/5/4 8:59:54",
+		"030887":   "2024/12/26 19:23:09",
+		"769873":   "",
+		"766730":   "",
+		"038749":   "2024/9/17 19:00:55",
+		"772235":   "",
+		"051746":   "2025/3/3 21:05:42",
+		"770424":   "",
+		"036974":   "2024/3/16 23:22:13",
+		"047675":   "2024/11/22 20:03:37",
+		"772097":   "",
+		"043974":   "2025/2/4 19:55:57",
+		"866106":   "",
+		"066055":   "2024/8/29 19:39:09",
+		"728292":   "2024/11/18 20:51:40",
+		"725836":   "2025/1/14 20:45:40",
+		"728210":   "2024/12/14 19:33:49",
+		"770749":   "",
+		"843246":   "2025/3/10 22:29:10",
+		"122598":   "2024/9/7 19:18:36",
+		"869283":   "",
+		"138168":   "2024/5/26 18:06:07",
+		"844530":   "2025/2/26 21:16:38",
+		"869293":   "",
+		"065380":   "2024/11/20 14:21:55",
+		"735654":   "2024/5/4 9:05:13",
+		"843206":   "2024/5/19 11:25:04",
+		"770510":   "",
+		"065028":   "2024/11/20 14:20:10",
+		"770412":   "",
+		"731192":   "2024/5/23 14:23:10",
+		"767725":   "",
+		"838208":   "2024/9/27 20:05:16",
+		"770747":   "",
+		"831716":   "2024/10/18 22:35:48",
+		"772121":   "",
+		"731152":   "2024/9/14 15:32:12",
+		"770508":   "",
+		"182695":   "2024/10/28 20:42:54",
+		"026370":   "2025/3/10 22:30:27",
+		"770775":   "",
+		"128812":   "2025/4/1 20:20:05",
+		"768764":   "",
+		"045401":   "2024/6/1 14:51:28",
+		"772175":   "",
+		"061746":   "2024/10/13 18:24:29",
+		"425968":   "2024/11/4 18:34:03",
+		"731076":   "2024/9/14 18:34:05",
+		"732402":   "2024/11/19 22:00:35",
+		"771943":   "",
+		"771939":   "",
+		"768807":   "",
+		"768724":   "",
+		"038363":   "2024/10/30 23:13:14",
+		"770416":   "",
+		"728174":   "2024/11/15 21:02:40",
+		"739432":   "2025/1/8 20:51:17",
+		"765566":   "",
+		"772089":   "",
+		"066270":   "2024/9/3 18:25:53",
+		"060550":   "2024/10/27 22:58:55",
+		"725804":   "2024/2/24 21:05:46",
+		"228734":   "2024/6/3 14:11:25",
+		"431926":   "2024/10/22 22:51:52",
+		"770761":   "",
+		"770462":   "",
+		"766486":   "",
+		"766444":   "",
+		"026442":   "2024/10/19 22:43:11",
+		"830684":   "2024/4/11 16:46:12",
+		"058460":   "2024/11/15 20:21:15",
+		"768795":   "",
+		"772289":   "",
+		"036984":   "2025/4/9 23:12:01",
+		"728282":   "2024/11/14 19:58:21",
+		"062401":   "2024/12/10 21:38:42",
+		"739414":   "2024/11/12 19:18:38",
+		"769595":   "",
+		"768778":   "",
+		"768780":   "",
+		"772057":   "",
+		"769871":   "",
+		"838590":   "2024/1/1 19:14:19",
+		"728234":   "2024/4/28 12:10:11",
+		"906628":   "2025/4/19 0:04:52",
+		"771965":   "",
+		"738382":   "2024/9/10 16:43:55",
+		"825306":   "2024/12/11 23:32:51",
+		"182924":   "2024/12/25 9:10:26",
+		"768704":   "",
+		"768774":   "",
+		"831620":   "2024/12/31 22:54:51",
+		"766126":   "",
+		"045308":   "2024/10/31 20:36:16",
+		"770779":   "",
+		"049144":   "2024/12/26 19:22:13",
+		"769334":   "",
+		"038153":   "2024/6/1 14:50:42",
+		"728064":   "2024/4/22 14:50:39",
+		"770486":   "",
+		"838526":   "2024/5/31 16:40:17",
+		"822264":   "2024/6/21 18:20:53",
+		"866098":   "",
+		"043890":   "2024/4/15 10:55:02",
+		"770715":   "",
+		"766472":   "",
+		"770472":   "",
+		"772095":   "",
+		"771911":   "",
+		"065213":   "2024/11/9 23:23:46",
+		"053643":   "2024/6/9 14:42:38",
+		"769276":   "",
+		"768742":   "",
+		"739442":   "2025/4/21 22:08:38",
+		"831714":   "2024/10/11 17:03:52",
+		"768700":   "",
+		"770448":   "",
+		"766426":   "",
+		"769242":   "",
+		"766710":   "",
+		"767745":   "",
+		"733528":   "2025/3/13 21:18:43",
+		"054412":   "2024/9/8 16:49:07",
+		"247216":   "2025/3/23 23:18:32",
+		"728284":   "2025/3/26 23:45:42",
+		"728112":   "2024/6/8 16:12:29",
+		"731220":   "2025/3/25 23:54:30",
+		"766698":   "",
+		"827862":   "2025/1/14 20:47:26",
+		"770450":   "",
+		"738330":   "2025/4/11 23:00:27",
+		"732428":   "2024/12/22 23:53:27",
+		"825322":   "2024/12/5 23:45:03",
+		"059205":   "2024/10/11 17:57:16",
+		"728038":   "2024/11/6 21:48:31",
+		"770671":   "",
+		"772251":   "",
+		"766734":   "",
+		"827882":   "2024/4/14 16:33:35",
+		"128866":   "2024/10/1 21:22:21",
+		"039196":   "2024/6/18 16:17:07",
+		"769577":   "",
+		"735644":   "2025/1/16 23:40:21",
+		"728032":   "2025/1/9 22:22:52",
+		"033998":   "2025/1/6 23:52:28",
+		"769907":   "",
+		"766776":   "",
+		"865936":   "",
+		"769266":   "",
+		"027514":   "2024/6/18 16:11:52",
+		"731010":   "2025/4/20 23:35:13",
+		"731298":   "2024/11/12 19:18:52",
+		"725890":   "2025/2/19 21:27:16",
+		"731258":   "2025/3/3 21:06:19",
+		"058147":   "2024/9/5 17:10:18",
+		"039022":   "2024/8/26 20:10:53",
+		"731234":   "2024/10/13 18:50:13",
+		"728140":   "2024/10/18 22:33:27",
+		"746402":   "2024/5/5 9:04:03",
+		"770200":   "",
+		"772119":   "",
+		"034918":   "2024/11/4 18:34:24",
+		"728124":   "2025/4/21 22:08:04",
+		"054390":   "2024/12/16 22:48:29",
+		"765580":   "",
+		"838206":   "2024/8/23 16:31:47",
+		"247212":   "2025/4/23 23:07:45",
+		"706208":   "2024/12/20 15:05:31",
+		"053965":   "2024/8/28 19:59:13",
+		"770426":   "",
+		"182173":   "2024/10/4 20:34:42",
+		"037486":   "2024/5/15 15:46:05",
+		"767715":   "",
+		"830850":   "2024/9/10 16:45:26",
+		"027442":   "2025/4/11 22:58:01",
+		"027560":   "2024/6/18 23:31:23",
+		"732426":   "2024/11/14 20:02:12",
+		"770264":   "",
+		"036858":   "2024/11/3 19:32:39",
+		"770773":   "",
+		"871891":   "",
+		"772049":   "",
+		"038985":   "2024/9/14 11:58:00",
+		"037368":   "2024/9/30 21:50:00",
+		"731194":   "2024/10/18 22:33:00",
+		"768712":   "",
+		"766464":   "",
+		"739434":   "2023/10/1 21:00:09",
+		"866112":   "",
+		"770476":   "",
+		"037424":   "2024/9/17 16:42:17",
+		"731046":   "2024/11/12 19:17:49",
+		"228720":   "2024/6/13 16:34:39",
+		"772139":   "",
+		"770402":   "",
+		"030598":   "2024/8/19 18:39:11",
+		"831712":   "2024/6/22 16:33:25",
+		"766714":   "",
+		"038448":   "2024/8/25 18:55:05",
+		"026588":   "2024/12/17 23:45:07",
+		"733522":   "2024/12/12 23:52:45",
+		"044986":   "2024/8/26 20:07:08",
+		"772011":   "",
+		"038888":   "2024/10/13 18:32:37",
+		"431982":   "2024/11/18 20:32:42",
+		"771811":   "",
+		"772307":   "",
+		"771999":   "",
+		"130458":   "2024/8/31 19:13:52",
+		"710480":   "2025/1/5 23:55:26",
+		"838580":   "2024/10/9 16:48:27",
+		"037472":   "2024/6/26 21:42:35",
+		"766708":   "",
+		"054986":   "2024/6/17 12:34:38",
+		"036966":   "2025/3/26 23:45:52",
+		"772185":   "",
+		"182635":   "2024/9/16 14:43:14",
+		"772277":   "",
+		"766480":   "",
+	}
+	for k, v := range calvingAgeMap {
+		if v == "" {
+			continue
+		}
+		cowInfo, err := s.GetCowInfoByEarNumber(ctx, 4, k)
+		if err != nil {
+			zaplog.Error("CalvingAge", zap.Any("k", k), zap.Any("v", v), zap.Any("err", err))
+			continue
+		}
+
+		calvingAt, _ := util.TimeParseLocal(model.LayoutTime2, v)
+		if !calvingAt.IsZero() {
+			cowInfo.LastCalvingAt = calvingAt.Unix()
+			cowInfo.LactationAge = cowInfo.GetLactationDays()
+			if err = s.DB.Model(new(model.Cow)).
+				Where("id = ?", cowInfo.Id).
+				Updates(map[string]interface{}{
+					"last_calving_at": cowInfo.LastCalvingAt,
+					"lactation_age":   cowInfo.LactationAge,
+				}).Error; err != nil {
+				zaplog.Error("CalvingAge", zap.Any("err", err))
+			}
+		}
+	}
+	return nil
+}

+ 200 - 2
module/backend/upload_file.go

@@ -9,7 +9,9 @@ import (
 	"mime/multipart"
 	"os"
 	"path/filepath"
+	"reflect"
 	"strconv"
+	"strings"
 	"time"
 
 	"gorm.io/gorm"
@@ -79,7 +81,7 @@ func (s *StoreEntry) ImportExcel(ctx context.Context, data [][]string) error {
 		return err
 	}
 
-	penMap := model.PenMap
+	penMap := s.PenMap2(ctx, userModel.AppPasture.Id)
 	if userModel.AppPasture.Id <= 0 {
 		return xerr.Custom("无效的牧场ID")
 	}
@@ -107,7 +109,7 @@ func (s *StoreEntry) ImportExcel(ctx context.Context, data [][]string) error {
 				ts.EarNumber = d
 			case 3:
 				if pn, ok := penMap[d]; ok {
-					ts.PenId = pn
+					ts.PenId = pn.Id
 					ts.PenName = d
 				}
 			case 4:
@@ -197,6 +199,202 @@ func (s *StoreEntry) ImportExcel(ctx context.Context, data [][]string) error {
 	return s.ExecExcelData(ctx, pastureId, eventEnterList)
 }
 
+func (s *StoreEntry) ImportExcel2(ctx context.Context, data [][]string, excelHeader []string) error {
+	// 获取当前用户信息
+	userModel, err := s.GetUserModel(ctx)
+	if err != nil {
+		return err
+	}
+
+	penMap := s.PenMap2(ctx, userModel.AppPasture.Id)
+	if userModel.AppPasture.Id <= 0 {
+		return xerr.Custom("无效的牧场ID")
+	}
+	// 处理Excel数据
+	//headers := data[0]
+	eventEnterList := make([]*pasturePb.EventEnterRequest, 0)
+	/*for _, row := range data[1:] {
+		if len(row) <= 0 {
+			continue
+		}
+		ts := &pasturePb.EventEnterRequest{
+			OperationId:   int32(userModel.SystemUser.Id),
+			OperationName: userModel.SystemUser.Name,
+			MessengerId:   int32(userModel.SystemUser.Id),
+			MessengerName: userModel.SystemUser.Name,
+		}
+		for j, d := range row {
+			switch j {
+			case 0:
+				continue
+			case 1:
+				continue
+			case 2:
+				ts.EarNumber = d
+			case 3:
+				if pn, ok := penMap[d]; ok {
+					ts.PenId = pn.Id
+					ts.PenName = pn.Name
+				}
+			case 4:
+				ts.Sex = pasturePb.Genders_Female
+				if d == "公" {
+					ts.Sex = pasturePb.Genders_Male
+				}
+			case 5:
+				if d == "成母牛" {
+					ts.CowType = pasturePb.CowType_Breeding_Calf
+				} else if d == "犊牛" {
+					ts.CowType = pasturePb.CowType_Lactating_Calf
+				} else if d == "青年牛" {
+					ts.CowType = pasturePb.CowType_Youth_Calf
+				} else if d == "育成牛" {
+					ts.CowType = pasturePb.CowType_Reserve_Calf
+				}
+			case 6:
+				continue
+			case 7:
+				bat, _ := util.TimeParseLocal(model.LayoutTime2, d)
+				if !bat.IsZero() {
+					ts.BirthAt = int32(bat.Local().Unix())
+				}
+			case 8:
+				lact, _ := strconv.Atoi(d)
+				ts.Lact = int32(lact)
+			case 9:
+				eat, _ := util.TimeParseLocal(model.LayoutTime2, d)
+				if !eat.IsZero() {
+					ts.EnterAt = int32(eat.Local().Unix())
+				}
+			case 10:
+				ts.FatherNumber = d
+			case 11:
+				ts.MotherNumber = d
+			case 12:
+				mat, _ := util.TimeParseLocal(model.LayoutTime2, d)
+				if !mat.IsZero() {
+					ts.MatingAt = int32(mat.Local().Unix())
+				}
+			case 13:
+				continue
+			case 14:
+				continue
+			case 15:
+				mt, _ := strconv.Atoi(d)
+				ts.MatingTimes = int32(mt)
+			case 16:
+				continue
+			case 17:
+				pat, _ := util.TimeParseLocal(model.LayoutTime2, d)
+				if !pat.IsZero() {
+					ts.PregnancyCheckAt = int32(pat.Local().Unix())
+				}
+			case 18:
+				continue
+			case 19:
+				continue
+			case 20:
+				cat, _ := util.TimeParseLocal(model.LayoutTime2, d)
+				if !cat.IsZero() {
+					ts.CalvingAt = int32(cat.Local().Unix())
+				}
+			case 21:
+				continue
+			case 22:
+				continue
+			case 23:
+				continue
+			case 24:
+				ts.CowKind = pasturePb.CowKind_AGSN
+			}
+		}
+		eventEnterList = append(eventEnterList, ts)
+	}*/
+	// 遍历数据行(跳过表头)
+	for _, row := range data[1:] {
+		if len(row) == 0 {
+			continue
+		}
+
+		ts := &pasturePb.EventEnterRequest{
+			OperationId:   int32(userModel.SystemUser.Id),
+			OperationName: userModel.SystemUser.Name,
+			MessengerId:   int32(userModel.SystemUser.Id),
+			MessengerName: userModel.SystemUser.Name,
+		}
+
+		// 使用反射动态匹配字段
+		val := reflect.ValueOf(ts).Elem()
+		typ := val.Type()
+
+		for i := 0; i < val.NumField(); i++ {
+			field := typ.Field(i)
+			fieldVal := val.Field(i)
+
+			// 获取字段的 excel 标签(如 excel:"耳标号")
+			excelTag := strings.ReplaceAll(field.Tag.Get("json"), ",omitempty", "")
+			if excelTag == "" {
+				continue // 没有 excel 标签的字段跳过
+			}
+
+			// 查找 excelHeader 中匹配的列索引
+			colIndex := -1
+			for j, colName := range excelHeader {
+				if colName == "" {
+					continue // 跳过空列名
+				}
+				if colName == excelTag {
+					colIndex = j
+					break
+				}
+			}
+
+			if colIndex == -1 || colIndex >= len(row) {
+				continue // 列名不匹配或数据越界
+			}
+
+			cellValue := row[colIndex]
+			if cellValue == "" {
+				continue // 空值跳过
+			}
+			// 根据字段类型设置值
+			switch fieldVal.Kind() {
+			case reflect.String:
+				fieldVal.SetString(cellValue)
+			case reflect.Int32:
+				if num, err := strconv.ParseInt(cellValue, 10, 32); err == nil {
+					fieldVal.SetInt(num)
+				}
+			case reflect.Struct: // 处理枚举或时间类型
+				switch field.Type {
+				case reflect.TypeOf(pasturePb.Genders_Female):
+					if cellValue == "公" {
+						fieldVal.Set(reflect.ValueOf(pasturePb.Genders_Male))
+					} else {
+						fieldVal.Set(reflect.ValueOf(pasturePb.Genders_Female))
+					}
+					// 添加其他自定义类型的处理...
+				}
+			}
+		}
+
+		// 特殊处理 PenId 和 PenName(依赖 penMap)
+		if ts.PenName != "" {
+			if pen, ok := penMap[ts.PenName]; ok {
+				ts.PenId = pen.Id
+			}
+		}
+
+		eventEnterList = append(eventEnterList, ts)
+	}
+	if len(eventEnterList) <= 0 {
+		return nil
+	}
+
+	return nil
+	return s.ExecExcelData(ctx, userModel.AppPasture.Id, eventEnterList)
+}
+
 func (s *StoreEntry) ExecExcelData(ctx context.Context, pastureId int64, dataList []*pasturePb.EventEnterRequest) error {
 	if len(dataList) <= 0 {
 		return nil

+ 2 - 2
module/crontab/cow_cron.go

@@ -424,11 +424,11 @@ func (e *Entry) SystemBasicCrontab() error {
 			pref.Where("day_age = ?", systemBasic.MinValue).
 				Where("NOT EXISTS (SELECT 1 FROM event_weaning WHERE event_weaning.cow_id = cow.id AND event_weaning.status = ?)", pasturePb.IsShow_No)
 		case model.PregnancyAge: // 产犊清单
-			pref.Where("pregnancy_age = ?", systemBasic.MinValue-10).
+			pref.Where("pregnancy_age BETWEEN ? AND ?", systemBasic.MinValue, systemBasic.MaxValue).
 				Where("breed_status = ?", pasturePb.BreedStatus_Pregnant).
 				Where("NOT EXISTS (SELECT 1 FROM event_calving WHERE event_calving.cow_id = cow.id AND event_calving.status = ?)", pasturePb.IsShow_No)
 		case model.DryMilkAge: // 干奶清单
-			pref.Where("pregnancy_age = ?", systemBasic.MinValue).
+			pref.Where("pregnancy_age BETWEEN ? AND ?", systemBasic.MinValue, systemBasic.MaxValue).
 				Where("breed_status = ?", pasturePb.BreedStatus_Pregnant).
 				Where("is_pregnant = ?", pasturePb.IsShow_Ok).
 				Where("NOT EXISTS (SELECT 1 FROM event_dry_milk WHERE event_dry_milk.cow_id = cow.id AND event_dry_milk.status = ?)", pasturePb.IsShow_No)

+ 133 - 35
module/crontab/health_warning.go

@@ -2,8 +2,12 @@ package crontab
 
 import (
 	"kpt-pasture/model"
+	"kpt-pasture/util"
+	"math"
 	"time"
 
+	pasturePb "gitee.com/xuyiping_admin/go_proto/proto/go/backend/cow"
+
 	"gitee.com/xuyiping_admin/pkg/xerr"
 
 	"gitee.com/xuyiping_admin/pkg/logger/zaplog"
@@ -22,9 +26,9 @@ func (e *Entry) HealthWarning(pastureId int64, processIds []int64) {
 	}
 
 	var (
-		lastCowID         int64
-		lastHeatDate      string
-		lastScore         int32
+		lastCowID         int64  = 0
+		lastHeatDate      string = "2001-01-01"
+		lastScore         int32  = 100
 		healthWarningList []*model.NeckRingHealth
 	)
 
@@ -63,17 +67,50 @@ func (e *Entry) HealthWarning(pastureId int64, processIds []int64) {
 
 		if isWorse == 1 {
 			newHealthWarning := model.NewNeckRingHealth(habit, sumChew, chew3dago)
-			if count := e.FindHealthWarning(pastureId, newHealthWarning); count <= 0 {
-				continue
-			}
 			healthWarningList = append(healthWarningList, newHealthWarning)
 		}
 	}
 	if len(healthWarningList) > 0 {
-		if err := e.DB.Create(&healthWarningList).Error; err != nil {
-			zaplog.Error("HealthWarning", zap.Any("error", err), zap.Any("healthWarningList", healthWarningList))
+		e.updateNeckRingHealth(pastureId, healthWarningList)
+	}
+}
+
+func (e *Entry) updateNeckRingHealth(pastureId int64, healthWarningList []*model.NeckRingHealth) {
+	zaplog.Info("HealthWarning", zap.Any("healthWarningList", healthWarningList))
+	for _, v := range healthWarningList {
+		startAt := util.TimeParseLocalUnix(v.HeatDate)
+		endAt := util.TimeParseLocalEndUnix(v.HeatDate)
+		isMove := e.isEventCowLog(pastureId, v.CowId, startAt, endAt, pasturePb.EventType_Transfer_Ben)
+		if isMove {
+			v.IsTransferGroup = pasturePb.IsShow_Ok
+		}
+		isDryMilk := e.isEventCowLog(pastureId, v.CowId, startAt, endAt, pasturePb.EventType_Dry_Milk)
+		if isDryMilk {
+			v.IsDryMilk = pasturePb.IsShow_Ok
 		}
+		isImmunization := e.isEventCowLog(pastureId, v.CowId, startAt, endAt, pasturePb.EventType_Immunication)
+		if isImmunization {
+			v.IsImmunization = pasturePb.IsShow_Ok
+		}
+	}
+
+	if err := e.DB.Model(new(model.NeckRingHealth)).Create(&healthWarningList).Error; err != nil {
+		zaplog.Error("HealthWarning", zap.Any("error", err), zap.Any("healthWarningList", healthWarningList))
+	}
+}
+
+func (e *Entry) isEventCowLog(pastureId int64, CowId int64, startAt, endAt int64, eventType pasturePb.EventType_Kind) bool {
+	var count int64
+	eventCowLog := &model.EventCowLog{CowId: CowId}
+	if err := e.DB.Table(eventCowLog.TableName()).
+		Where("pasture_id = ?", pastureId).
+		Where("cow_id = ?", CowId).
+		Where("event_at BETWEEN ? AND ?", startAt, endAt).
+		Where("event_type = ?", eventType).
+		Count(&count).Error; err != nil {
+		return false
 	}
+	return count > 0
 }
 
 func (e *Entry) NeckRingHealthWarning() error {
@@ -82,6 +119,11 @@ func (e *Entry) NeckRingHealthWarning() error {
 		return nil
 	}
 	for _, pasture := range pastureList {
+
+		e.DB.Model(new(model.NeckRingHealthWarning)).
+			Delete(new(model.NeckRingHealthWarning)).
+			Where("pasture_id = ?", pasture.Id)
+
 		if err := e.UpdateNeckRingHealth(pasture.Id); err != nil {
 			zaplog.Error("NeckRingHealthWarning", zap.Any("UpdateNeckRingHealth", err), zap.Any("pasture", pasture))
 		}
@@ -102,23 +144,82 @@ func (e *Entry) UpdateNeckRingHealth(pastureId int64) error {
 		healthValue = int32(v.Value)
 	}
 
+	newNeckRingHealthWarningList, err := e.FindNewNeckRingHealthWarning(pastureId, healthValue)
+	if err != nil {
+		return xerr.WithStack(err)
+	}
+
+	if len(newNeckRingHealthWarningList) > 0 {
+		if err = e.DB.Model(new(model.NeckRingHealthWarning)).
+			Create(&newNeckRingHealthWarningList).Error; err != nil {
+			zaplog.Error("UpdateNeckRingHealth",
+				zap.Any("error", err),
+				zap.Any("newNeckRingHealthWarningList", newNeckRingHealthWarningList))
+		}
+	}
+	return nil
+}
+
+func calculateNewScore(data *model.NeckRingHealth) int32 {
+	otherScore := int32(0)
+
+	otherScore += calculateMilkFilterScore(data.FilterMilk, data.MaxHigh)
+	if data.IsTransferGroup == pasturePb.IsShow_Ok {
+		otherScore += 3
+	}
+
+	if data.IsDryMilk == pasturePb.IsShow_Ok {
+		otherScore += 5
+	}
+
+	if data.IsImmunization == pasturePb.IsShow_Ok {
+		otherScore += 12
+	}
+	return data.Score + otherScore
+}
+
+func calculateMilkFilterScore(milkFilter int32, maxHigh int32) int32 {
+	// 处理NULL值,默认为0
+	milkFilterValue := int32(0)
+	if milkFilter != 0 {
+		milkFilterValue = milkFilter
+	}
+
+	// 计算系数:如果maxHigh>50则为0.5,否则为1
+	coefficient := 1.0
+	if maxHigh > 50 {
+		coefficient = 0.5
+	}
+
+	// 计算中间值:milkFilterValue * 0.3 * coefficient
+	intermediateValue := float64(milkFilterValue) * 0.3 * coefficient
+
+	// 四舍五入
+	roundedValue := math.Round(intermediateValue)
+
+	// 取最小值(roundedValue和0中的较小值)
+	result := int32(math.Min(roundedValue, 0))
+
+	return result
+}
+
+func (e *Entry) FindNewNeckRingHealthWarning(pastureId int64, healthValue int32) ([]*model.NeckRingHealthWarning, error) {
 	nowTime := time.Now().Local()
+	//endTime := nowTime.Format(model.LayoutDate2)
+	startTime := nowTime.AddDate(0, 0, -1).Format(model.LayoutDate2)
 	neckRingHealthList := make([]*model.NeckRingHealth, 0)
-	if err = e.DB.Model(new(model.NeckRingHealth)).
-		Select("MAX(id) AS id,neck_ring_number,cow_id,score,max_high,created_at,min_high,min_chew,min_intake,sum_chew,before_three_sum_chew").
+	if err := e.DB.Model(new(model.NeckRingHealth)).
+		Select(`MAX(id) AS id,heat_date,neck_ring_number,cow_id,score,max_high,created_at,min_high,min_chew,
+		min_intake,sum_chew,before_three_sum_chew`).
 		Where("pasture_id = ?", pastureId).
-		Where("heat_date >= ?", nowTime.AddDate(0, 0, -1).Format(model.LayoutDate2)).
+		Where("heat_date >= ?", startTime).
 		Group("neck_ring_number").
 		Find(&neckRingHealthList).Error; err != nil {
-		return xerr.WithStack(err)
+		return nil, xerr.WithStack(err)
 	}
 
 	newNeckRingHealthWarningList := make([]*model.NeckRingHealthWarning, 0)
 	for _, v := range neckRingHealthList {
-		newScore := calculateNewScore(v)
-		if newScore > healthValue {
-			continue
-		}
 		cowInfo, err := e.GetCowById(pastureId, v.CowId)
 		if err != nil {
 			continue
@@ -126,33 +227,30 @@ func (e *Entry) UpdateNeckRingHealth(pastureId int64) error {
 		if cowInfo == nil {
 			continue
 		}
+		newScore := calculateNewScore(v)
+		if newScore > healthValue {
+			continue
+		}
+
+		if e.HistoryNeckRingHealthWarning(pastureId, cowInfo.NeckRingNumber, v.HeatDate) {
+			continue
+		}
 
 		newNeckRingHealthWarning := model.NewNeckRingHealthWarning(pastureId, v, cowInfo, newScore)
 		newNeckRingHealthWarningList = append(newNeckRingHealthWarningList, newNeckRingHealthWarning)
 	}
-
-	if len(newNeckRingHealthWarningList) > 0 {
-		if err = e.DB.Model(new(model.NeckRingHealthWarning)).
-			Create(&newNeckRingHealthWarningList).Error; err != nil {
-			zaplog.Error("UpdateNeckRingHealth", zap.Any("error", err), zap.Any("newNeckRingHealthWarningList", newNeckRingHealthWarningList))
-		}
-	}
-	return nil
+	return newNeckRingHealthWarningList, nil
 }
 
-func (e *Entry) FindHealthWarning(pastureId int64, data *model.NeckRingHealth) int64 {
+func (e *Entry) HistoryNeckRingHealthWarning(pastureId int64, neckRingNumber string, heatDate string) bool {
 	var count int64
-	if err := e.DB.Model(new(model.NeckRingHealth)).
+	if err := e.DB.Model(new(model.NeckRingHealthWarning)).
 		Where("pasture_id = ?", pastureId).
-		Where("cow_id = ?", data.CowId).
-		Where("heat_date = ?", data.HeatDate).
-		Where("score = ?", data.Score).
+		Where("neck_ring_number = ?", neckRingNumber).
+		Where("heat_date = ?", heatDate).
+		Where("is_show = ?", pasturePb.IsShow_No).
 		Count(&count).Error; err != nil {
-		zaplog.Error("FindHealthWarning", zap.Any("error", err))
+		return false
 	}
-	return count
-}
-
-func calculateNewScore(data *model.NeckRingHealth) int32 {
-	return data.Score
+	return count > 0
 }

+ 3 - 0
module/crontab/interface.go

@@ -2,6 +2,7 @@ package crontab
 
 import (
 	"kpt-pasture/config"
+	"kpt-pasture/service/alert"
 	"kpt-pasture/service/asynqsvc"
 	"kpt-pasture/service/redis"
 	"kpt-pasture/store/kptstore"
@@ -18,6 +19,7 @@ type Entry struct {
 	DB          *kptstore.DB
 	AsynqClient asynqsvc.Client
 	Redis       *redis.CacheStoreRedisEntry
+	Alert       *alert.Alert
 }
 
 func NewCrontab(entry Entry) Crontab {
@@ -34,6 +36,7 @@ type Crontab interface {
 	SystemBasicCrontab() error
 	DeleteOldOriginal() error
 	UpdateDiseaseToCalendar() error
+	TwentyOnePregnantRate() error
 
 	// NeckRingOriginalMerge 脖环数据
 	NeckRingOriginalMerge() error // 合并脖环数据

+ 11 - 10
module/crontab/model.go

@@ -44,16 +44,17 @@ type EstrusIsPeakData struct {
 }
 
 type XToday struct {
-	LastMaxHabitId  int64
-	CurrMaxHabitId  int64
-	High            int32
-	Rumina          int32
-	ActiveLow       int32
-	ActiveMiddle    int32
-	ActiveHigh      int32
-	XRuminaDisc     int32
-	XChangeDiscount int32
-	WeeklyActive    int32
+	LastMaxHabitId    int64
+	CurrMaxHabitId    int64
+	High              int32
+	Rumina            int32
+	ActiveLow         int32
+	ActiveMiddle      int32
+	ActiveHigh        int32
+	XRuminaDisc       int32
+	XChangeDiscount   int32
+	WeeklyActive      int32
+	BeforeDayNeckRing int32
 }
 
 type FilterData struct {

+ 12 - 10
module/crontab/neck_ring_calculate.go

@@ -87,7 +87,7 @@ func (e *Entry) FirstFilterUpdate(pastureId int64, xToDay *XToday) (processIds [
 		limit = defaultLimit
 	}
 
-	firstHeatDate := time.Now().Local().AddDate(0, 0, -30).Format(model.LayoutDate2)
+	firstHeatDate := time.Now().Local().AddDate(0, 0, int(xToDay.BeforeDayNeckRing)*-1).Format(model.LayoutDate2)
 	querySql := `SELECT * FROM neck_active_habit WHERE pasture_id = ? AND is_show = ? AND heat_date >= ? AND high >= ?
 			UNION
 				 SELECT * FROM neck_active_habit WHERE pasture_id = ? AND is_show = ? AND heat_date >= ? AND rumina >= ?
@@ -306,6 +306,13 @@ func (e *Entry) FilterCorrectAndScoreUpdate(pastureId int64, processIds []int64,
 	}
 
 	for _, v := range neckActiveHabitList {
+		cowScore := calculateScore(v)
+		if err := e.DB.Model(new(model.NeckActiveHabit)).
+			Where("id = ?", v.Id).
+			Update("score", cowScore).Error; err != nil {
+			zaplog.Error("ActivityVolumeChanges-2", zap.Any("error", err), zap.Any("xToday", xToday))
+		}
+
 		activityVolume := &ActivityVolume{}
 		if err := e.DB.Model(new(model.NeckActiveHabit)).
 			Select("neck_ring_number", "AVG(IF(change_filter>=60, 60, change_filter)) as avg_filter",
@@ -318,9 +325,10 @@ func (e *Entry) FilterCorrectAndScoreUpdate(pastureId int64, processIds []int64,
 			Where("neck_ring_number = ?", v.NeckRingNumber).
 			Having("nb >= ?", DefaultNb).
 			First(&activityVolume).Error; err != nil {
-			zaplog.Error("ActivityVolumeChanges-0", zap.Any("error", err), zap.Any("xToday", xToday))
+			zaplog.Error("ActivityVolumeChanges-0", zap.Any("error", err), zap.Any("xToday", xToday), zap.Any("v", v))
 			continue
 		}
+
 		if activityVolume != nil && activityVolume.NeckRingNumber != "" {
 			//filterCorrect := model.DefaultFilterCorrect - int(math.Floor(activityVolume.AvgFilter/3+float64(activityVolume.StdFilter)/2))
 			filterCorrect := model.DefaultFilterCorrect - int(math.Round(activityVolume.AvgFilter/3+float64(int(math.Round(activityVolume.StdFilter))/2)))
@@ -333,14 +341,6 @@ func (e *Entry) FilterCorrectAndScoreUpdate(pastureId int64, processIds []int64,
 				continue
 			}
 		}
-
-		cowScore := calculateScore(v)
-		if err := e.DB.Model(new(model.NeckActiveHabit)).
-			Where("id = ?", v.Id).
-			Update("score", cowScore).Error; err != nil {
-			zaplog.Error("ActivityVolumeChanges-2", zap.Any("error", err), zap.Any("xToday", xToday))
-			continue
-		}
 	}
 }
 
@@ -460,6 +460,8 @@ func (e *Entry) XToday(pastureId int64) (*XToday, error) {
 			xToday.XChangeDiscount = int32(v.Value)
 		case model.WeeklyActive:
 			xToday.WeeklyActive = int32(v.Value)
+		case model.BeforeDayNeckRing:
+			xToday.BeforeDayNeckRing = int32(v.Value)
 		}
 	}
 	return xToday, nil

+ 0 - 3227
module/crontab/neck_ring_estus_test.go

@@ -11,3233 +11,6 @@ import (
 )
 
 func TestCalculateCFT(t *testing.T) {
-	/*neckActiveHabitList := make([]*model.NeckActiveHabit, 0)
-	str := `[
-	    {
-	        "id": 1725734,
-	        "pastureId": 1,
-	        "neckRingNumber": "10054",
-	        "cowId": 109,
-	        "lact": 3,
-	        "calvingAge": 166,
-	        "activeTime": "2025-02-25 01:00:00",
-	        "frameid": 0,
-	        "heatDate": "2025-02-25",
-	        "rumina": 34,
-	        "intake": 51,
-	        "inactive": 49,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 2119,
-	        "active": 81,
-	        "filterHigh": 43,
-	        "filterRumina": 16,
-	        "filterChew": 16,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 268,
-	        "weekRuminaHabit": 10,
-	        "weekIntakeHabit": 24,
-	        "weekChewHabit": 14,
-	        "weekInactiveHabit": 24,
-	        "weekOtherHabit": 0,
-	        "changeHigh": -19,
-	        "changeRumina": 60,
-	        "changeChew": 14,
-	        "changeAdjust": -19,
-	        "changeFilter": -6,
-	        "ruminaFilter": 18,
-	        "chewFilter": 4,
-	        "filterCorrect": 97,
-	        "sumRumina": 62,
-	        "sumIntake": 269,
-	        "sumInactive": 445,
-	        "sumActive": 659,
-	        "sumMinHigh": -10000,
-	        "sumMaxHigh": 18,
-	        "SumMinChew": 0,
-	        "beforeThreeSumRumina": 70,
-	        "beforeThreeSumIntake": 200,
-	        "score": 97,
-	        "isMaxTime": 2,
-	        "isShow": 2,
-	        "recordCount": 6,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740414165,
-	        "updatedAt": 1740466954
-	    },
-	    {
-	        "id": 1725740,
-	        "pastureId": 1,
-	        "neckRingNumber": "10055",
-	        "cowId": 110,
-	        "lact": 2,
-	        "calvingAge": 61,
-	        "activeTime": "2025-02-25 01:00:00",
-	        "frameid": 0,
-	        "heatDate": "2025-02-25",
-	        "rumina": 61,
-	        "intake": 8,
-	        "inactive": 48,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 1851,
-	        "active": 59,
-	        "filterHigh": 326,
-	        "filterRumina": 27,
-	        "filterChew": 35,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 744,
-	        "weekRuminaHabit": 16,
-	        "weekIntakeHabit": 19,
-	        "weekChewHabit": 23,
-	        "weekInactiveHabit": 19,
-	        "weekOtherHabit": 0,
-	        "changeHigh": -33,
-	        "changeRumina": 69,
-	        "changeChew": 52,
-	        "changeAdjust": 0,
-	        "changeFilter": -10,
-	        "ruminaFilter": 10,
-	        "chewFilter": 16,
-	        "filterCorrect": 95,
-	        "sumRumina": 120,
-	        "sumIntake": 235,
-	        "sumInactive": 605,
-	        "sumActive": 623,
-	        "sumMinHigh": -10000,
-	        "sumMaxHigh": 18,
-	        "SumMinChew": 0,
-	        "beforeThreeSumRumina": 105,
-	        "beforeThreeSumIntake": 272,
-	        "score": 96,
-	        "isMaxTime": 2,
-	        "isShow": 2,
-	        "recordCount": 6,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740415350,
-	        "updatedAt": 1740466954
-	    },
-	    {
-	        "id": 1725743,
-	        "pastureId": 1,
-	        "neckRingNumber": "10032",
-	        "cowId": 88,
-	        "lact": 0,
-	        "calvingAge": 0,
-	        "activeTime": "2025-02-25 01:00:00",
-	        "frameid": 0,
-	        "heatDate": "2025-02-25",
-	        "rumina": 5,
-	        "intake": 12,
-	        "inactive": 31,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 2273,
-	        "active": 86,
-	        "filterHigh": 513,
-	        "filterRumina": 3,
-	        "filterChew": 8,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 878,
-	        "weekRuminaHabit": 12,
-	        "weekIntakeHabit": 29,
-	        "weekChewHabit": 22,
-	        "weekInactiveHabit": 29,
-	        "weekOtherHabit": 0,
-	        "changeHigh": -28,
-	        "changeRumina": -75,
-	        "changeChew": -64,
-	        "changeAdjust": 0,
-	        "changeFilter": -7,
-	        "ruminaFilter": -9,
-	        "chewFilter": -10,
-	        "filterCorrect": 97,
-	        "sumRumina": 61,
-	        "sumIntake": 220,
-	        "sumInactive": 632,
-	        "sumActive": 504,
-	        "sumMinHigh": -10000,
-	        "sumMaxHigh": 11,
-	        "SumMinChew": 0,
-	        "beforeThreeSumRumina": 140,
-	        "beforeThreeSumIntake": 206,
-	        "score": 97,
-	        "isMaxTime": 2,
-	        "isShow": 2,
-	        "recordCount": 6,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740415395,
-	        "updatedAt": 1740466954
-	    },
-	    {
-	        "id": 1725746,
-	        "pastureId": 1,
-	        "neckRingNumber": "10028",
-	        "cowId": 84,
-	        "lact": 2,
-	        "calvingAge": 299,
-	        "activeTime": "2025-02-25 01:00:00",
-	        "frameid": 0,
-	        "heatDate": "2025-02-25",
-	        "rumina": 7,
-	        "intake": 23,
-	        "inactive": 11,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 3126,
-	        "active": 109,
-	        "filterHigh": 1004,
-	        "filterRumina": 9,
-	        "filterChew": 24,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 802,
-	        "weekRuminaHabit": 8,
-	        "weekIntakeHabit": 12,
-	        "weekChewHabit": 18,
-	        "weekInactiveHabit": 12,
-	        "weekOtherHabit": 0,
-	        "changeHigh": 16,
-	        "changeRumina": 13,
-	        "changeChew": 33,
-	        "changeAdjust": 0,
-	        "changeFilter": 5,
-	        "ruminaFilter": 4,
-	        "chewFilter": 10,
-	        "filterCorrect": 95,
-	        "sumRumina": 123,
-	        "sumIntake": 271,
-	        "sumInactive": 563,
-	        "sumActive": 569,
-	        "sumMinHigh": -10000,
-	        "sumMaxHigh": 15,
-	        "SumMinChew": 7,
-	        "beforeThreeSumRumina": 175,
-	        "beforeThreeSumIntake": 275,
-	        "score": 100,
-	        "isMaxTime": 2,
-	        "isShow": 2,
-	        "recordCount": 6,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740415655,
-	        "updatedAt": 1740466954
-	    },
-	    {
-	        "id": 1725748,
-	        "pastureId": 1,
-	        "neckRingNumber": "10030",
-	        "cowId": 86,
-	        "lact": 2,
-	        "calvingAge": 299,
-	        "activeTime": "2025-02-25 01:00:00",
-	        "frameid": 0,
-	        "heatDate": "2025-02-25",
-	        "rumina": 38,
-	        "intake": 13,
-	        "inactive": 33,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 2514,
-	        "active": 81,
-	        "filterHigh": 270,
-	        "filterRumina": 18,
-	        "filterChew": 22,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 336,
-	        "weekRuminaHabit": 20,
-	        "weekIntakeHabit": 17,
-	        "weekChewHabit": 27,
-	        "weekInactiveHabit": 17,
-	        "weekOtherHabit": 0,
-	        "changeHigh": -6,
-	        "changeRumina": -10,
-	        "changeChew": -19,
-	        "changeAdjust": 0,
-	        "changeFilter": -2,
-	        "ruminaFilter": -3,
-	        "chewFilter": -6,
-	        "filterCorrect": 97,
-	        "sumRumina": 159,
-	        "sumIntake": 254,
-	        "sumInactive": 637,
-	        "sumActive": 587,
-	        "sumMinHigh": -10000,
-	        "sumMaxHigh": 18,
-	        "SumMinChew": 3,
-	        "beforeThreeSumRumina": 139,
-	        "beforeThreeSumIntake": 251,
-	        "score": 99,
-	        "isMaxTime": 2,
-	        "isShow": 2,
-	        "recordCount": 6,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740415655,
-	        "updatedAt": 1740466954
-	    },
-	    {
-	        "id": 1725749,
-	        "pastureId": 1,
-	        "neckRingNumber": "10038",
-	        "cowId": 94,
-	        "lact": 0,
-	        "calvingAge": 0,
-	        "activeTime": "2025-02-25 01:00:00",
-	        "frameid": 0,
-	        "heatDate": "2025-02-25",
-	        "rumina": 0,
-	        "intake": 0,
-	        "inactive": 41,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 76,
-	        "active": 3,
-	        "filterHigh": 28,
-	        "filterRumina": 1,
-	        "filterChew": 1,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 430,
-	        "weekRuminaHabit": 9,
-	        "weekIntakeHabit": 25,
-	        "weekChewHabit": 12,
-	        "weekInactiveHabit": 25,
-	        "weekOtherHabit": 0,
-	        "changeHigh": -34,
-	        "changeRumina": -89,
-	        "changeChew": -92,
-	        "changeAdjust": 0,
-	        "changeFilter": 0,
-	        "ruminaFilter": 0,
-	        "chewFilter": 0,
-	        "filterCorrect": 98,
-	        "sumRumina": 11,
-	        "sumIntake": 0,
-	        "sumInactive": 432,
-	        "sumActive": 153,
-	        "sumMinHigh": -7,
-	        "sumMaxHigh": 1,
-	        "SumMinChew": 0,
-	        "beforeThreeSumRumina": 58,
-	        "beforeThreeSumIntake": 252,
-	        "score": 68,
-	        "isMaxTime": 2,
-	        "isShow": 2,
-	        "recordCount": 6,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740415660,
-	        "updatedAt": 1740466954
-	    },
-	    {
-	        "id": 1725756,
-	        "pastureId": 1,
-	        "neckRingNumber": "10053",
-	        "cowId": 108,
-	        "lact": 0,
-	        "calvingAge": 0,
-	        "activeTime": "2025-02-25 01:00:00",
-	        "frameid": 0,
-	        "heatDate": "2025-02-25",
-	        "rumina": 25,
-	        "intake": 17,
-	        "inactive": 51,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 1263,
-	        "active": 54,
-	        "filterHigh": 318,
-	        "filterRumina": 8,
-	        "filterChew": 19,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 511,
-	        "weekRuminaHabit": 15,
-	        "weekIntakeHabit": 21,
-	        "weekChewHabit": 29,
-	        "weekInactiveHabit": 21,
-	        "weekOtherHabit": 0,
-	        "changeHigh": -16,
-	        "changeRumina": -47,
-	        "changeChew": -34,
-	        "changeAdjust": 0,
-	        "changeFilter": -4,
-	        "ruminaFilter": -11,
-	        "chewFilter": -10,
-	        "filterCorrect": 96,
-	        "sumRumina": 140,
-	        "sumIntake": 293,
-	        "sumInactive": 709,
-	        "sumActive": 578,
-	        "sumMinHigh": -10000,
-	        "sumMaxHigh": 19,
-	        "SumMinChew": 10,
-	        "beforeThreeSumRumina": 183,
-	        "beforeThreeSumIntake": 266,
-	        "score": 98,
-	        "isMaxTime": 2,
-	        "isShow": 2,
-	        "recordCount": 6,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740416500,
-	        "updatedAt": 1740466954
-	    },
-	    {
-	        "id": 1725759,
-	        "pastureId": 1,
-	        "neckRingNumber": "10027",
-	        "cowId": 30,
-	        "lact": 0,
-	        "calvingAge": 0,
-	        "activeTime": "2025-02-25 01:00:00",
-	        "frameid": 0,
-	        "heatDate": "2025-02-25",
-	        "rumina": 23,
-	        "intake": 43,
-	        "inactive": 5,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 2761,
-	        "active": 100,
-	        "filterHigh": 1279,
-	        "filterRumina": 10,
-	        "filterChew": 20,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 1121,
-	        "weekRuminaHabit": 8,
-	        "weekIntakeHabit": 30,
-	        "weekChewHabit": 16,
-	        "weekInactiveHabit": 30,
-	        "weekOtherHabit": 0,
-	        "changeHigh": 12,
-	        "changeRumina": 25,
-	        "changeChew": 25,
-	        "changeAdjust": 0,
-	        "changeFilter": 3,
-	        "ruminaFilter": 6,
-	        "chewFilter": 8,
-	        "filterCorrect": 94,
-	        "sumRumina": 121,
-	        "sumIntake": 268,
-	        "sumInactive": 644,
-	        "sumActive": 621,
-	        "sumMinHigh": -10000,
-	        "sumMaxHigh": 20,
-	        "SumMinChew": 5,
-	        "beforeThreeSumRumina": 121,
-	        "beforeThreeSumIntake": 205,
-	        "score": 100,
-	        "isMaxTime": 2,
-	        "isShow": 2,
-	        "recordCount": 6,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740416525,
-	        "updatedAt": 1740466955
-	    },
-	    {
-	        "id": 1725764,
-	        "pastureId": 1,
-	        "neckRingNumber": "10054",
-	        "cowId": 109,
-	        "lact": 3,
-	        "calvingAge": 167,
-	        "activeTime": "2025-02-25 03:00:00",
-	        "frameid": 1,
-	        "heatDate": "2025-02-25",
-	        "rumina": 36,
-	        "intake": 20,
-	        "inactive": 20,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 2019,
-	        "active": 77,
-	        "filterHigh": 318,
-	        "filterRumina": 7,
-	        "filterChew": 8,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 356,
-	        "weekRuminaHabit": 5,
-	        "weekIntakeHabit": 20,
-	        "weekChewHabit": 10,
-	        "weekInactiveHabit": 20,
-	        "weekOtherHabit": 0,
-	        "changeHigh": -3,
-	        "changeRumina": 40,
-	        "changeChew": -20,
-	        "changeAdjust": 0,
-	        "changeFilter": -1,
-	        "ruminaFilter": 12,
-	        "chewFilter": -6,
-	        "filterCorrect": 97,
-	        "sumRumina": 69,
-	        "sumIntake": 303,
-	        "sumInactive": 517,
-	        "sumActive": 674,
-	        "sumMinHigh": -10000,
-	        "sumMaxHigh": 18,
-	        "SumMinChew": 0,
-	        "beforeThreeSumRumina": 71,
-	        "beforeThreeSumIntake": 241,
-	        "score": 99,
-	        "isMaxTime": 2,
-	        "isShow": 2,
-	        "recordCount": 6,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740421320,
-	        "updatedAt": 1740466955
-	    },
-	    {
-	        "id": 1725771,
-	        "pastureId": 1,
-	        "neckRingNumber": "10055",
-	        "cowId": 110,
-	        "lact": 2,
-	        "calvingAge": 62,
-	        "activeTime": "2025-02-25 03:00:00",
-	        "frameid": 1,
-	        "heatDate": "2025-02-25",
-	        "rumina": 4,
-	        "intake": 31,
-	        "inactive": 46,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 2875,
-	        "active": 73,
-	        "filterHigh": 1212,
-	        "filterRumina": 0,
-	        "filterChew": 12,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 1042,
-	        "weekRuminaHabit": 2,
-	        "weekIntakeHabit": 32,
-	        "weekChewHabit": 18,
-	        "weekInactiveHabit": 32,
-	        "weekOtherHabit": 0,
-	        "changeHigh": 13,
-	        "changeRumina": -100,
-	        "changeChew": -33,
-	        "changeAdjust": 0,
-	        "changeFilter": 4,
-	        "ruminaFilter": -15,
-	        "chewFilter": -10,
-	        "filterCorrect": 95,
-	        "sumRumina": 120,
-	        "sumIntake": 237,
-	        "sumInactive": 567,
-	        "sumActive": 666,
-	        "sumMinHigh": -10000,
-	        "sumMaxHigh": 18,
-	        "SumMinChew": 0,
-	        "beforeThreeSumRumina": 102,
-	        "beforeThreeSumIntake": 253,
-	        "score": 100,
-	        "isMaxTime": 2,
-	        "isShow": 2,
-	        "recordCount": 6,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740422555,
-	        "updatedAt": 1740466955
-	    },
-	    {
-	        "id": 1725774,
-	        "pastureId": 1,
-	        "neckRingNumber": "10028",
-	        "cowId": 84,
-	        "lact": 2,
-	        "calvingAge": 300,
-	        "activeTime": "2025-02-25 03:00:00",
-	        "frameid": 1,
-	        "heatDate": "2025-02-25",
-	        "rumina": 65,
-	        "intake": 16,
-	        "inactive": 66,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 1436,
-	        "active": 50,
-	        "filterHigh": 382,
-	        "filterRumina": 17,
-	        "filterChew": 21,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 138,
-	        "weekRuminaHabit": 13,
-	        "weekIntakeHabit": 8,
-	        "weekChewHabit": 10,
-	        "weekInactiveHabit": 8,
-	        "weekOtherHabit": 0,
-	        "changeHigh": 21,
-	        "changeRumina": 31,
-	        "changeChew": 110,
-	        "changeAdjust": 0,
-	        "changeFilter": 6,
-	        "ruminaFilter": 9,
-	        "chewFilter": 16,
-	        "filterCorrect": 95,
-	        "sumRumina": 131,
-	        "sumIntake": 277,
-	        "sumInactive": 566,
-	        "sumActive": 655,
-	        "sumMinHigh": -10000,
-	        "sumMaxHigh": 15,
-	        "SumMinChew": 7,
-	        "beforeThreeSumRumina": 193,
-	        "beforeThreeSumIntake": 290,
-	        "score": 100,
-	        "isMaxTime": 2,
-	        "isShow": 2,
-	        "recordCount": 6,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740422555,
-	        "updatedAt": 1740466955
-	    },
-	    {
-	        "id": 1725778,
-	        "pastureId": 1,
-	        "neckRingNumber": "10032",
-	        "cowId": 88,
-	        "lact": 0,
-	        "calvingAge": 0,
-	        "activeTime": "2025-02-25 03:00:00",
-	        "frameid": 1,
-	        "heatDate": "2025-02-25",
-	        "rumina": 0,
-	        "intake": 46,
-	        "inactive": 49,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 1726,
-	        "active": 55,
-	        "filterHigh": 1027,
-	        "filterRumina": 0,
-	        "filterChew": 25,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 689,
-	        "weekRuminaHabit": 9,
-	        "weekIntakeHabit": 27,
-	        "weekChewHabit": 21,
-	        "weekInactiveHabit": 27,
-	        "weekOtherHabit": 0,
-	        "changeHigh": 27,
-	        "changeRumina": -100,
-	        "changeChew": 19,
-	        "changeAdjust": 0,
-	        "changeFilter": 6,
-	        "ruminaFilter": -12,
-	        "chewFilter": 6,
-	        "filterCorrect": 97,
-	        "sumRumina": 56,
-	        "sumIntake": 242,
-	        "sumInactive": 576,
-	        "sumActive": 587,
-	        "sumMinHigh": -10000,
-	        "sumMaxHigh": 11,
-	        "SumMinChew": 0,
-	        "beforeThreeSumRumina": 136,
-	        "beforeThreeSumIntake": 224,
-	        "score": 100,
-	        "isMaxTime": 2,
-	        "isShow": 2,
-	        "recordCount": 6,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740422595,
-	        "updatedAt": 1740466955
-	    },
-	    {
-	        "id": 1725782,
-	        "pastureId": 1,
-	        "neckRingNumber": "10030",
-	        "cowId": 86,
-	        "lact": 2,
-	        "calvingAge": 300,
-	        "activeTime": "2025-02-25 03:00:00",
-	        "frameid": 1,
-	        "heatDate": "2025-02-25",
-	        "rumina": 27,
-	        "intake": 64,
-	        "inactive": 12,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 2781,
-	        "active": 96,
-	        "filterHigh": 592,
-	        "filterRumina": 17,
-	        "filterChew": 21,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 807,
-	        "weekRuminaHabit": 7,
-	        "weekIntakeHabit": 37,
-	        "weekChewHabit": 21,
-	        "weekInactiveHabit": 37,
-	        "weekOtherHabit": 0,
-	        "changeHigh": -17,
-	        "changeRumina": 143,
-	        "changeChew": 0,
-	        "changeAdjust": 0,
-	        "changeFilter": -5,
-	        "ruminaFilter": 21,
-	        "chewFilter": 0,
-	        "filterCorrect": 97,
-	        "sumRumina": 176,
-	        "sumIntake": 243,
-	        "sumInactive": 659,
-	        "sumActive": 642,
-	        "sumMinHigh": -10000,
-	        "sumMaxHigh": 18,
-	        "SumMinChew": 3,
-	        "beforeThreeSumRumina": 130,
-	        "beforeThreeSumIntake": 265,
-	        "score": 98,
-	        "isMaxTime": 2,
-	        "isShow": 2,
-	        "recordCount": 6,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740422850,
-	        "updatedAt": 1740466955
-	    },
-	    {
-	        "id": 1725784,
-	        "pastureId": 1,
-	        "neckRingNumber": "10038",
-	        "cowId": 94,
-	        "lact": 0,
-	        "calvingAge": 0,
-	        "activeTime": "2025-02-25 03:00:00",
-	        "frameid": 1,
-	        "heatDate": "2025-02-25",
-	        "rumina": 1,
-	        "intake": 0,
-	        "inactive": 43,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 266,
-	        "active": 11,
-	        "filterHigh": 24,
-	        "filterRumina": 0,
-	        "filterChew": 0,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 145,
-	        "weekRuminaHabit": 4,
-	        "weekIntakeHabit": 6,
-	        "weekChewHabit": 9,
-	        "weekInactiveHabit": 6,
-	        "weekOtherHabit": 0,
-	        "changeHigh": -11,
-	        "changeRumina": -100,
-	        "changeChew": -100,
-	        "changeAdjust": 0,
-	        "changeFilter": -3,
-	        "ruminaFilter": -12,
-	        "chewFilter": -15,
-	        "filterCorrect": 98,
-	        "sumRumina": 11,
-	        "sumIntake": 0,
-	        "sumInactive": 513,
-	        "sumActive": 149,
-	        "sumMinHigh": -10000,
-	        "sumMaxHigh": 1,
-	        "SumMinChew": 0,
-	        "beforeThreeSumRumina": 0,
-	        "beforeThreeSumIntake": 0,
-	        "score": 68,
-	        "isMaxTime": 2,
-	        "isShow": 2,
-	        "recordCount": 6,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740422915,
-	        "updatedAt": 1740466955
-	    },
-	    {
-	        "id": 1725786,
-	        "pastureId": 1,
-	        "neckRingNumber": "10053",
-	        "cowId": 108,
-	        "lact": 0,
-	        "calvingAge": 0,
-	        "activeTime": "2025-02-25 03:00:00",
-	        "frameid": 1,
-	        "heatDate": "2025-02-25",
-	        "rumina": 50,
-	        "intake": 3,
-	        "inactive": 96,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 763,
-	        "active": 28,
-	        "filterHigh": 532,
-	        "filterRumina": 14,
-	        "filterChew": 16,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 471,
-	        "weekRuminaHabit": 13,
-	        "weekIntakeHabit": 19,
-	        "weekChewHabit": 24,
-	        "weekInactiveHabit": 19,
-	        "weekOtherHabit": 0,
-	        "changeHigh": 5,
-	        "changeRumina": 8,
-	        "changeChew": -33,
-	        "changeAdjust": 0,
-	        "changeFilter": 1,
-	        "ruminaFilter": 2,
-	        "chewFilter": -10,
-	        "filterCorrect": 96,
-	        "sumRumina": 140,
-	        "sumIntake": 272,
-	        "sumInactive": 734,
-	        "sumActive": 606,
-	        "sumMinHigh": -10000,
-	        "sumMaxHigh": 19,
-	        "SumMinChew": 10,
-	        "beforeThreeSumRumina": 181,
-	        "beforeThreeSumIntake": 294,
-	        "score": 100,
-	        "isMaxTime": 2,
-	        "isShow": 2,
-	        "recordCount": 6,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740423705,
-	        "updatedAt": 1740466955
-	    },
-	    {
-	        "id": 1725789,
-	        "pastureId": 1,
-	        "neckRingNumber": "10027",
-	        "cowId": 30,
-	        "lact": 0,
-	        "calvingAge": 0,
-	        "activeTime": "2025-02-25 03:00:00",
-	        "frameid": 1,
-	        "heatDate": "2025-02-25",
-	        "rumina": 45,
-	        "intake": 33,
-	        "inactive": 2,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 1855,
-	        "active": 66,
-	        "filterHigh": 1145,
-	        "filterRumina": 11,
-	        "filterChew": 31,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 499,
-	        "weekRuminaHabit": 7,
-	        "weekIntakeHabit": 23,
-	        "weekChewHabit": 14,
-	        "weekInactiveHabit": 23,
-	        "weekOtherHabit": 0,
-	        "changeHigh": 53,
-	        "changeRumina": 57,
-	        "changeChew": 121,
-	        "changeAdjust": 0,
-	        "changeFilter": 13,
-	        "ruminaFilter": 14,
-	        "chewFilter": 18,
-	        "filterCorrect": 94,
-	        "sumRumina": 132,
-	        "sumIntake": 328,
-	        "sumInactive": 631,
-	        "sumActive": 688,
-	        "sumMinHigh": -10000,
-	        "sumMaxHigh": 20,
-	        "SumMinChew": 5,
-	        "beforeThreeSumRumina": 120,
-	        "beforeThreeSumIntake": 265,
-	        "score": 100,
-	        "isMaxTime": 2,
-	        "isShow": 2,
-	        "recordCount": 6,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740423730,
-	        "updatedAt": 1740466955
-	    },
-	    {
-	        "id": 1725794,
-	        "pastureId": 1,
-	        "neckRingNumber": "10054",
-	        "cowId": 109,
-	        "lact": 3,
-	        "calvingAge": 167,
-	        "activeTime": "2025-02-25 05:00:00",
-	        "frameid": 2,
-	        "heatDate": "2025-02-25",
-	        "rumina": 41,
-	        "intake": 11,
-	        "inactive": 106,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 485,
-	        "active": 18,
-	        "filterHigh": 327,
-	        "filterRumina": 1,
-	        "filterChew": 9,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 143,
-	        "weekRuminaHabit": 7,
-	        "weekIntakeHabit": 5,
-	        "weekChewHabit": 7,
-	        "weekInactiveHabit": 5,
-	        "weekOtherHabit": 0,
-	        "changeHigh": 16,
-	        "changeRumina": -86,
-	        "changeChew": 29,
-	        "changeAdjust": 0,
-	        "changeFilter": 5,
-	        "ruminaFilter": -13,
-	        "chewFilter": 9,
-	        "filterCorrect": 97,
-	        "sumRumina": 57,
-	        "sumIntake": 333,
-	        "sumInactive": 521,
-	        "sumActive": 738,
-	        "sumMinHigh": -10000,
-	        "sumMaxHigh": 18,
-	        "SumMinChew": 0,
-	        "beforeThreeSumRumina": 62,
-	        "beforeThreeSumIntake": 241,
-	        "score": 100,
-	        "isMaxTime": 2,
-	        "isShow": 2,
-	        "recordCount": 6,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740428520,
-	        "updatedAt": 1740466955
-	    },
-	    {
-	        "id": 1725801,
-	        "pastureId": 1,
-	        "neckRingNumber": "10030",
-	        "cowId": 86,
-	        "lact": 2,
-	        "calvingAge": 300,
-	        "activeTime": "2025-02-25 05:00:00",
-	        "frameid": 2,
-	        "heatDate": "2025-02-25",
-	        "rumina": 65,
-	        "intake": 0,
-	        "inactive": 116,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 160,
-	        "active": 6,
-	        "filterHigh": 29,
-	        "filterRumina": 9,
-	        "filterChew": 9,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 22,
-	        "weekRuminaHabit": 18,
-	        "weekIntakeHabit": 1,
-	        "weekChewHabit": 18,
-	        "weekInactiveHabit": 1,
-	        "weekOtherHabit": 0,
-	        "changeHigh": 1,
-	        "changeRumina": -50,
-	        "changeChew": -50,
-	        "changeAdjust": 0,
-	        "changeFilter": 0,
-	        "ruminaFilter": -15,
-	        "chewFilter": -15,
-	        "filterCorrect": 97,
-	        "sumRumina": 182,
-	        "sumIntake": 300,
-	        "sumInactive": 638,
-	        "sumActive": 698,
-	        "sumMinHigh": -10000,
-	        "sumMaxHigh": 18,
-	        "SumMinChew": 5,
-	        "beforeThreeSumRumina": 142,
-	        "beforeThreeSumIntake": 291,
-	        "score": 100,
-	        "isMaxTime": 2,
-	        "isShow": 2,
-	        "recordCount": 6,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740429745,
-	        "updatedAt": 1740466955
-	    },
-	    {
-	        "id": 1725802,
-	        "pastureId": 1,
-	        "neckRingNumber": "10028",
-	        "cowId": 84,
-	        "lact": 2,
-	        "calvingAge": 300,
-	        "activeTime": "2025-02-25 05:00:00",
-	        "frameid": 2,
-	        "heatDate": "2025-02-25",
-	        "rumina": 36,
-	        "intake": 0,
-	        "inactive": 115,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 199,
-	        "active": 7,
-	        "filterHigh": 31,
-	        "filterRumina": 0,
-	        "filterChew": 0,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 407,
-	        "weekRuminaHabit": 5,
-	        "weekIntakeHabit": 32,
-	        "weekChewHabit": 14,
-	        "weekInactiveHabit": 32,
-	        "weekOtherHabit": 0,
-	        "changeHigh": -32,
-	        "changeRumina": -100,
-	        "changeChew": -100,
-	        "changeAdjust": 0,
-	        "changeFilter": -10,
-	        "ruminaFilter": -15,
-	        "chewFilter": -15,
-	        "filterCorrect": 95,
-	        "sumRumina": 108,
-	        "sumIntake": 285,
-	        "sumInactive": 583,
-	        "sumActive": 688,
-	        "sumMinHigh": -10000,
-	        "sumMaxHigh": 15,
-	        "SumMinChew": 0,
-	        "beforeThreeSumRumina": 190,
-	        "beforeThreeSumIntake": 220,
-	        "score": 96,
-	        "isMaxTime": 2,
-	        "isShow": 2,
-	        "recordCount": 6,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740429750,
-	        "updatedAt": 1740466955
-	    },
-	    {
-	        "id": 1725805,
-	        "pastureId": 1,
-	        "neckRingNumber": "10055",
-	        "cowId": 110,
-	        "lact": 2,
-	        "calvingAge": 62,
-	        "activeTime": "2025-02-25 05:00:00",
-	        "frameid": 2,
-	        "heatDate": "2025-02-25",
-	        "rumina": 92,
-	        "intake": 0,
-	        "inactive": 108,
-	        "gasp": 1,
-	        "other": 0,
-	        "high": 260,
-	        "active": 14,
-	        "filterHigh": 41,
-	        "filterRumina": 24,
-	        "filterChew": 24,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 39,
-	        "weekRuminaHabit": 18,
-	        "weekIntakeHabit": 0,
-	        "weekChewHabit": 18,
-	        "weekInactiveHabit": 0,
-	        "weekOtherHabit": 0,
-	        "changeHigh": 0,
-	        "changeRumina": 33,
-	        "changeChew": 33,
-	        "changeAdjust": 0,
-	        "changeFilter": 0,
-	        "ruminaFilter": 10,
-	        "chewFilter": 10,
-	        "filterCorrect": 95,
-	        "sumRumina": 134,
-	        "sumIntake": 251,
-	        "sumInactive": 533,
-	        "sumActive": 695,
-	        "sumMinHigh": -10000,
-	        "sumMaxHigh": 18,
-	        "SumMinChew": 0,
-	        "beforeThreeSumRumina": 102,
-	        "beforeThreeSumIntake": 260,
-	        "score": 100,
-	        "isMaxTime": 2,
-	        "isShow": 2,
-	        "recordCount": 6,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740429755,
-	        "updatedAt": 1740466955
-	    },
-	    {
-	        "id": 1725807,
-	        "pastureId": 1,
-	        "neckRingNumber": "10038",
-	        "cowId": 94,
-	        "lact": 0,
-	        "calvingAge": 0,
-	        "activeTime": "2025-02-25 05:00:00",
-	        "frameid": 2,
-	        "heatDate": "2025-02-25",
-	        "rumina": 0,
-	        "intake": 0,
-	        "inactive": 18,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 230,
-	        "active": 9,
-	        "filterHigh": 162,
-	        "filterRumina": 0,
-	        "filterChew": 0,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 23,
-	        "weekRuminaHabit": 8,
-	        "weekIntakeHabit": 0,
-	        "weekChewHabit": 8,
-	        "weekInactiveHabit": 0,
-	        "weekOtherHabit": 0,
-	        "changeHigh": 12,
-	        "changeRumina": -100,
-	        "changeChew": -100,
-	        "changeAdjust": 0,
-	        "changeFilter": 3,
-	        "ruminaFilter": -12,
-	        "chewFilter": -15,
-	        "filterCorrect": 98,
-	        "sumRumina": 11,
-	        "sumIntake": 0,
-	        "sumInactive": 515,
-	        "sumActive": 162,
-	        "sumMinHigh": -10000,
-	        "sumMaxHigh": 1,
-	        "SumMinChew": 0,
-	        "beforeThreeSumRumina": 31,
-	        "beforeThreeSumIntake": 240,
-	        "score": 70,
-	        "isMaxTime": 2,
-	        "isShow": 2,
-	        "recordCount": 6,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740429780,
-	        "updatedAt": 1740466955
-	    },
-	    {
-	        "id": 1725810,
-	        "pastureId": 1,
-	        "neckRingNumber": "10032",
-	        "cowId": 88,
-	        "lact": 0,
-	        "calvingAge": 0,
-	        "activeTime": "2025-02-25 05:00:00",
-	        "frameid": 2,
-	        "heatDate": "2025-02-25",
-	        "rumina": 59,
-	        "intake": 0,
-	        "inactive": 104,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 370,
-	        "active": 11,
-	        "filterHigh": 149,
-	        "filterRumina": 9,
-	        "filterChew": 9,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 123,
-	        "weekRuminaHabit": 12,
-	        "weekIntakeHabit": 16,
-	        "weekChewHabit": 14,
-	        "weekInactiveHabit": 16,
-	        "weekOtherHabit": 0,
-	        "changeHigh": 2,
-	        "changeRumina": -25,
-	        "changeChew": -36,
-	        "changeAdjust": 0,
-	        "changeFilter": 0,
-	        "ruminaFilter": -6,
-	        "chewFilter": -11,
-	        "filterCorrect": 97,
-	        "sumRumina": 47,
-	        "sumIntake": 227,
-	        "sumInactive": 578,
-	        "sumActive": 572,
-	        "sumMinHigh": -10000,
-	        "sumMaxHigh": 11,
-	        "SumMinChew": 0,
-	        "beforeThreeSumRumina": 138,
-	        "beforeThreeSumIntake": 211,
-	        "score": 90,
-	        "isMaxTime": 2,
-	        "isShow": 2,
-	        "recordCount": 6,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740429795,
-	        "updatedAt": 1740466956
-	    },
-	    {
-	        "id": 1725815,
-	        "pastureId": 1,
-	        "neckRingNumber": "10053",
-	        "cowId": 108,
-	        "lact": 0,
-	        "calvingAge": 0,
-	        "activeTime": "2025-02-25 05:00:00",
-	        "frameid": 2,
-	        "heatDate": "2025-02-25",
-	        "rumina": 45,
-	        "intake": 48,
-	        "inactive": 54,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 1908,
-	        "active": 69,
-	        "filterHigh": 148,
-	        "filterRumina": 26,
-	        "filterChew": 26,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 191,
-	        "weekRuminaHabit": 15,
-	        "weekIntakeHabit": 28,
-	        "weekChewHabit": 20,
-	        "weekInactiveHabit": 28,
-	        "weekOtherHabit": 0,
-	        "changeHigh": -4,
-	        "changeRumina": 73,
-	        "changeChew": 30,
-	        "changeAdjust": 0,
-	        "changeFilter": -1,
-	        "ruminaFilter": 9,
-	        "chewFilter": 9,
-	        "filterCorrect": 96,
-	        "sumRumina": 154,
-	        "sumIntake": 272,
-	        "sumInactive": 740,
-	        "sumActive": 611,
-	        "sumMinHigh": -10000,
-	        "sumMaxHigh": 19,
-	        "SumMinChew": 10,
-	        "beforeThreeSumRumina": 179,
-	        "beforeThreeSumIntake": 247,
-	        "score": 99,
-	        "isMaxTime": 2,
-	        "isShow": 2,
-	        "recordCount": 6,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740430900,
-	        "updatedAt": 1740466956
-	    },
-	    {
-	        "id": 1725819,
-	        "pastureId": 1,
-	        "neckRingNumber": "10027",
-	        "cowId": 30,
-	        "lact": 0,
-	        "calvingAge": 0,
-	        "activeTime": "2025-02-25 05:00:00",
-	        "frameid": 2,
-	        "heatDate": "2025-02-25",
-	        "rumina": 36,
-	        "intake": 0,
-	        "inactive": 84,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 490,
-	        "active": 41,
-	        "filterHigh": 76,
-	        "filterRumina": 0,
-	        "filterChew": 0,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 590,
-	        "weekRuminaHabit": 14,
-	        "weekIntakeHabit": 23,
-	        "weekChewHabit": 23,
-	        "weekInactiveHabit": 23,
-	        "weekOtherHabit": 0,
-	        "changeHigh": -42,
-	        "changeRumina": -100,
-	        "changeChew": -100,
-	        "changeAdjust": 0,
-	        "changeFilter": -10,
-	        "ruminaFilter": -12,
-	        "chewFilter": -15,
-	        "filterCorrect": 94,
-	        "sumRumina": 107,
-	        "sumIntake": 331,
-	        "sumInactive": 562,
-	        "sumActive": 699,
-	        "sumMinHigh": -10000,
-	        "sumMaxHigh": 20,
-	        "SumMinChew": 0,
-	        "beforeThreeSumRumina": 136,
-	        "beforeThreeSumIntake": 254,
-	        "score": 96,
-	        "isMaxTime": 2,
-	        "isShow": 2,
-	        "recordCount": 6,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740430925,
-	        "updatedAt": 1740466956
-	    },
-	    {
-	        "id": 1725824,
-	        "pastureId": 1,
-	        "neckRingNumber": "10054",
-	        "cowId": 109,
-	        "lact": 3,
-	        "calvingAge": 167,
-	        "activeTime": "2025-02-25 07:00:00",
-	        "frameid": 3,
-	        "heatDate": "2025-02-25",
-	        "rumina": 82,
-	        "intake": 0,
-	        "inactive": 109,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 232,
-	        "active": 8,
-	        "filterHigh": 168,
-	        "filterRumina": 9,
-	        "filterChew": 9,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 28,
-	        "weekRuminaHabit": 7,
-	        "weekIntakeHabit": 28,
-	        "weekChewHabit": 7,
-	        "weekInactiveHabit": 28,
-	        "weekOtherHabit": 0,
-	        "changeHigh": 13,
-	        "changeRumina": 29,
-	        "changeChew": 29,
-	        "changeAdjust": 0,
-	        "changeFilter": 4,
-	        "ruminaFilter": 9,
-	        "chewFilter": 9,
-	        "filterCorrect": 97,
-	        "sumRumina": 66,
-	        "sumIntake": 293,
-	        "sumInactive": 560,
-	        "sumActive": 700,
-	        "sumMinHigh": -10000,
-	        "sumMaxHigh": 18,
-	        "SumMinChew": 0,
-	        "beforeThreeSumRumina": 62,
-	        "beforeThreeSumIntake": 198,
-	        "score": 100,
-	        "isMaxTime": 2,
-	        "isShow": 2,
-	        "recordCount": 6,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740435720,
-	        "updatedAt": 1740466956
-	    },
-	    {
-	        "id": 1725831,
-	        "pastureId": 1,
-	        "neckRingNumber": "10030",
-	        "cowId": 86,
-	        "lact": 2,
-	        "calvingAge": 300,
-	        "activeTime": "2025-02-25 07:00:00",
-	        "frameid": 3,
-	        "heatDate": "2025-02-25",
-	        "rumina": 91,
-	        "intake": 0,
-	        "inactive": 110,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 214,
-	        "active": 10,
-	        "filterHigh": 121,
-	        "filterRumina": 27,
-	        "filterChew": 27,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 27,
-	        "weekRuminaHabit": 24,
-	        "weekIntakeHabit": 3,
-	        "weekChewHabit": 24,
-	        "weekInactiveHabit": 3,
-	        "weekOtherHabit": 0,
-	        "changeHigh": 8,
-	        "changeRumina": 13,
-	        "changeChew": 13,
-	        "changeAdjust": 0,
-	        "changeFilter": 2,
-	        "ruminaFilter": 4,
-	        "chewFilter": 4,
-	        "filterCorrect": 97,
-	        "sumRumina": 182,
-	        "sumIntake": 297,
-	        "sumInactive": 638,
-	        "sumActive": 694,
-	        "sumMinHigh": -10000,
-	        "sumMaxHigh": 18,
-	        "SumMinChew": 5,
-	        "beforeThreeSumRumina": 128,
-	        "beforeThreeSumIntake": 291,
-	        "score": 100,
-	        "isMaxTime": 2,
-	        "isShow": 2,
-	        "recordCount": 6,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740436955,
-	        "updatedAt": 1740466956
-	    },
-	    {
-	        "id": 1725832,
-	        "pastureId": 1,
-	        "neckRingNumber": "10055",
-	        "cowId": 110,
-	        "lact": 2,
-	        "calvingAge": 62,
-	        "activeTime": "2025-02-25 07:00:00",
-	        "frameid": 3,
-	        "heatDate": "2025-02-25",
-	        "rumina": 95,
-	        "intake": 0,
-	        "inactive": 110,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 264,
-	        "active": 16,
-	        "filterHigh": 144,
-	        "filterRumina": 23,
-	        "filterChew": 23,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 55,
-	        "weekRuminaHabit": 19,
-	        "weekIntakeHabit": 9,
-	        "weekChewHabit": 20,
-	        "weekInactiveHabit": 9,
-	        "weekOtherHabit": 0,
-	        "changeHigh": 8,
-	        "changeRumina": 21,
-	        "changeChew": 15,
-	        "changeAdjust": 0,
-	        "changeFilter": 2,
-	        "ruminaFilter": 6,
-	        "chewFilter": 4,
-	        "filterCorrect": 95,
-	        "sumRumina": 143,
-	        "sumIntake": 251,
-	        "sumInactive": 579,
-	        "sumActive": 706,
-	        "sumMinHigh": -10000,
-	        "sumMaxHigh": 18,
-	        "SumMinChew": 0,
-	        "beforeThreeSumRumina": 78,
-	        "beforeThreeSumIntake": 260,
-	        "score": 100,
-	        "isMaxTime": 2,
-	        "isShow": 2,
-	        "recordCount": 6,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740436960,
-	        "updatedAt": 1740466956
-	    },
-	    {
-	        "id": 1725839,
-	        "pastureId": 1,
-	        "neckRingNumber": "10032",
-	        "cowId": 88,
-	        "lact": 0,
-	        "calvingAge": 0,
-	        "activeTime": "2025-02-25 07:00:00",
-	        "frameid": 3,
-	        "heatDate": "2025-02-25",
-	        "rumina": 13,
-	        "intake": 0,
-	        "inactive": 118,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 126,
-	        "active": 2,
-	        "filterHigh": 78,
-	        "filterRumina": 3,
-	        "filterChew": 3,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 133,
-	        "weekRuminaHabit": 4,
-	        "weekIntakeHabit": 13,
-	        "weekChewHabit": 7,
-	        "weekInactiveHabit": 13,
-	        "weekOtherHabit": 0,
-	        "changeHigh": -5,
-	        "changeRumina": -25,
-	        "changeChew": -57,
-	        "changeAdjust": 0,
-	        "changeFilter": -1,
-	        "ruminaFilter": -6,
-	        "chewFilter": -17,
-	        "filterCorrect": 97,
-	        "sumRumina": 50,
-	        "sumIntake": 200,
-	        "sumInactive": 628,
-	        "sumActive": 526,
-	        "sumMinHigh": -10000,
-	        "sumMaxHigh": 11,
-	        "SumMinChew": 0,
-	        "beforeThreeSumRumina": 0,
-	        "beforeThreeSumIntake": 0,
-	        "score": 89,
-	        "isMaxTime": 2,
-	        "isShow": 2,
-	        "recordCount": 6,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740436990,
-	        "updatedAt": 1740466956
-	    },
-	    {
-	        "id": 1725845,
-	        "pastureId": 1,
-	        "neckRingNumber": "10053",
-	        "cowId": 108,
-	        "lact": 0,
-	        "calvingAge": 0,
-	        "activeTime": "2025-02-25 07:00:00",
-	        "frameid": 3,
-	        "heatDate": "2025-02-25",
-	        "rumina": 33,
-	        "intake": 1,
-	        "inactive": 112,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 231,
-	        "active": 6,
-	        "filterHigh": 127,
-	        "filterRumina": 23,
-	        "filterChew": 23,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 91,
-	        "weekRuminaHabit": 20,
-	        "weekIntakeHabit": 12,
-	        "weekChewHabit": 21,
-	        "weekInactiveHabit": 12,
-	        "weekOtherHabit": 0,
-	        "changeHigh": 3,
-	        "changeRumina": 15,
-	        "changeChew": 10,
-	        "changeAdjust": 0,
-	        "changeFilter": 1,
-	        "ruminaFilter": 4,
-	        "chewFilter": 3,
-	        "filterCorrect": 96,
-	        "sumRumina": 159,
-	        "sumIntake": 301,
-	        "sumInactive": 700,
-	        "sumActive": 646,
-	        "sumMinHigh": -10000,
-	        "sumMaxHigh": 19,
-	        "SumMinChew": 10,
-	        "beforeThreeSumRumina": 180,
-	        "beforeThreeSumIntake": 286,
-	        "score": 100,
-	        "isMaxTime": 2,
-	        "isShow": 2,
-	        "recordCount": 6,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740438100,
-	        "updatedAt": 1740466956
-	    },
-	    {
-	        "id": 1725849,
-	        "pastureId": 1,
-	        "neckRingNumber": "10027",
-	        "cowId": 30,
-	        "lact": 0,
-	        "calvingAge": 0,
-	        "activeTime": "2025-02-25 07:00:00",
-	        "frameid": 3,
-	        "heatDate": "2025-02-25",
-	        "rumina": 71,
-	        "intake": 9,
-	        "inactive": 0,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 936,
-	        "active": 49,
-	        "filterHigh": 595,
-	        "filterRumina": 18,
-	        "filterChew": 24,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 77,
-	        "weekRuminaHabit": 23,
-	        "weekIntakeHabit": 7,
-	        "weekChewHabit": 23,
-	        "weekInactiveHabit": 7,
-	        "weekOtherHabit": 0,
-	        "changeHigh": 46,
-	        "changeRumina": -22,
-	        "changeChew": 4,
-	        "changeAdjust": 0,
-	        "changeFilter": 11,
-	        "ruminaFilter": -5,
-	        "chewFilter": 1,
-	        "filterCorrect": 94,
-	        "sumRumina": 109,
-	        "sumIntake": 334,
-	        "sumInactive": 485,
-	        "sumActive": 756,
-	        "sumMinHigh": -10000,
-	        "sumMaxHigh": 20,
-	        "SumMinChew": 0,
-	        "beforeThreeSumRumina": 126,
-	        "beforeThreeSumIntake": 248,
-	        "score": 100,
-	        "isMaxTime": 2,
-	        "isShow": 2,
-	        "recordCount": 6,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740438130,
-	        "updatedAt": 1740466956
-	    },
-	    {
-	        "id": 1725853,
-	        "pastureId": 1,
-	        "neckRingNumber": "10028",
-	        "cowId": 84,
-	        "lact": 2,
-	        "calvingAge": 300,
-	        "activeTime": "2025-02-25 07:00:00",
-	        "frameid": 3,
-	        "heatDate": "2025-02-25",
-	        "rumina": 3,
-	        "intake": 9,
-	        "inactive": 105,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 583,
-	        "active": 20,
-	        "filterHigh": 16,
-	        "filterRumina": 0,
-	        "filterChew": 0,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 341,
-	        "weekRuminaHabit": 12,
-	        "weekIntakeHabit": 30,
-	        "weekChewHabit": 16,
-	        "weekInactiveHabit": 30,
-	        "weekOtherHabit": 0,
-	        "changeHigh": -28,
-	        "changeRumina": -100,
-	        "changeChew": -100,
-	        "changeAdjust": 0,
-	        "changeFilter": -8,
-	        "ruminaFilter": -15,
-	        "chewFilter": -15,
-	        "filterCorrect": 95,
-	        "sumRumina": 103,
-	        "sumIntake": 251,
-	        "sumInactive": 654,
-	        "sumActive": 633,
-	        "sumMinHigh": -10000,
-	        "sumMaxHigh": 15,
-	        "SumMinChew": 0,
-	        "beforeThreeSumRumina": 163,
-	        "beforeThreeSumIntake": 255,
-	        "score": 96,
-	        "isMaxTime": 2,
-	        "isShow": 2,
-	        "recordCount": 6,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740442795,
-	        "updatedAt": 1740466956
-	    },
-	    {
-	        "id": 1725854,
-	        "pastureId": 1,
-	        "neckRingNumber": "10054",
-	        "cowId": 109,
-	        "lact": 3,
-	        "calvingAge": 167,
-	        "activeTime": "2025-02-25 09:00:00",
-	        "frameid": 4,
-	        "heatDate": "2025-02-25",
-	        "rumina": 62,
-	        "intake": 1,
-	        "inactive": 86,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 783,
-	        "active": 34,
-	        "filterHigh": 329,
-	        "filterRumina": 7,
-	        "filterChew": 7,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 258,
-	        "weekRuminaHabit": 0,
-	        "weekIntakeHabit": 40,
-	        "weekChewHabit": 10,
-	        "weekInactiveHabit": 40,
-	        "weekOtherHabit": 0,
-	        "changeHigh": 6,
-	        "changeRumina": 0,
-	        "changeChew": -30,
-	        "changeAdjust": 0,
-	        "changeFilter": 2,
-	        "ruminaFilter": 0,
-	        "chewFilter": -9,
-	        "filterCorrect": 97,
-	        "sumRumina": 73,
-	        "sumIntake": 234,
-	        "sumInactive": 661,
-	        "sumActive": 628,
-	        "sumMinHigh": -10000,
-	        "sumMaxHigh": 18,
-	        "SumMinChew": 3,
-	        "beforeThreeSumRumina": 64,
-	        "beforeThreeSumIntake": 205,
-	        "score": 100,
-	        "isMaxTime": 2,
-	        "isShow": 2,
-	        "recordCount": 6,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740442915,
-	        "updatedAt": 1740466956
-	    },
-	    {
-	        "id": 1725862,
-	        "pastureId": 1,
-	        "neckRingNumber": "10055",
-	        "cowId": 110,
-	        "lact": 2,
-	        "calvingAge": 62,
-	        "activeTime": "2025-02-25 09:00:00",
-	        "frameid": 4,
-	        "heatDate": "2025-02-25",
-	        "rumina": 43,
-	        "intake": 7,
-	        "inactive": 29,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 2458,
-	        "active": 77,
-	        "filterHigh": 1077,
-	        "filterRumina": 7,
-	        "filterChew": 11,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 892,
-	        "weekRuminaHabit": 10,
-	        "weekIntakeHabit": 29,
-	        "weekChewHabit": 21,
-	        "weekInactiveHabit": 29,
-	        "weekOtherHabit": 0,
-	        "changeHigh": 14,
-	        "changeRumina": -30,
-	        "changeChew": -48,
-	        "changeAdjust": 0,
-	        "changeFilter": 4,
-	        "ruminaFilter": -9,
-	        "chewFilter": -14,
-	        "filterCorrect": 95,
-	        "sumRumina": 132,
-	        "sumIntake": 230,
-	        "sumInactive": 648,
-	        "sumActive": 681,
-	        "sumMinHigh": -10000,
-	        "sumMaxHigh": 18,
-	        "SumMinChew": 0,
-	        "beforeThreeSumRumina": 56,
-	        "beforeThreeSumIntake": 276,
-	        "score": 100,
-	        "isMaxTime": 2,
-	        "isShow": 2,
-	        "recordCount": 6,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740444160,
-	        "updatedAt": 1740466956
-	    },
-	    {
-	        "id": 1725865,
-	        "pastureId": 1,
-	        "neckRingNumber": "10032",
-	        "cowId": 88,
-	        "lact": 0,
-	        "calvingAge": 0,
-	        "activeTime": "2025-02-25 09:00:00",
-	        "frameid": 4,
-	        "heatDate": "2025-02-25",
-	        "rumina": 0,
-	        "intake": 34,
-	        "inactive": 31,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 1540,
-	        "active": 71,
-	        "filterHigh": 239,
-	        "filterRumina": 0,
-	        "filterChew": 0,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 357,
-	        "weekRuminaHabit": 3,
-	        "weekIntakeHabit": 19,
-	        "weekChewHabit": 6,
-	        "weekInactiveHabit": 19,
-	        "weekOtherHabit": 0,
-	        "changeHigh": -10,
-	        "changeRumina": -100,
-	        "changeChew": -100,
-	        "changeAdjust": 0,
-	        "changeFilter": -2,
-	        "ruminaFilter": -12,
-	        "chewFilter": -15,
-	        "filterCorrect": 97,
-	        "sumRumina": 50,
-	        "sumIntake": 186,
-	        "sumInactive": 739,
-	        "sumActive": 469,
-	        "sumMinHigh": -10000,
-	        "sumMaxHigh": 11,
-	        "SumMinChew": 0,
-	        "beforeThreeSumRumina": 141,
-	        "beforeThreeSumIntake": 215,
-	        "score": 89,
-	        "isMaxTime": 2,
-	        "isShow": 2,
-	        "recordCount": 6,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740444195,
-	        "updatedAt": 1740466956
-	    },
-	    {
-	        "id": 1725870,
-	        "pastureId": 1,
-	        "neckRingNumber": "10030",
-	        "cowId": 86,
-	        "lact": 2,
-	        "calvingAge": 300,
-	        "activeTime": "2025-02-25 09:00:00",
-	        "frameid": 4,
-	        "heatDate": "2025-02-25",
-	        "rumina": 66,
-	        "intake": 0,
-	        "inactive": 46,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 1275,
-	        "active": 57,
-	        "filterHigh": 329,
-	        "filterRumina": 18,
-	        "filterChew": 18,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 412,
-	        "weekRuminaHabit": 13,
-	        "weekIntakeHabit": 18,
-	        "weekChewHabit": 20,
-	        "weekInactiveHabit": 18,
-	        "weekOtherHabit": 0,
-	        "changeHigh": -7,
-	        "changeRumina": 38,
-	        "changeChew": -10,
-	        "changeAdjust": 0,
-	        "changeFilter": -2,
-	        "ruminaFilter": 11,
-	        "chewFilter": -3,
-	        "filterCorrect": 97,
-	        "sumRumina": 200,
-	        "sumIntake": 267,
-	        "sumInactive": 691,
-	        "sumActive": 651,
-	        "sumMinHigh": -10000,
-	        "sumMaxHigh": 10,
-	        "SumMinChew": 5,
-	        "beforeThreeSumRumina": 116,
-	        "beforeThreeSumIntake": 283,
-	        "score": 99,
-	        "isMaxTime": 2,
-	        "isShow": 2,
-	        "recordCount": 6,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740444450,
-	        "updatedAt": 1740466956
-	    },
-	    {
-	        "id": 1725873,
-	        "pastureId": 1,
-	        "neckRingNumber": "10038",
-	        "cowId": 94,
-	        "lact": 0,
-	        "calvingAge": 0,
-	        "activeTime": "2025-02-25 09:00:00",
-	        "frameid": 4,
-	        "heatDate": "2025-02-25",
-	        "rumina": 4,
-	        "intake": 0,
-	        "inactive": 0,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 209,
-	        "active": 13,
-	        "filterHigh": 77,
-	        "filterRumina": 3,
-	        "filterChew": 3,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 359,
-	        "weekRuminaHabit": 2,
-	        "weekIntakeHabit": 17,
-	        "weekChewHabit": 4,
-	        "weekInactiveHabit": 17,
-	        "weekOtherHabit": 0,
-	        "changeHigh": -24,
-	        "changeRumina": 50,
-	        "changeChew": -25,
-	        "changeAdjust": 0,
-	        "changeFilter": -6,
-	        "ruminaFilter": 12,
-	        "chewFilter": -8,
-	        "filterCorrect": 98,
-	        "sumRumina": 12,
-	        "sumIntake": 0,
-	        "sumInactive": 502,
-	        "sumActive": 132,
-	        "sumMinHigh": -10000,
-	        "sumMaxHigh": 3,
-	        "SumMinChew": 0,
-	        "beforeThreeSumRumina": 19,
-	        "beforeThreeSumIntake": 157,
-	        "score": 67,
-	        "isMaxTime": 2,
-	        "isShow": 2,
-	        "recordCount": 6,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740445065,
-	        "updatedAt": 1740466956
-	    },
-	    {
-	        "id": 1725874,
-	        "pastureId": 1,
-	        "neckRingNumber": "10053",
-	        "cowId": 108,
-	        "lact": 0,
-	        "calvingAge": 0,
-	        "activeTime": "2025-02-25 09:00:00",
-	        "frameid": 4,
-	        "heatDate": "2025-02-25",
-	        "rumina": 33,
-	        "intake": 26,
-	        "inactive": 3,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 2339,
-	        "active": 96,
-	        "filterHigh": 1061,
-	        "filterRumina": 7,
-	        "filterChew": 25,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 475,
-	        "weekRuminaHabit": 12,
-	        "weekIntakeHabit": 26,
-	        "weekChewHabit": 26,
-	        "weekInactiveHabit": 26,
-	        "weekOtherHabit": 0,
-	        "changeHigh": 49,
-	        "changeRumina": -42,
-	        "changeChew": -4,
-	        "changeAdjust": 0,
-	        "changeFilter": 12,
-	        "ruminaFilter": -10,
-	        "chewFilter": -1,
-	        "filterCorrect": 96,
-	        "sumRumina": 163,
-	        "sumIntake": 263,
-	        "sumInactive": 763,
-	        "sumActive": 589,
-	        "sumMinHigh": -10000,
-	        "sumMaxHigh": 9,
-	        "SumMinChew": 10,
-	        "beforeThreeSumRumina": 193,
-	        "beforeThreeSumIntake": 284,
-	        "score": 100,
-	        "isMaxTime": 2,
-	        "isShow": 2,
-	        "recordCount": 6,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740445305,
-	        "updatedAt": 1740466956
-	    },
-	    {
-	        "id": 1725879,
-	        "pastureId": 1,
-	        "neckRingNumber": "10027",
-	        "cowId": 30,
-	        "lact": 0,
-	        "calvingAge": 0,
-	        "activeTime": "2025-02-25 09:00:00",
-	        "frameid": 4,
-	        "heatDate": "2025-02-25",
-	        "rumina": 34,
-	        "intake": 27,
-	        "inactive": 15,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 1563,
-	        "active": 64,
-	        "filterHigh": 720,
-	        "filterRumina": 23,
-	        "filterChew": 27,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 796,
-	        "weekRuminaHabit": 2,
-	        "weekIntakeHabit": 26,
-	        "weekChewHabit": 7,
-	        "weekInactiveHabit": 26,
-	        "weekOtherHabit": 0,
-	        "changeHigh": -6,
-	        "changeRumina": 1050,
-	        "changeChew": 286,
-	        "changeAdjust": 0,
-	        "changeFilter": -1,
-	        "ruminaFilter": 50,
-	        "chewFilter": 43,
-	        "filterCorrect": 94,
-	        "sumRumina": 132,
-	        "sumIntake": 295,
-	        "sumInactive": 473,
-	        "sumActive": 719,
-	        "sumMinHigh": -10000,
-	        "sumMaxHigh": 20,
-	        "SumMinChew": 0,
-	        "beforeThreeSumRumina": 127,
-	        "beforeThreeSumIntake": 232,
-	        "score": 99,
-	        "isMaxTime": 2,
-	        "isShow": 2,
-	        "recordCount": 6,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740445320,
-	        "updatedAt": 1740466956
-	    },
-	    {
-	        "id": 1725883,
-	        "pastureId": 1,
-	        "neckRingNumber": "10028",
-	        "cowId": 84,
-	        "lact": 2,
-	        "calvingAge": 300,
-	        "activeTime": "2025-02-25 09:00:00",
-	        "frameid": 4,
-	        "heatDate": "2025-02-25",
-	        "rumina": 15,
-	        "intake": 43,
-	        "inactive": 2,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 2796,
-	        "active": 99,
-	        "filterHigh": 1259,
-	        "filterRumina": 4,
-	        "filterChew": 21,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 598,
-	        "weekRuminaHabit": 5,
-	        "weekIntakeHabit": 15,
-	        "weekChewHabit": 11,
-	        "weekInactiveHabit": 15,
-	        "weekOtherHabit": 0,
-	        "changeHigh": 54,
-	        "changeRumina": -20,
-	        "changeChew": 91,
-	        "changeAdjust": 0,
-	        "changeFilter": 16,
-	        "ruminaFilter": -6,
-	        "chewFilter": 14,
-	        "filterCorrect": 95,
-	        "sumRumina": 105,
-	        "sumIntake": 265,
-	        "sumInactive": 717,
-	        "sumActive": 651,
-	        "sumMinHigh": -13,
-	        "sumMaxHigh": 16,
-	        "SumMinChew": 0,
-	        "beforeThreeSumRumina": 160,
-	        "beforeThreeSumIntake": 282,
-	        "score": 97,
-	        "isMaxTime": 2,
-	        "isShow": 1,
-	        "recordCount": 6,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740445670,
-	        "updatedAt": 1740466957
-	    },
-	    {
-	        "id": 1725884,
-	        "pastureId": 1,
-	        "neckRingNumber": "10054",
-	        "cowId": 109,
-	        "lact": 3,
-	        "calvingAge": 167,
-	        "activeTime": "2025-02-25 11:00:00",
-	        "frameid": 5,
-	        "heatDate": "2025-02-25",
-	        "rumina": 35,
-	        "intake": 39,
-	        "inactive": 1,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 2761,
-	        "active": 95,
-	        "filterHigh": 247,
-	        "filterRumina": 6,
-	        "filterChew": 6,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 388,
-	        "weekRuminaHabit": 1,
-	        "weekIntakeHabit": 21,
-	        "weekChewHabit": 8,
-	        "weekInactiveHabit": 21,
-	        "weekOtherHabit": 0,
-	        "changeHigh": -12,
-	        "changeRumina": 500,
-	        "changeChew": -25,
-	        "changeAdjust": 0,
-	        "changeFilter": -4,
-	        "ruminaFilter": 50,
-	        "chewFilter": -8,
-	        "filterCorrect": 97,
-	        "sumRumina": 70,
-	        "sumIntake": 210,
-	        "sumInactive": 741,
-	        "sumActive": 577,
-	        "sumMinHigh": -10000,
-	        "sumMaxHigh": 18,
-	        "SumMinChew": 3,
-	        "beforeThreeSumRumina": 68,
-	        "beforeThreeSumIntake": 225,
-	        "score": 98,
-	        "isMaxTime": 2,
-	        "isShow": 2,
-	        "recordCount": 6,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740450120,
-	        "updatedAt": 1740466957
-	    },
-	    {
-	        "id": 1725891,
-	        "pastureId": 1,
-	        "neckRingNumber": "10030",
-	        "cowId": 86,
-	        "lact": 2,
-	        "calvingAge": 300,
-	        "activeTime": "2025-02-25 11:00:00",
-	        "frameid": 5,
-	        "heatDate": "2025-02-25",
-	        "rumina": 48,
-	        "intake": 41,
-	        "inactive": 51,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 1893,
-	        "active": 71,
-	        "filterHigh": 803,
-	        "filterRumina": 1,
-	        "filterChew": 18,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 719,
-	        "weekRuminaHabit": 6,
-	        "weekIntakeHabit": 36,
-	        "weekChewHabit": 18,
-	        "weekInactiveHabit": 36,
-	        "weekOtherHabit": 0,
-	        "changeHigh": 7,
-	        "changeRumina": -83,
-	        "changeChew": 0,
-	        "changeAdjust": 0,
-	        "changeFilter": 2,
-	        "ruminaFilter": -12,
-	        "chewFilter": 0,
-	        "filterCorrect": 97,
-	        "sumRumina": 192,
-	        "sumIntake": 250,
-	        "sumInactive": 697,
-	        "sumActive": 640,
-	        "sumMinHigh": -10000,
-	        "sumMaxHigh": 10,
-	        "SumMinChew": 5,
-	        "beforeThreeSumRumina": 128,
-	        "beforeThreeSumIntake": 246,
-	        "score": 100,
-	        "isMaxTime": 2,
-	        "isShow": 2,
-	        "recordCount": 6,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740451350,
-	        "updatedAt": 1740466957
-	    },
-	    {
-	        "id": 1725894,
-	        "pastureId": 1,
-	        "neckRingNumber": "10055",
-	        "cowId": 110,
-	        "lact": 2,
-	        "calvingAge": 62,
-	        "activeTime": "2025-02-25 11:00:00",
-	        "frameid": 5,
-	        "heatDate": "2025-02-25",
-	        "rumina": 0,
-	        "intake": 45,
-	        "inactive": 52,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 2748,
-	        "active": 66,
-	        "filterHigh": 1309,
-	        "filterRumina": 0,
-	        "filterChew": 19,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 884,
-	        "weekRuminaHabit": 5,
-	        "weekIntakeHabit": 31,
-	        "weekChewHabit": 14,
-	        "weekInactiveHabit": 31,
-	        "weekOtherHabit": 0,
-	        "changeHigh": 33,
-	        "changeRumina": -100,
-	        "changeChew": 36,
-	        "changeAdjust": 0,
-	        "changeFilter": 10,
-	        "ruminaFilter": -15,
-	        "chewFilter": 11,
-	        "filterCorrect": 95,
-	        "sumRumina": 122,
-	        "sumIntake": 214,
-	        "sumInactive": 670,
-	        "sumActive": 656,
-	        "sumMinHigh": -10000,
-	        "sumMaxHigh": 18,
-	        "SumMinChew": 0,
-	        "beforeThreeSumRumina": 52,
-	        "beforeThreeSumIntake": 277,
-	        "score": 100,
-	        "isMaxTime": 2,
-	        "isShow": 2,
-	        "recordCount": 6,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740451355,
-	        "updatedAt": 1740466957
-	    },
-	    {
-	        "id": 1725896,
-	        "pastureId": 1,
-	        "neckRingNumber": "10038",
-	        "cowId": 94,
-	        "lact": 0,
-	        "calvingAge": 0,
-	        "activeTime": "2025-02-25 11:00:00",
-	        "frameid": 5,
-	        "heatDate": "2025-02-25",
-	        "rumina": 2,
-	        "intake": 0,
-	        "inactive": 76,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 249,
-	        "active": 6,
-	        "filterHigh": 20,
-	        "filterRumina": 2,
-	        "filterChew": 2,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 48,
-	        "weekRuminaHabit": 7,
-	        "weekIntakeHabit": 11,
-	        "weekChewHabit": 11,
-	        "weekInactiveHabit": 11,
-	        "weekOtherHabit": 0,
-	        "changeHigh": -3,
-	        "changeRumina": -71,
-	        "changeChew": -82,
-	        "changeAdjust": 0,
-	        "changeFilter": -1,
-	        "ruminaFilter": -9,
-	        "chewFilter": -12,
-	        "filterCorrect": 98,
-	        "sumRumina": 13,
-	        "sumIntake": 0,
-	        "sumInactive": 515,
-	        "sumActive": 136,
-	        "sumMinHigh": -10000,
-	        "sumMaxHigh": 3,
-	        "SumMinChew": 0,
-	        "beforeThreeSumRumina": 20,
-	        "beforeThreeSumIntake": 121,
-	        "score": 69,
-	        "isMaxTime": 2,
-	        "isShow": 2,
-	        "recordCount": 6,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740451385,
-	        "updatedAt": 1740466957
-	    },
-	    {
-	        "id": 1725901,
-	        "pastureId": 1,
-	        "neckRingNumber": "10032",
-	        "cowId": 88,
-	        "lact": 0,
-	        "calvingAge": 0,
-	        "activeTime": "2025-02-25 11:00:00",
-	        "frameid": 5,
-	        "heatDate": "2025-02-25",
-	        "rumina": 7,
-	        "intake": 24,
-	        "inactive": 66,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 1082,
-	        "active": 51,
-	        "filterHigh": 365,
-	        "filterRumina": 3,
-	        "filterChew": 8,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 113,
-	        "weekRuminaHabit": 16,
-	        "weekIntakeHabit": 7,
-	        "weekChewHabit": 20,
-	        "weekInactiveHabit": 7,
-	        "weekOtherHabit": 0,
-	        "changeHigh": 22,
-	        "changeRumina": -81,
-	        "changeChew": -60,
-	        "changeAdjust": 0,
-	        "changeFilter": 0,
-	        "ruminaFilter": 0,
-	        "chewFilter": 0,
-	        "filterCorrect": 97,
-	        "sumRumina": 52,
-	        "sumIntake": 204,
-	        "sumInactive": 686,
-	        "sumActive": 506,
-	        "sumMinHigh": -11,
-	        "sumMaxHigh": 11,
-	        "SumMinChew": 0,
-	        "beforeThreeSumRumina": 123,
-	        "beforeThreeSumIntake": 225,
-	        "score": 87,
-	        "isMaxTime": 2,
-	        "isShow": 2,
-	        "recordCount": 6,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740451390,
-	        "updatedAt": 1740466957
-	    },
-	    {
-	        "id": 1725904,
-	        "pastureId": 1,
-	        "neckRingNumber": "10053",
-	        "cowId": 108,
-	        "lact": 0,
-	        "calvingAge": 0,
-	        "activeTime": "2025-02-25 11:00:00",
-	        "frameid": 5,
-	        "heatDate": "2025-02-25",
-	        "rumina": 48,
-	        "intake": 42,
-	        "inactive": 68,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 1135,
-	        "active": 49,
-	        "filterHigh": 847,
-	        "filterRumina": 2,
-	        "filterChew": 30,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 651,
-	        "weekRuminaHabit": 13,
-	        "weekIntakeHabit": 20,
-	        "weekChewHabit": 26,
-	        "weekInactiveHabit": 20,
-	        "weekOtherHabit": 0,
-	        "changeHigh": 16,
-	        "changeRumina": -85,
-	        "changeChew": 15,
-	        "changeAdjust": 0,
-	        "changeFilter": 4,
-	        "ruminaFilter": -10,
-	        "chewFilter": 4,
-	        "filterCorrect": 96,
-	        "sumRumina": 158,
-	        "sumIntake": 299,
-	        "sumInactive": 700,
-	        "sumActive": 637,
-	        "sumMinHigh": -10000,
-	        "sumMaxHigh": 12,
-	        "SumMinChew": 10,
-	        "beforeThreeSumRumina": 193,
-	        "beforeThreeSumIntake": 270,
-	        "score": 100,
-	        "isMaxTime": 2,
-	        "isShow": 2,
-	        "recordCount": 6,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740452505,
-	        "updatedAt": 1740466957
-	    },
-	    {
-	        "id": 1725908,
-	        "pastureId": 1,
-	        "neckRingNumber": "10027",
-	        "cowId": 30,
-	        "lact": 0,
-	        "calvingAge": 0,
-	        "activeTime": "2025-02-25 11:00:00",
-	        "frameid": 5,
-	        "heatDate": "2025-02-25",
-	        "rumina": 43,
-	        "intake": 25,
-	        "inactive": 93,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 821,
-	        "active": 30,
-	        "filterHigh": 32,
-	        "filterRumina": 29,
-	        "filterChew": 29,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 277,
-	        "weekRuminaHabit": 18,
-	        "weekIntakeHabit": 11,
-	        "weekChewHabit": 24,
-	        "weekInactiveHabit": 11,
-	        "weekOtherHabit": 0,
-	        "changeHigh": -21,
-	        "changeRumina": 61,
-	        "changeChew": 21,
-	        "changeAdjust": 0,
-	        "changeFilter": -5,
-	        "ruminaFilter": 7,
-	        "chewFilter": 6,
-	        "filterCorrect": 94,
-	        "sumRumina": 144,
-	        "sumIntake": 285,
-	        "sumInactive": 533,
-	        "sumActive": 654,
-	        "sumMinHigh": -10000,
-	        "sumMaxHigh": 20,
-	        "SumMinChew": 0,
-	        "beforeThreeSumRumina": 127,
-	        "beforeThreeSumIntake": 297,
-	        "score": 98,
-	        "isMaxTime": 2,
-	        "isShow": 2,
-	        "recordCount": 6,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740452530,
-	        "updatedAt": 1740466957
-	    },
-	    {
-	        "id": 1725913,
-	        "pastureId": 1,
-	        "neckRingNumber": "10028",
-	        "cowId": 84,
-	        "lact": 2,
-	        "calvingAge": 300,
-	        "activeTime": "2025-02-25 11:00:00",
-	        "frameid": 5,
-	        "heatDate": "2025-02-25",
-	        "rumina": 64,
-	        "intake": 36,
-	        "inactive": 67,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 1391,
-	        "active": 57,
-	        "filterHigh": 512,
-	        "filterRumina": 20,
-	        "filterChew": 31,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 559,
-	        "weekRuminaHabit": 4,
-	        "weekIntakeHabit": 29,
-	        "weekChewHabit": 13,
-	        "weekInactiveHabit": 29,
-	        "weekOtherHabit": 0,
-	        "changeHigh": -4,
-	        "changeRumina": 400,
-	        "changeChew": 138,
-	        "changeAdjust": 0,
-	        "changeFilter": -1,
-	        "ruminaFilter": 50,
-	        "chewFilter": 21,
-	        "filterCorrect": 95,
-	        "sumRumina": 110,
-	        "sumIntake": 264,
-	        "sumInactive": 725,
-	        "sumActive": 645,
-	        "sumMinHigh": -13,
-	        "sumMaxHigh": 16,
-	        "SumMinChew": 0,
-	        "beforeThreeSumRumina": 157,
-	        "beforeThreeSumIntake": 266,
-	        "score": 97,
-	        "isMaxTime": 2,
-	        "isShow": 1,
-	        "recordCount": 6,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740452850,
-	        "updatedAt": 1740466957
-	    },
-	    {
-	        "id": 1725914,
-	        "pastureId": 1,
-	        "neckRingNumber": "10054",
-	        "cowId": 109,
-	        "lact": 3,
-	        "calvingAge": 167,
-	        "activeTime": "2025-02-25 13:00:00",
-	        "frameid": 6,
-	        "heatDate": "2025-02-25",
-	        "rumina": 26,
-	        "intake": 27,
-	        "inactive": 69,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 1001,
-	        "active": 46,
-	        "filterHigh": 349,
-	        "filterRumina": 0,
-	        "filterChew": 14,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 200,
-	        "weekRuminaHabit": 8,
-	        "weekIntakeHabit": 8,
-	        "weekChewHabit": 9,
-	        "weekInactiveHabit": 8,
-	        "weekOtherHabit": 0,
-	        "changeHigh": 13,
-	        "changeRumina": -100,
-	        "changeChew": 56,
-	        "changeAdjust": 0,
-	        "changeFilter": 4,
-	        "ruminaFilter": -15,
-	        "chewFilter": 17,
-	        "filterCorrect": 97,
-	        "sumRumina": 67,
-	        "sumIntake": 254,
-	        "sumInactive": 674,
-	        "sumActive": 627,
-	        "sumMinHigh": -10000,
-	        "sumMaxHigh": 5,
-	        "SumMinChew": 3,
-	        "beforeThreeSumRumina": 73,
-	        "beforeThreeSumIntake": 227,
-	        "score": 100,
-	        "isMaxTime": 2,
-	        "isShow": 2,
-	        "recordCount": 6,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740457320,
-	        "updatedAt": 1740466957
-	    },
-	    {
-	        "id": 1725921,
-	        "pastureId": 1,
-	        "neckRingNumber": "10030",
-	        "cowId": 86,
-	        "lact": 2,
-	        "calvingAge": 300,
-	        "activeTime": "2025-02-25 13:00:00",
-	        "frameid": 6,
-	        "heatDate": "2025-02-25",
-	        "rumina": 54,
-	        "intake": 0,
-	        "inactive": 105,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 198,
-	        "active": 10,
-	        "filterHigh": 48,
-	        "filterRumina": 15,
-	        "filterChew": 15,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 32,
-	        "weekRuminaHabit": 13,
-	        "weekIntakeHabit": 2,
-	        "weekChewHabit": 13,
-	        "weekInactiveHabit": 2,
-	        "weekOtherHabit": 0,
-	        "changeHigh": 1,
-	        "changeRumina": 15,
-	        "changeChew": 15,
-	        "changeAdjust": 0,
-	        "changeFilter": 0,
-	        "ruminaFilter": 4,
-	        "chewFilter": 4,
-	        "filterCorrect": 97,
-	        "sumRumina": 180,
-	        "sumIntake": 266,
-	        "sumInactive": 677,
-	        "sumActive": 664,
-	        "sumMinHigh": -10000,
-	        "sumMaxHigh": 10,
-	        "SumMinChew": 5,
-	        "beforeThreeSumRumina": 128,
-	        "beforeThreeSumIntake": 278,
-	        "score": 100,
-	        "isMaxTime": 2,
-	        "isShow": 2,
-	        "recordCount": 6,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740458550,
-	        "updatedAt": 1740466957
-	    },
-	    {
-	        "id": 1725926,
-	        "pastureId": 1,
-	        "neckRingNumber": "10055",
-	        "cowId": 110,
-	        "lact": 2,
-	        "calvingAge": 62,
-	        "activeTime": "2025-02-25 13:00:00",
-	        "frameid": 6,
-	        "heatDate": "2025-02-25",
-	        "rumina": 23,
-	        "intake": 29,
-	        "inactive": 71,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 1844,
-	        "active": 50,
-	        "filterHigh": 402,
-	        "filterRumina": 16,
-	        "filterChew": 19,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 296,
-	        "weekRuminaHabit": 13,
-	        "weekIntakeHabit": 12,
-	        "weekChewHabit": 17,
-	        "weekInactiveHabit": 12,
-	        "weekOtherHabit": 0,
-	        "changeHigh": 9,
-	        "changeRumina": 23,
-	        "changeChew": 12,
-	        "changeAdjust": 0,
-	        "changeFilter": 3,
-	        "ruminaFilter": 7,
-	        "chewFilter": 4,
-	        "filterCorrect": 95,
-	        "sumRumina": 121,
-	        "sumIntake": 236,
-	        "sumInactive": 627,
-	        "sumActive": 696,
-	        "sumMinHigh": -10000,
-	        "sumMaxHigh": 18,
-	        "SumMinChew": 0,
-	        "beforeThreeSumRumina": 68,
-	        "beforeThreeSumIntake": 282,
-	        "score": 100,
-	        "isMaxTime": 2,
-	        "isShow": 2,
-	        "recordCount": 6,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740458585,
-	        "updatedAt": 1740466957
-	    },
-	    {
-	        "id": 1725932,
-	        "pastureId": 1,
-	        "neckRingNumber": "10032",
-	        "cowId": 88,
-	        "lact": 0,
-	        "calvingAge": 0,
-	        "activeTime": "2025-02-25 13:00:00",
-	        "frameid": 6,
-	        "heatDate": "2025-02-25",
-	        "rumina": 66,
-	        "intake": 0,
-	        "inactive": 111,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 90,
-	        "active": 6,
-	        "filterHigh": 4,
-	        "filterRumina": 27,
-	        "filterChew": 27,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 216,
-	        "weekRuminaHabit": 9,
-	        "weekIntakeHabit": 13,
-	        "weekChewHabit": 14,
-	        "weekInactiveHabit": 13,
-	        "weekOtherHabit": 0,
-	        "changeHigh": -18,
-	        "changeRumina": 200,
-	        "changeChew": 93,
-	        "changeAdjust": 0,
-	        "changeFilter": -4,
-	        "ruminaFilter": 24,
-	        "chewFilter": 14,
-	        "filterCorrect": 97,
-	        "sumRumina": 62,
-	        "sumIntake": 220,
-	        "sumInactive": 664,
-	        "sumActive": 530,
-	        "sumMinHigh": -10000,
-	        "sumMaxHigh": 11,
-	        "SumMinChew": 0,
-	        "beforeThreeSumRumina": 123,
-	        "beforeThreeSumIntake": 249,
-	        "score": 98,
-	        "isMaxTime": 2,
-	        "isShow": 2,
-	        "recordCount": 6,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740458625,
-	        "updatedAt": 1740466957
-	    },
-	    {
-	        "id": 1725934,
-	        "pastureId": 1,
-	        "neckRingNumber": "10053",
-	        "cowId": 108,
-	        "lact": 0,
-	        "calvingAge": 0,
-	        "activeTime": "2025-02-25 13:00:00",
-	        "frameid": 6,
-	        "heatDate": "2025-02-25",
-	        "rumina": 45,
-	        "intake": 31,
-	        "inactive": 62,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 1464,
-	        "active": 58,
-	        "filterHigh": 267,
-	        "filterRumina": 14,
-	        "filterChew": -13,
-	        "changeAdjust": 0,
-	        "changeFilter": 3,
-	        "ruminaFilter": -7,
-	        "chewFilter": -4,
-	        "filterCorrect": 96,
-	        "sumRumina": 151,
-	        "sumIntake": 294,
-	        "sumInactive": 715,
-	        "sumActive": 625,
-	        "sumMinHigh": -10000,
-	        "sumMaxHigh": 12,
-	        "SumMinChew": 10,
-	        "beforeThreeSumRumina": 185,
-	        "beforeThreeSumIntake": 253,
-	        "score": 100,
-	        "isMaxTime": 2,
-	        "isShow": 2,
-	        "recordCount": 6,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740459700,
-	        "updatedAt": 1740466957
-	    },
-	    {
-	        "id": 1725938,
-	        "pastureId": 1,
-	        "neckRingNumber": "10027",
-	        "cowId": 30,
-	        "lact": 0,
-	        "calvingAge": 0,
-	        "activeTime": "2025-02-25 13:00:00",
-	        "frameid": 6,
-	        "heatDate": "2025-02-25",
-	        "rumina": 41,
-	        "intake": 13,
-	        "inactive": 94,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 752,
-	        "active": 30,
-	        "filterHigh": 498,
-	        "filterRumina": 17,
-	        "filterChew": 25,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 470,
-	        "weekRuminaHabit": 9,
-	        "weekIntakeHabit": 27,
-	        "weekChewHabit": 22,
-	        "weekInactiveHabit": 27,
-	        "weekOtherHabit": 0,
-	        "changeHigh": 2,
-	        "changeRumina": 89,
-	        "changeChew": 14,
-	        "changeAdjust": 0,
-	        "changeFilter": 0,
-	        "ruminaFilter": 11,
-	        "chewFilter": 4,
-	        "filterCorrect": 94,
-	        "sumRumina": 146,
-	        "sumIntake": 323,
-	        "sumInactive": 480,
-	        "sumActive": 702,
-	        "sumMinHigh": -10000,
-	        "sumMaxHigh": 20,
-	        "SumMinChew": 0,
-	        "beforeThreeSumRumina": 126,
-	        "beforeThreeSumIntake": 274,
-	        "score": 100,
-	        "isMaxTime": 2,
-	        "isShow": 2,
-	        "recordCount": 6,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740459725,
-	        "updatedAt": 1740466957
-	    },
-	    {
-	        "id": 1725943,
-	        "pastureId": 1,
-	        "neckRingNumber": "10028",
-	        "cowId": 84,
-	        "lact": 2,
-	        "calvingAge": 300,
-	        "activeTime": "2025-02-25 13:00:00",
-	        "frameid": 6,
-	        "heatDate": "2025-02-25",
-	        "rumina": 30,
-	        "intake": 0,
-	        "inactive": 109,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 223,
-	        "active": 8,
-	        "filterHigh": 162,
-	        "filterRumina": 17,
-	        "filterChew": 17,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 639,
-	        "weekRuminaHabit": 2,
-	        "weekIntakeHabit": 32,
-	        "weekChewHabit": 13,
-	        "weekInactiveHabit": 32,
-	        "weekOtherHabit": 0,
-	        "changeHigh": -39,
-	        "changeRumina": 750,
-	        "changeChew": 31,
-	        "changeAdjust": 0,
-	        "changeFilter": -12,
-	        "ruminaFilter": 50,
-	        "chewFilter": 9,
-	        "filterCorrect": 95,
-	        "sumRumina": 124,
-	        "sumIntake": 246,
-	        "sumInactive": 821,
-	        "sumActive": 597,
-	        "sumMinHigh": -13,
-	        "sumMaxHigh": 16,
-	        "SumMinChew": 0,
-	        "beforeThreeSumRumina": 151,
-	        "beforeThreeSumIntake": 244,
-	        "score": 95,
-	        "isMaxTime": 2,
-	        "isShow": 1,
-	        "recordCount": 6,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740460350,
-	        "updatedAt": 1740466957
-	    },
-	    {
-	        "id": 1725944,
-	        "pastureId": 1,
-	        "neckRingNumber": "10054",
-	        "cowId": 109,
-	        "lact": 3,
-	        "calvingAge": 167,
-	        "activeTime": "2025-02-25 15:00:00",
-	        "frameid": 7,
-	        "heatDate": "2025-02-25",
-	        "rumina": 38,
-	        "intake": 20,
-	        "inactive": 43,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 1131,
-	        "active": 39,
-	        "filterHigh": 1,
-	        "filterRumina": 9,
-	        "filterChew": 9,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 110,
-	        "weekRuminaHabit": 6,
-	        "weekIntakeHabit": 45,
-	        "weekChewHabit": 6,
-	        "weekInactiveHabit": 45,
-	        "weekOtherHabit": 0,
-	        "changeHigh": -10,
-	        "changeRumina": 50,
-	        "changeChew": 50,
-	        "changeAdjust": 0,
-	        "changeFilter": -3,
-	        "ruminaFilter": 15,
-	        "chewFilter": 15,
-	        "filterCorrect": 97,
-	        "sumRumina": 73,
-	        "sumIntake": 253,
-	        "sumInactive": 695,
-	        "sumActive": 606,
-	        "sumMinHigh": -10000,
-	        "sumMaxHigh": 5,
-	        "SumMinChew": 5,
-	        "beforeThreeSumRumina": 75,
-	        "beforeThreeSumIntake": 196,
-	        "score": 98,
-	        "isMaxTime": 2,
-	        "isShow": 2,
-	        "recordCount": 4,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740464515,
-	        "updatedAt": 1740468120
-	    },
-	    {
-	        "id": 1725950,
-	        "pastureId": 1,
-	        "neckRingNumber": "10030",
-	        "cowId": 86,
-	        "lact": 2,
-	        "calvingAge": 300,
-	        "activeTime": "2025-02-25 15:00:00",
-	        "frameid": 7,
-	        "heatDate": "2025-02-25",
-	        "rumina": 50,
-	        "intake": 26,
-	        "inactive": 62,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 1140,
-	        "active": 43,
-	        "filterHigh": 24,
-	        "filterRumina": 27,
-	        "filterChew": 27,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 307,
-	        "weekRuminaHabit": 8,
-	        "weekIntakeHabit": 42,
-	        "weekChewHabit": 15,
-	        "weekInactiveHabit": 42,
-	        "weekOtherHabit": 0,
-	        "changeHigh": -24,
-	        "changeRumina": 238,
-	        "changeChew": 80,
-	        "changeAdjust": 0,
-	        "changeFilter": -7,
-	        "ruminaFilter": 36,
-	        "chewFilter": 12,
-	        "filterCorrect": 97,
-	        "sumRumina": 188,
-	        "sumIntake": 238,
-	        "sumInactive": 713,
-	        "sumActive": 621,
-	        "sumMinHigh": -10000,
-	        "sumMaxHigh": 10,
-	        "SumMinChew": 5,
-	        "beforeThreeSumRumina": 154,
-	        "beforeThreeSumIntake": 230,
-	        "score": 97,
-	        "isMaxTime": 2,
-	        "isShow": 2,
-	        "recordCount": 5,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740465745,
-	        "updatedAt": 1740469355
-	    },
-	    {
-	        "id": 1725955,
-	        "pastureId": 1,
-	        "neckRingNumber": "10038",
-	        "cowId": 94,
-	        "lact": 0,
-	        "calvingAge": 0,
-	        "activeTime": "2025-02-25 15:00:00",
-	        "frameid": 7,
-	        "heatDate": "2025-02-25",
-	        "rumina": 2,
-	        "intake": 0,
-	        "inactive": 50,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 532,
-	        "active": 20,
-	        "filterHigh": 23,
-	        "filterRumina": 0,
-	        "filterChew": 0,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 287,
-	        "weekRuminaHabit": 6,
-	        "weekIntakeHabit": 35,
-	        "weekChewHabit": 12,
-	        "weekInactiveHabit": 35,
-	        "weekOtherHabit": 0,
-	        "changeHigh": -23,
-	        "changeRumina": -100,
-	        "changeChew": -100,
-	        "changeAdjust": 0,
-	        "changeFilter": -6,
-	        "ruminaFilter": -12,
-	        "chewFilter": -15,
-	        "filterCorrect": 98,
-	        "sumRumina": 10,
-	        "sumIntake": 0,
-	        "sumInactive": 679,
-	        "sumActive": 124,
-	        "sumMinHigh": -10000,
-	        "sumMaxHigh": 3,
-	        "SumMinChew": 0,
-	        "beforeThreeSumRumina": 8,
-	        "beforeThreeSumIntake": 7,
-	        "score": 67,
-	        "isMaxTime": 2,
-	        "isShow": 2,
-	        "recordCount": 5,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740465775,
-	        "updatedAt": 1740469385
-	    },
-	    {
-	        "id": 1725957,
-	        "pastureId": 1,
-	        "neckRingNumber": "10055",
-	        "cowId": 110,
-	        "lact": 2,
-	        "calvingAge": 62,
-	        "activeTime": "2025-02-25 15:00:00",
-	        "frameid": 7,
-	        "heatDate": "2025-02-25",
-	        "rumina": 24,
-	        "intake": 39,
-	        "inactive": 32,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 1902,
-	        "active": 63,
-	        "filterHigh": 47,
-	        "filterRumina": 15,
-	        "filterChew": 15,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 980,
-	        "weekRuminaHabit": 3,
-	        "weekIntakeHabit": 34,
-	        "weekChewHabit": 14,
-	        "weekInactiveHabit": 34,
-	        "weekOtherHabit": 0,
-	        "changeHigh": -71,
-	        "changeRumina": 400,
-	        "changeChew": 7,
-	        "changeAdjust": 0,
-	        "changeFilter": -21,
-	        "ruminaFilter": 50,
-	        "chewFilter": 2,
-	        "filterCorrect": 95,
-	        "sumRumina": 125,
-	        "sumIntake": 208,
-	        "sumInactive": 690,
-	        "sumActive": 627,
-	        "sumMinHigh": -10000,
-	        "sumMaxHigh": 18,
-	        "SumMinChew": 0,
-	        "beforeThreeSumRumina": 71,
-	        "beforeThreeSumIntake": 279,
-	        "score": 91,
-	        "isMaxTime": 2,
-	        "isShow": 2,
-	        "recordCount": 5,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740465780,
-	        "updatedAt": 1740469380
-	    },
-	    {
-	        "id": 1725961,
-	        "pastureId": 1,
-	        "neckRingNumber": "10032",
-	        "cowId": 88,
-	        "lact": 0,
-	        "calvingAge": 0,
-	        "activeTime": "2025-02-25 15:00:00",
-	        "frameid": 7,
-	        "heatDate": "2025-02-25",
-	        "rumina": 40,
-	        "intake": 34,
-	        "inactive": 39,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 1908,
-	        "active": 62,
-	        "filterHigh": 52,
-	        "filterRumina": 25,
-	        "filterChew": 25,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 393,
-	        "weekRuminaHabit": 5,
-	        "weekIntakeHabit": 44,
-	        "weekChewHabit": 16,
-	        "weekInactiveHabit": 44,
-	        "weekOtherHabit": 0,
-	        "changeHigh": -29,
-	        "changeRumina": 400,
-	        "changeChew": 56,
-	        "changeAdjust": 0,
-	        "changeFilter": -7,
-	        "ruminaFilter": 48,
-	        "chewFilter": 17,
-	        "filterCorrect": 97,
-	        "sumRumina": 72,
-	        "sumIntake": 184,
-	        "sumInactive": 734,
-	        "sumActive": 464,
-	        "sumMinHigh": -10000,
-	        "sumMaxHigh": 11,
-	        "SumMinChew": 0,
-	        "beforeThreeSumRumina": 87,
-	        "beforeThreeSumIntake": 206,
-	        "score": 87,
-	        "isMaxTime": 2,
-	        "isShow": 2,
-	        "recordCount": 5,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740465815,
-	        "updatedAt": 1740469420
-	    },
-	    {
-	        "id": 1725965,
-	        "pastureId": 1,
-	        "neckRingNumber": "10053",
-	        "cowId": 108,
-	        "lact": 0,
-	        "calvingAge": 0,
-	        "activeTime": "2025-02-25 15:00:00",
-	        "frameid": 7,
-	        "heatDate": "2025-02-25",
-	        "rumina": 44,
-	        "intake": 0,
-	        "inactive": 60,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 37,
-	        "active": 0,
-	        "filterHigh": 29,
-	        "filterRumina": 30,
-	        "filterChew": 30,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 576,
-	        "weekRuminaHabit": 14,
-	        "weekIntakeHabit": 39,
-	        "weekChewHabit": 29,
-	        "weekInactiveHabit": 39,
-	        "weekOtherHabit": 0,
-	        "changeHigh": -45,
-	        "changeRumina": 114,
-	        "changeChew": 3,
-	        "changeAdjust": 0,
-	        "changeFilter": -11,
-	        "ruminaFilter": 14,
-	        "chewFilter": 1,
-	        "filterCorrect": 96,
-	        "sumRumina": 162,
-	        "sumIntake": 274,
-	        "sumInactive": 762,
-	        "sumActive": 583,
-	        "sumMinHigh": -10000,
-	        "sumMaxHigh": 12,
-	        "SumMinChew": 10,
-	        "beforeThreeSumRumina": 201,
-	        "beforeThreeSumIntake": 245,
-	        "score": 95,
-	        "isMaxTime": 2,
-	        "isShow": 1,
-	        "recordCount": 3,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740466900,
-	        "updatedAt": 1740466958
-	    },
-	    {
-	        "id": 1725968,
-	        "pastureId": 1,
-	        "neckRingNumber": "10027",
-	        "cowId": 30,
-	        "lact": 0,
-	        "calvingAge": 0,
-	        "activeTime": "2025-02-25 15:00:00",
-	        "frameid": 7,
-	        "heatDate": "2025-02-25",
-	        "rumina": 22,
-	        "intake": 0,
-	        "inactive": 60,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 89,
-	        "active": 6,
-	        "filterHigh": 69,
-	        "filterRumina": 15,
-	        "filterChew": 15,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 588,
-	        "weekRuminaHabit": 14,
-	        "weekIntakeHabit": 28,
-	        "weekChewHabit": 25,
-	        "weekInactiveHabit": 28,
-	        "weekOtherHabit": 0,
-	        "changeHigh": -42,
-	        "changeRumina": 7,
-	        "changeChew": -40,
-	        "changeAdjust": 0,
-	        "changeFilter": -10,
-	        "ruminaFilter": 2,
-	        "chewFilter": -12,
-	        "filterCorrect": 94,
-	        "sumRumina": 156,
-	        "sumIntake": 300,
-	        "sumInactive": 515,
-	        "sumActive": 677,
-	        "sumMinHigh": -10000,
-	        "sumMaxHigh": 20,
-	        "SumMinChew": 0,
-	        "beforeThreeSumRumina": 96,
-	        "beforeThreeSumIntake": 316,
-	        "score": 96,
-	        "isMaxTime": 2,
-	        "isShow": 1,
-	        "recordCount": 3,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740466925,
-	        "updatedAt": 1740466958
-	    },
-	    {
-	        "id": 1725973,
-	        "pastureId": 1,
-	        "neckRingNumber": "10028",
-	        "cowId": 84,
-	        "lact": 2,
-	        "calvingAge": 300,
-	        "activeTime": "2025-02-25 15:00:00",
-	        "frameid": 7,
-	        "heatDate": "2025-02-25",
-	        "rumina": 14,
-	        "intake": 36,
-	        "inactive": 12,
-	        "gasp": 0,
-	        "other": 0,
-	        "high": 1541,
-	        "active": 50,
-	        "filterHigh": 1187,
-	        "filterRumina": 10,
-	        "filterChew": 34,
-	        "weekHigh": 1500,
-	        "weekHighHabit": 203,
-	        "weekRuminaHabit": 14,
-	        "weekIntakeHabit": 36,
-	        "weekChewHabit": 16,
-	        "weekInactiveHabit": 36,
-	        "weekOtherHabit": 0,
-	        "changeHigh": 86,
-	        "changeRumina": -29,
-	        "changeChew": 113,
-	        "changeAdjust": 0,
-	        "changeFilter": 26,
-	        "ruminaFilter": -9,
-	        "chewFilter": 17,
-	        "filterCorrect": 95,
-	        "sumRumina": 127,
-	        "sumIntake": 231,
-	        "sumInactive": 791,
-	        "sumActive": 567,
-	        "sumMinHigh": -10000,
-	        "sumMaxHigh": 16,
-	        "SumMinChew": 0,
-	        "beforeThreeSumRumina": 134,
-	        "beforeThreeSumIntake": 243,
-	        "score": 100,
-	        "isMaxTime": 2,
-	        "isShow": 1,
-	        "recordCount": 3,
-	        "firmwareVersion": 57,
-	        "createdAt": 1740466940,
-	        "updatedAt": 1740466958
-	    }
-	]`
-
-	if err := json.Unmarshal([]byte(str), &neckActiveHabitList); err != nil {
-		panic(err)
-	}
-
-	for _, habit := range neckActiveHabitList {
-		cft := calculateCFT(habit)
-		fmt.Println(habit.Id, cft)
-	}*/
-
 	activeTimeParse, _ := time.Parse(model.LayoutTime, "2025-03-04 01:00:00")
 	println(activeTimeParse.Format(model.LayoutTime))
 }

+ 4 - 18
module/crontab/neck_ring_merge.go

@@ -37,10 +37,6 @@ func (e *Entry) NeckRingOriginalMerge() (err error) {
 		e.DB.Model(new(model.NeckRingOriginal)).
 			Where("created_at < ?", newTime.AddDate(0, -1, 0).Unix()).
 			Delete(new(model.NeckRingOriginal))
-		// 活动数据删除6个月前的数据
-		e.DB.Model(new(model.NeckActiveHabit)).
-			Where("created_at < ?", newTime.AddDate(0, -2, 0).Unix()).
-			Delete(new(model.NeckActiveHabit))
 	}
 
 	pastureList := e.FindPastureList()
@@ -211,15 +207,6 @@ func (e *Entry) againRecalculate(data *model.NeckActiveHabit) *model.NeckActiveH
 		return nil
 	}
 
-	/*if err := e.DB.Model(new(model.NeckRingOriginal)).
-		Where("pasture_id = ?", data.PastureId).
-		Where("neck_ring_number = ?", data.NeckRingNumber).
-		Where("active_date = ?", data.HeatDate).
-		Where("frameid IN (?)", frameIds).
-		Find(&originalList).Error; err != nil {
-		return nil
-	}*/
-
 	originalList = RemoveDuplicates(originalList)
 	newDataList := Recalculate(originalList)
 
@@ -258,15 +245,14 @@ func calculateScore(habit *model.NeckActiveHabit) int {
 
 	// 第二部分逻辑
 	var part2 float64
-	switch {
-	case habit.FirmwareVersion%100 >= 52:
+	versionMod := habit.FirmwareVersion % 100
+	if versionMod >= 52 {
 		part2 = 1
-	case habit.FirmwareVersion%100 >= 30 && habit.FirmwareVersion%100 <= 43:
+	} else if versionMod >= 30 && versionMod <= 43 {
 		part2 = 0.8
-	default:
+	} else {
 		part2 = 0.6
 	}
-
 	// 最终 score
 	return DefaultScore + int(math.Floor(part1*part2))
 }

+ 3 - 7
module/crontab/pen_behavior.go

@@ -72,7 +72,7 @@ func (e *Entry) PenBehavior(pastureId, maxPenBehavior int64) {
 func (e *Entry) getNeckRingOriginalList(pastureId, maxPenBehavior int64) ([]*model.PenBehaviorModel, error) {
 	var penBehaviorModelList []*model.PenBehaviorModel
 	if err := e.DB.Table(fmt.Sprintf("%s as h", new(model.NeckRingOriginal).TableName())).
-		Joins("JOIN cow as c ON h.pasture_id = c.pasture_id AND h.neck_ring_number = c.neck_ring_number").
+		Joins("INNER JOIN cow as c ON h.pasture_id = c.pasture_id AND h.neck_ring_number = c.neck_ring_number").
 		Select("h.id,c.pasture_id, c.pen_id, c.pen_name, h.active_date, h.frameid, h.high, h.rumina, h.intake, h.inactive, h.gasp").
 		Where("h.id > ? AND h.pasture_id = ?", maxPenBehavior, pastureId).
 		Order("h.active_date,h.frameid").
@@ -158,10 +158,8 @@ func (e *Entry) savePenBehaviorData(penData map[string]*model.PenBehaviorData) e
 	for _, data := range penData {
 		// 构建活动时间
 		activeTime := e.calculateActiveTime(data.HeatDate, data.Frameid)
-
 		// 构建保存数据
 		penBehavior := model.NewPenBehavior(data, activeTime)
-
 		if e.isExistByPenBehavior(data.PastureId, data.HeatDate, data.PenId, data.Frameid) {
 			historyData := e.findPenBehavior(data.PastureId, data.HeatDate, data.PenId, data.Frameid)
 			if historyData == nil || historyData.Id <= 0 {
@@ -193,8 +191,6 @@ func (e *Entry) savePenBehaviorData(penData map[string]*model.PenBehaviorData) e
 			}
 			continue
 		}
-
-		// 使用 Upsert 操作
 		if err := e.DB.Model(new(model.PenBehavior)).
 			Create(penBehavior).Error; err != nil {
 			zaplog.Error("savePenBehaviorData", zap.Any("penBehavior", penBehavior), zap.Any("err", err))
@@ -288,7 +284,7 @@ func (e *Entry) UpdatePenBehaviorWeekData(pastureId int64) {
 					"week_gasp_rate":   int32(float64(stats.SumGasp) / float64(stats.CowCount)),
 					"rumina_std":       int32(calculateStd(stats.RuminaRate)),
 					"intake_std":       int32(calculateStd(stats.IntakeRate)),
-					"rest_std":         int32(calculateStd(stats.RuminaRate)),
+					"rest_std":         int32(calculateStd(stats.RestRate)),
 					"gasp_std":         int32(calculateStd(stats.GaspRate)),
 					"is_show":          pasturePb.IsShow_Ok,
 				}).Error; err != nil {
@@ -373,7 +369,7 @@ func (e *Entry) calculateActiveTime(heatDate string, frameid int32) string {
 func (e *Entry) isExistByPenBehavior(pastureId int64, heatDate string, penId int32, frameid int32) bool {
 	var count int64
 	if err := e.DB.Model(new(model.PenBehavior)).
-		Where("pasture_id = ? AND heat_date = ? AND frameid = ? AND pen_id = ?", pastureId, heatDate, penId, frameid).
+		Where("pasture_id = ? AND heat_date = ? AND frameid = ? AND pen_id = ?", pastureId, heatDate, frameid, penId).
 		Count(&count).Error; err != nil {
 		return false
 	}

+ 38 - 0
module/crontab/twenty_one_pregnant_rate.go

@@ -0,0 +1,38 @@
+package crontab
+
+import (
+	"kpt-pasture/model"
+	"time"
+
+	pasturePb "gitee.com/xuyiping_admin/go_proto/proto/go/backend/cow"
+	"gitee.com/xuyiping_admin/pkg/logger/zaplog"
+	"go.uber.org/zap"
+)
+
+func (e *Entry) TwentyOnePregnantRate() error {
+	pastureList := e.FindPastureList()
+	for _, pasture := range pastureList {
+		e.TwentyOnePregnantHandle(pasture.Id)
+	}
+	return nil
+}
+
+func (e *Entry) TwentyOnePregnantHandle(pastureId int64) {
+	nowTime := time.Now().Local().Format(model.LayoutDate2)
+	cowList := make([]*model.Cow, 0)
+	if err := e.DB.Model(new(model.Cow)).
+		Where("pasture_id = ?", pastureId).
+		Where("sex = ?", pasturePb.Genders_Female).
+		Find(&cowList).Error; err != nil {
+		zaplog.Error("TwentyOnePregnantHandle", zap.Any("err", err), zap.Any("pastureId", pastureId))
+		return
+	}
+	everyDayCalvingList := model.NewEveryDayCalvingList(pastureId, nowTime, cowList)
+	if len(everyDayCalvingList) > 0 {
+		if err := e.DB.Model(new(model.CowCalving)).
+			Create(&everyDayCalvingList).Error; err != nil {
+			zaplog.Error("TwentyOnePregnantHandle", zap.Any("err", err), zap.Any("pastureId", pastureId))
+			return
+		}
+	}
+}

+ 26 - 0
service/alert/alert.go

@@ -0,0 +1,26 @@
+package alert
+
+import (
+	"kpt-pasture/config"
+
+	"gitee.com/xuyiping_admin/pkg/alert"
+)
+
+type Alert struct {
+	Email *alert.EmailConfig
+}
+
+func NewAlert(cfg *config.AppConfig) *Alert {
+	// 从配置中获取邮件配置
+	emailConfig := alert.NewEmailConfig(
+		cfg.EmailConfig.Host,
+		cfg.EmailConfig.Port,
+		cfg.EmailConfig.Username,
+		cfg.EmailConfig.Password,
+		cfg.EmailConfig.From,
+		cfg.EmailConfig.To,
+	)
+	return &Alert{
+		Email: emailConfig,
+	}
+}

+ 0 - 3
util/util.go

@@ -209,11 +209,8 @@ func Get21DayPeriods(startDay, endDay string) ([][]string, error) {
 
 	var periods [][]string
 	for date := endDate; date.After(startDate); {
-		// Calculate the end of the current period
 		periodEnd := date.AddDate(0, 0, -20)
-		// Append the current period to the result slice
 		periods = append(periods, []string{periodEnd.Format(Layout), date.Format(Layout)})
-		// Move on to the next day
 		date = periodEnd.AddDate(0, 0, -1)
 	}
 	reverseRows(periods)