package service import ( "XT_New/models" "database/sql" "fmt" "github.com/jinzhu/gorm" "reflect" "strings" "time" ) func GetDialysisTotalDatas() { } func GetNewDialysiTotal(startime int64, endtime int64, orgid int64, origin int64) (int64, error) { counts := models.PatientPrescriptionCountStruct{} var err error if origin == 1 { //透析记录,上机为准 db := XTReadDB().Table("xt_dialysis_order as x").Joins("join xt_dialysis_prescription p on p.patient_id = x.patient_id and p.record_date = x.dialysis_date") err = db.Select("count(x.id) as count").Where("x.dialysis_date >= ? and x.dialysis_date<=? and x.user_org_id = ? AND x.status = 1", startime, endtime, orgid).Scan(&counts).Error return counts.Count, err } else { var count int64 var schs []models.Schedule db := XTReadDB().Model(&models.Schedule{}) err := db. Group("patient_id, schedule_date"). Where("schedule_date >= ? AND schedule_date <= ? and user_org_id = ? and status = 1", startime, endtime, orgid). Find(&schs). Error count = int64(len(schs)) return count, err } } type TreatmentMode struct { ModeID int `json:"mode_id"` ModeName string `json:"mode_name"` } type DialysisStat struct { Date string `json:"日期"` Counts map[string]int `json:"counts"` Total int `json:"合计"` } func GetTreatmentModes() ([]models.TreatmentMode, error) { var modes []models.TreatmentMode if err := XTReadDB().Model(&models.TreatmentMode{}).Find(&modes).Error; err != nil { return nil, err } return modes, nil } func GetDialysisStats(start int64, end int64, mode int64, org_id int64, time_way int64) ([]map[string]interface{}, error) { // 将时间戳转换为time.Time类型 t := time.Unix(start, 0) // 使用布局定义格式化时间 layout := "2006-01-02" // 将时间格式化为字符串 startDate := t.Format(layout) + " 00:00:00" t2 := time.Unix(end, 0) // 使用布局定义格式化时间 //layout := "2006-01-02" // 将时间格式化为字符串 endDate := t2.Format(layout) + " 00:00:00" //var stats []DialysisStat var modes []models.TreatmentMode fmt.Println(mode) if mode == 0 { modes, _ = GetTreatmentModes() } else { modes_two, _ := GetTreatmentModes() for _, item := range modes_two { if item.ModeID == mode { modes = append(modes, item) } } } // 获取透析模式 if err != nil { return nil, err } var selectClauses []string // 构建动态查询语句 if time_way == 1 { //selectClauses = []string{fmt.Sprintf("'%s' AS `日期`", strings.Split(startDate, " ")[0])} selectClauses = []string{fmt.Sprintf("'%s' AS `日期`", strings.Split(startDate, " ")[0]+"~"+strings.Split(endDate, " ")[0])} } else if time_way == 3 { selectClauses = []string{fmt.Sprintf("'%s' AS `日期`", strings.Split(startDate, " ")[0]+"~"+strings.Split(endDate, " ")[0])} //selectClauses = []string{fmt.Sprintf("'%s' AS `日期`", strings.Split(strings.Split(startDate, " ")[0], "-")[0]+"-"+strings.Split(strings.Split(startDate, " ")[0], "-")[1])} } else if time_way == 4 { selectClauses = []string{fmt.Sprintf("'%s' AS `日期`", strings.Split(startDate, " ")[0]+"~"+strings.Split(endDate, " ")[0])} //selectClauses = []string{fmt.Sprintf("'%s' AS `日期`", strings.Split(strings.Split(startDate, " ")[0], "-")[0])} } else { selectClauses = []string{fmt.Sprintf("'%s' AS `日期`", strings.Split(startDate, " ")[0]+"~"+strings.Split(endDate, " ")[0])} } for _, mode := range modes { fmt.Println(mode) selectClauses = append(selectClauses, fmt.Sprintf("COALESCE(SUM(CASE WHEN t.name = '%s' THEN 1 ELSE 0 END), 0) AS `%s`", mode.Name, mode.Name)) } selectClauses = append(selectClauses, "COUNT(*) AS `合计`") var rows *sql.Rows var query string if mode > 0 { query = fmt.Sprintf(` SELECT %s FROM xt_dialysis_prescription p JOIN xt_treatment_mode t ON p.mode_id = t.mode_id WHERE FROM_UNIXTIME(p.record_date) >= ? AND FROM_UNIXTIME(p.record_date) <= ? AND p.user_org_id = ? and p.mode_id = ? GROUP BY 日期 `, strings.Join(selectClauses, ", ")) rows, _ = readDb.Raw(query, startDate, endDate, org_id, mode).Rows() } else { query = fmt.Sprintf(` SELECT %s FROM xt_dialysis_prescription p JOIN xt_treatment_mode t ON p.mode_id = t.mode_id WHERE FROM_UNIXTIME(p.record_date) >= ? AND FROM_UNIXTIME(p.record_date) <= ? AND p.user_org_id = ? GROUP BY 日期 `, strings.Join(selectClauses, ", ")) rows, _ = readDb.Raw(query, startDate, endDate, org_id).Rows() } if err != nil { return nil, err } defer rows.Close() columns, err := rows.Columns() if err != nil { return nil, err } var results []map[string]interface{} for rows.Next() { // 创建一个长度为列数的切片,用于存储每一行的值 columnValues := make([]interface{}, len(columns)) columnPointers := make([]interface{}, len(columns)) for i := range columnValues { columnPointers[i] = &columnValues[i] } // 扫描当前行的值 if err := rows.Scan(columnPointers...); err != nil { return nil, err } // 将扫描到的值放入结果 map 中 result := make(map[string]interface{}) for i, colName := range columns { val := columnPointers[i].(*interface{}) result[colName] = *val } results = append(results, result) } //// 解析查询结果 //for rows.Next() { // var stat DialysisStat // stat.Counts = make(map[string]int) // cols := []interface{}{&stat.Date} // for _, mode := range modes { // var count int // cols = append(cols, &count) // stat.Counts[mode.Name] = count // } // var total int // cols = append(cols, &total) // stat.Total = total // if err := rows.Scan(cols...); err != nil { // return nil, err // } // stats = append(stats, stat) //} return results, nil } func GetScheduleStats(start int64, end int64, mode int64, org_id int64, time_way int64) ([]map[string]interface{}, error) { // 将时间戳转换为time.Time类型 t := time.Unix(start, 0) // 使用布局定义格式化时间 layout := "2006-01-02" // 将时间格式化为字符串 startDate := t.Format(layout) + " 00:00:00" t2 := time.Unix(end, 0) // 使用布局定义格式化时间 //layout := "2006-01-02" // 将时间格式化为字符串 endDate := t2.Format(layout) + " 00:00:00" //var stats []DialysisStat var modes []models.TreatmentMode fmt.Println(mode) if mode == 0 { modes, _ = GetTreatmentModes() } else { modes_two, _ := GetTreatmentModes() for _, item := range modes_two { if item.ModeID == mode { modes = append(modes, item) } } } // 获取透析模式 if err != nil { return nil, err } var selectClauses []string // 构建动态查询语句 if time_way == 1 { selectClauses = []string{fmt.Sprintf("'%s' AS `日期`", strings.Split(startDate, " ")[0])} } else if time_way == 3 { selectClauses = []string{fmt.Sprintf("'%s' AS `日期`", strings.Split(strings.Split(startDate, " ")[0], "-")[0]+strings.Split(strings.Split(startDate, " ")[0], "-")[1])} } else if time_way == 4 { selectClauses = []string{fmt.Sprintf("'%s' AS `日期`", strings.Split(strings.Split(startDate, " ")[0], "-")[0])} } else { selectClauses = []string{fmt.Sprintf("'%s' AS `日期`", strings.Split(startDate, " ")[0]+"~"+strings.Split(endDate, " ")[0])} } for _, mode := range modes { fmt.Println(mode) selectClauses = append(selectClauses, fmt.Sprintf("COALESCE(SUM(CASE WHEN t.name = '%s' THEN 1 ELSE 0 END), 0) AS `%s`", mode.Name, mode.Name)) } selectClauses = append(selectClauses, "COUNT(*) AS `合计`") var rows *sql.Rows var query string if mode > 0 { query = fmt.Sprintf(` SELECT %s FROM xt_schedule p JOIN xt_treatment_mode t ON p.mode_id = t.mode_id WHERE FROM_UNIXTIME(p.schedule_date) >= ? AND FROM_UNIXTIME(p.schedule_date) <= ? AND p.user_org_id = ? and p.mode_id = ? GROUP BY 日期 `, strings.Join(selectClauses, ", ")) rows, _ = readDb.Raw(query, startDate, endDate, org_id, mode).Rows() } else { query = fmt.Sprintf(` SELECT %s FROM xt_schedule p JOIN xt_treatment_mode t ON p.mode_id = t.mode_id WHERE FROM_UNIXTIME(p.schedule_date) >= ? AND FROM_UNIXTIME(p.schedule_date) <= ? AND p.user_org_id = ? GROUP BY 日期 `, strings.Join(selectClauses, ", ")) rows, _ = readDb.Raw(query, startDate, endDate, org_id).Rows() } if err != nil { return nil, err } defer rows.Close() columns, err := rows.Columns() if err != nil { return nil, err } var results []map[string]interface{} for rows.Next() { // 创建一个长度为列数的切片,用于存储每一行的值 columnValues := make([]interface{}, len(columns)) columnPointers := make([]interface{}, len(columns)) for i := range columnValues { columnPointers[i] = &columnValues[i] } // 扫描当前行的值 if err := rows.Scan(columnPointers...); err != nil { return nil, err } // 将扫描到的值放入结果 map 中 result := make(map[string]interface{}) for i, colName := range columns { val := columnPointers[i].(*interface{}) result[colName] = *val } results = append(results, result) } //// 解析查询结果 //for rows.Next() { // var stat DialysisStat // stat.Counts = make(map[string]int) // cols := []interface{}{&stat.Date} // for _, mode := range modes { // var count int // cols = append(cols, &count) // stat.Counts[mode.Name] = count // } // var total int // cols = append(cols, &total) // stat.Total = total // if err := rows.Scan(cols...); err != nil { // return nil, err // } // stats = append(stats, stat) //} return results, nil } //func GetScheduleStats(startDate int64, endDate int64, groupBy int64, mode int64, org_id int64) ([]DialysisStat, error) { // var stats []DialysisStat // var modes []models.TreatmentMode // if mode > 0 { // modes, _ = GetTreatmentModes() // } else { // modes_two, _ := GetTreatmentModes() // for _, item := range modes_two { // if item.ModeID == mode { // modes = append(modes, item) // } // } // } // // 获取透析模式 // if err != nil { // return nil, err // } // // // 构建日期格式 // dateFormat := "%Y-%m-%d" // switch groupBy { // case 2: // dateFormat = "%Y-%m-%d" // case 1: // dateFormat = "%Y-%u" // case 3: // dateFormat = "%Y-%m" // case 4: // dateFormat = "%Y" // default: // return nil, fmt.Errorf("invalid group by option") // } // // 构建动态查询语句 // selectClauses := []string{fmt.Sprintf("DATE_FORMAT(p.schudle_date, '%s') AS `日期`", dateFormat)} // for _, mode := range modes { // selectClauses = append(selectClauses, fmt.Sprintf("SUM(CASE WHEN t.mode_name = '%s' THEN 1 ELSE 0 END) AS `%s`", mode.Name, mode.Name)) // } // selectClauses = append(selectClauses, "COUNT(*) AS `合计`") // // query := fmt.Sprintf(` // SELECT // %s // FROM // xt_schedule p // JOIN // xt_treatment_mode t ON p.mode_id = t.mode_id // WHERE // p.schedule_date >= ? AND p.schedule_date <= ? // GROUP BY // DATE_FORMAT(p.schedule_date, '%s') // `, dateFormat, dateFormat, selectClauses) // // rows, err := readDb.Raw(query, startDate, endDate).Rows() // if err != nil { // return nil, err // } // defer rows.Close() // // // 解析查询结果 // for rows.Next() { // var stat DialysisStat // stat.Counts = make(map[string]int) // cols := []interface{}{&stat.Date} // for _, mode := range modes { // var count int // cols = append(cols, &count) // stat.Counts[mode.Name] = count // } // var total int // cols = append(cols, &total) // stat.Total = total // if err := rows.Scan(cols...); err != nil { // return nil, err // } // stats = append(stats, stat) // } // // return stats, nil //} func GetNewDialysisCountMode(starttime int64, endtime int64, orgid int64, origin int64, mode_id int64) (counts []*models.PatientPrescriptionCountStruct, err error) { if origin == 1 { db := readDb.Table("xt_dialysis_order as o").Where("o.status = 1") if starttime > 0 { db = db.Where("o.dialysis_date >=?", starttime) } if endtime > 0 { db = db.Where("o.dialysis_date<=?", endtime) } if orgid > 0 { db = db.Where("o.user_org_id = ?", orgid) } if mode_id == 0 { err = db.Select("s.mode_id,count(s.mode_id) as count").Joins("join xt_dialysis_prescription as s on s.patient_id = o.patient_id and s.record_date = o.dialysis_date and s.status= 1 AND s.record_date >= ? AND s.record_date <= ? AND s.mode_id > 0 ", starttime, endtime).Group("s.mode_id").Scan(&counts).Error } else { err = db.Select("s.mode_id,count(s.mode_id) as count").Joins("join xt_dialysis_prescription as s on s.patient_id = o.patient_id and s.record_date = o.dialysis_date and s.status= 1 AND s.record_date >= ? AND s.record_date <= ? AND s.mode_id = ? ", starttime, endtime, mode_id).Group("s.mode_id").Scan(&counts).Error } return counts, err } else { err = readDb.Raw("select mode_id, count(aa.`mode_id`) as count from xt_schedule aa join (SELECT DISTINCT o.patient_id, o.`schedule_date` FROM xt_schedule AS o WHERE o.status = 1 AND o.schedule_date >= ? AND o.schedule_date <= ? AND o.user_org_id = ?) as b on aa.`patient_id` = b.`patient_id` and aa.`schedule_date` = b.`schedule_date` where aa.`status` = 1 and aa.schedule_date >= ? AND aa.schedule_date <= ? AND aa.user_org_id = ? Group by aa.`mode_id`", starttime, endtime, orgid, starttime, endtime, orgid).Find(&counts).Error return counts, err } } func GetNewDialysisCountModeTwo(starttime int64, endtime int64, orgid int64, origin int64, mode_id int64) (counts models.CustomDialysisData, err error) { // 将时间戳转换为time.Time类型 t := time.Unix(starttime, 0) // 使用布局定义格式化时间 layout := "2006-01-02" // 将时间格式化为字符串 startDate := t.Format(layout) + " 00:00:00" t2 := time.Unix(endtime, 0) // 使用布局定义格式化时间 //layout := "2006-01-02" // 将时间格式化为字符串 endDate := t2.Format(layout) + " 00:00:00" //fmt.Println(formattedDate) // 将日期字符串解析为time.Time类型 //start, _ := time.Parse("2006-01-02 15:04:05", formattedDate) //starttime = start.Unix() //fmt.Println(starttime) if origin == 1 { db := readDb.Table("xt_dialysis_order as o").Where("o.status = 1") if starttime > 0 { db = db.Where("DATE_FORMAT(FROM_UNIXTIME(o.dialysis_date), '%Y-%m-%d %H:%i:%s') >= ?", startDate) } if endtime > 0 { db = db.Where("DATE_FORMAT(FROM_UNIXTIME(o.dialysis_date), '%Y-%m-%d %H:%i:%s') <= ?", endDate) } if orgid > 0 { db = db.Where("o.user_org_id = ?", orgid) } err = db.Select("s.mode_id,count(s.mode_id) as count").Joins("join xt_dialysis_prescription as s on s.patient_id = o.patient_id and s.record_date = o.dialysis_date and s.status= 1 AND DATE_FORMAT(FROM_UNIXTIME(s.record_date), '%Y-%m-%d %H:%i:%s') >= ? AND DATE_FORMAT(FROM_UNIXTIME(s.record_date), '%Y-%m-%d %H:%i:%s') <= ? AND s.mode_id = ? ", startDate, endDate, mode_id).Group("s.mode_id").Scan(&counts).Error return counts, err } else { db := readDb.Table("xt_schedule as o").Where("o.status = 1").Select("patient_id, schedule_date").Group("mode_id") if starttime > 0 { db = db.Where("DATE_FORMAT(FROM_UNIXTIME(o.schedule_date),'%Y-%m-%d %H:%i:%s') >= ?", startDate) } if endtime > 0 { db = db.Where("DATE_FORMAT(FROM_UNIXTIME(o.schedule_date),'%Y-%m-%d %H:%i:%s') <= ?", endDate) } if orgid > 0 { db = db.Where("o.user_org_id = ?", orgid) } if mode_id > 0 { db = db.Where("o.mode_id = ?", mode_id) } err = db.Select("o.mode_id,count(o.mode_id) as count").Scan(&counts).Error return counts, err } } var anticoagulantMap = map[int]string{ 1: "无肝素", 2: "普通肝素", 3: "低分子肝素", 4: "阿加曲班", 5: "枸橼酸钠", 6: "低分子肝素钙", 7: "低分子肝素钠", 8: "依诺肝素", 9: "达肝素", 10: "体外抗凝", 11: "那屈肝素", 12: "无抗凝剂", 13: "那屈肝素钙", 14: "肝素钙注射液", 15: "甲磺酸萘莫司他", 16: "低分子量肝素钙", 17: "肝素钠", } func GetAnticoagulantData(start_time int64, end_time int64, org_id int64) (map[string]int, error) { var results []struct { Anticoagulant int Count int } err := XTReadDB().Model(&models.DialysisPrescription{}). Select("anticoagulant, COUNT(*) as count"). Where("status = 1 and record_date >= ? and record_date <= ? and user_org_id = ?", start_time, end_time, org_id). Group("anticoagulant"). Scan(&results).Error if err != nil { return nil, err } anticoagulantData := make(map[string]int) for _, result := range results { if name, ok := anticoagulantMap[result.Anticoagulant]; ok { anticoagulantData[name] = result.Count } else { anticoagulantData[fmt.Sprintf("Unknown (%d)", result.Anticoagulant)] = result.Count } } return anticoagulantData, nil } func GetAnticoagulantTotal(start_time int64, end_time int64, org_id int64) (total int64, err error) { err = XTReadDB().Model(&models.DialysisPrescription{}). Where("record_date >= ? and record_date <= ? and user_org_id = ? and status = 1", start_time, end_time, org_id). Count(&total).Error return } func GetDialyzerSummary(org_id int64) ([]string, error) { var Dialyzer []string err := XTReadDB().Model(&models.DialysisPrescription{}). Select("dialysis_dialyszers"). Where(" user_org_id = ? and status = 1", org_id). Group("dialysis_dialyszers"). Scan(&Dialyzer).Error if err != nil { return nil, err } return Dialyzer, nil } type DialyzerResult struct { Dialyzer string Count int } func GetDialyzerData(start_time int64, end_time int64, org_id int64) (dr []DialyzerResult, err error) { err = XTReadDB().Model(&models.DialysisPrescription{}). Select("dialysis_dialyszers as dialyzer, COUNT(*) as count"). Where("record_date >= ? and record_date <= ? and user_org_id = ? and status = 1", start_time, end_time, org_id). Group("dialysis_dialyszers"). Scan(&dr).Error return } func GetDialyzerTotal(start_time int64, end_time int64, org_id int64) (total int64, err error) { err = XTReadDB().Model(&models.DialysisPrescription{}). Where("status = 1 and record_date >= ? and record_date <= ? and user_org_id = ? and dialysis_dialyszers <> ''", start_time, end_time, org_id). Count(&total).Error return } func GetPrescriptionByAnticoagulant(page int64, limit int64, orgid int64, anticoagulant int64, start_time int64, end_time int64) (solution []*models.DialysisPrescription, total int64, err error) { db := XTReadDB().Model(&models.DialysisPrescription{}).Where("status = 1") if anticoagulant > 0 { db = db.Where("anticoagulant = ?", anticoagulant) } if orgid > 0 { db = db.Where("user_org_id = ?", orgid) } db = db.Where("record_date >= ? and record_date <= ?", start_time, end_time) offset := (page - 1) * limit err = db.Count(&total).Offset(offset).Limit(limit).Find(&solution).Error return solution, total, err } func GetPrescriptionByDialyzer(page int64, limit int64, orgid int64, dialyzer string, start_time int64, end_time int64) (solution []*models.DialysisPrescription, total int64, err error) { db := XTReadDB().Model(&models.DialysisPrescription{}).Where("status = 1") if len(dialyzer) > 0 { db = db.Where("dialysis_dialyszers = ?", dialyzer) } if orgid > 0 { db = db.Where("user_org_id = ?", orgid) } db = db.Where("record_date >= ? and record_date <= ?", start_time, end_time) offset := (page - 1) * limit err = db.Count(&total).Offset(offset).Limit(limit).Find(&solution).Error return solution, total, err } type DialysisData struct { DialysisStatus string `json:"dialysis_status"` Count int `json:"count"` } type CustomData struct { DialysisNo string PatientName string DialysisDate string DialysisDuration string ActualDuration string Diff string Doctor string Nurse string } func GetDialysisCompletionRate(org_id int64, start_time int64, end_time int64) (map[string]int, error) { var results []DialysisData query := ` SELECT CASE WHEN ABS(TIMESTAMPDIFF(MINUTE, MAKETIME(p.dialysis_duration_hour, p.dialysis_duration_minute, 0), MAKETIME(a.actual_treatment_hour, a.actual_treatment_minute, 0))) <= 15 THEN '达标' WHEN TIMESTAMPDIFF(MINUTE, MAKETIME(p.dialysis_duration_hour, p.dialysis_duration_minute, 0), MAKETIME(a.actual_treatment_hour, a.actual_treatment_minute, 0)) < 0 THEN '未达标' ELSE '超时' END AS dialysis_status, COUNT(*) AS count FROM xt_dialysis_order o JOIN xt_dialysis_prescription p ON o.dialysis_date = p.record_date AND o.patient_id = p.patient_id AND p.user_org_id = ? JOIN xt_assessment_after_dislysis a ON o.dialysis_date = a.assessment_date AND o.patient_id = a.patient_id AND a.user_org_id = ? WHERE o.stage = 2 AND o.user_org_id = ? AND o.dialysis_date >= ? AND o.dialysis_date <= ? GROUP BY dialysis_status; ` if err := readDb.Raw(query, org_id, org_id, org_id, start_time, end_time).Scan(&results).Error; err != nil { return nil, err } dialysisCompletionRate := make(map[string]int) for _, result := range results { dialysisCompletionRate[result.DialysisStatus] = result.Count } return dialysisCompletionRate, nil } func GetDialysisCompletionTotal(org_id int64, start_time int64, end_time int64) (int64, error) { var Count int64 query := ` SELECT COUNT(*) AS count FROM xt_dialysis_order o JOIN xt_dialysis_prescription p ON o.dialysis_date = p.record_date AND o.patient_id = p.patient_id AND p.user_org_id = ? JOIN xt_assessment_after_dislysis a ON o.dialysis_date = a.assessment_date AND o.patient_id = a.patient_id AND a.user_org_id = ? WHERE o.stage = 2 AND o.user_org_id = ? AND o.dialysis_date >= ? AND o.dialysis_date <= ? ` if err := readDb.Raw(query, org_id, org_id, org_id, start_time, end_time).Count(&Count).Error; err != nil { return 0, err } return Count, nil } func GetDialysisCompletionDetail(org_id int64, start_time int64, end_time int64, mode int64, limit int64, page int64) (results []interface{}, total int64, err error) { var query string if mode == 0 { query = ` SELECT p.dialysis_no as dialysis_no, p.name as patient_name, FROM_UNIXTIME(o.dialysis_date) as dialysis_date, CONCAT(p.dialysis_duration_hour, 'h', p.dialysis_duration_minute,'min') as dialysis_duration, CONCAT(a.actual_treatment_hour, 'h', a.actual_treatment_minute,'min') as actual_duration, ABS(TIMESTAMPDIFF(MINUTE, MAKETIME(p.dialysis_duration_hour, p.dialysis_duration_minute, 0), MAKETIME(a.actual_treatment_hour, a.actual_treatment_minute, 0))) as diff, p.prescription_doctor as doctor, o.finish_nurse as nurse FROM xt_dialysis_order o JOIN xt_patients pp ON o.patient_id = pp.id AND pp.user_org_id = ? JOIN xt_dialysis_prescription p ON o.dialysis_date = p.record_date AND o.patient_id = p.patient_id AND p.user_org_id = ? JOIN xt_assessment_after_dislysis a ON o.dialysis_date = a.assessment_date AND o.patient_id = a.patient_id AND a.user_org_id = ? WHERE o.stage = 2 AND o.user_org_id = ? AND o.dialysis_date >= ? AND o.dialysis_date <= ? ` readDb.Table("xt_dialysis_order o"). Joins("JOIN xt_patients pp ON o.patient_id = pp.id AND pp.user_org_id = ?", org_id). Joins("JOIN xt_dialysis_prescription p ON o.dialysis_date = p.record_date AND o.patient_id = p.patient_id AND p.user_org_id = ?", org_id). Joins("JOIN xt_assessment_after_dislysis a ON o.dialysis_date = a.assessment_date AND o.patient_id = a.patient_id AND a.user_org_id = ?", org_id). Where("o.stage = 2 AND o.user_org_id = ? AND o.dialysis_date >= ? AND o.dialysis_date <= ?", org_id, start_time, end_time).Count(&total) } else if mode == 1 { query = ` SELECT pp.dialysis_no as dialysis_no, pp.name as patient_name, FROM_UNIXTIME(o.dialysis_date) as dialysis_date, CONCAT(p.dialysis_duration_hour, 'h', p.dialysis_duration_minute,'min') as dialysis_duration, CONCAT(a.actual_treatment_hour, 'h', a.actual_treatment_minute,'min') as actual_duration, ABS(TIMESTAMPDIFF(MINUTE, MAKETIME(p.dialysis_duration_hour, p.dialysis_duration_minute, 0), MAKETIME(a.actual_treatment_hour, a.actual_treatment_minute, 0))) as diff, p.prescription_doctor as doctor, o.finish_nurse as nurse FROM xt_dialysis_order o JOIN xt_patients pp ON o.patient_id = pp.id AND pp.user_org_id = ? JOIN xt_dialysis_prescription p ON o.dialysis_date = p.record_date AND o.patient_id = p.patient_id AND p.user_org_id = ? JOIN xt_assessment_after_dislysis a ON o.dialysis_date = a.assessment_date AND o.patient_id = a.patient_id AND a.user_org_id = ? WHERE o.stage = 2 AND o.user_org_id = ? AND o.dialysis_date >= ? AND o.dialysis_date <= ? AND ABS(TIMESTAMPDIFF(MINUTE, MAKETIME(p.dialysis_duration_hour, p.dialysis_duration_minute, 0), MAKETIME(a.actual_treatment_hour, a.actual_treatment_minute, 0))) <= 15 ` readDb.Table("xt_dialysis_order o"). Joins("JOIN xt_patients pp ON o.patient_id = pp.id AND pp.user_org_id = ?", org_id). Joins("JOIN xt_dialysis_prescription p ON o.dialysis_date = p.record_date AND o.patient_id = p.patient_id AND p.user_org_id = ?", org_id). Joins("JOIN xt_assessment_after_dislysis a ON o.dialysis_date = a.assessment_date AND o.patient_id = a.patient_id AND a.user_org_id = ?", org_id). Where("o.stage = 2 AND o.user_org_id = ? AND o.dialysis_date >= ? AND o.dialysis_date <= ? and ABS(TIMESTAMPDIFF(MINUTE, MAKETIME(p.dialysis_duration_hour, p.dialysis_duration_minute, 0), MAKETIME(a.actual_treatment_hour, a.actual_treatment_minute, 0))) <= 15", org_id, start_time, end_time).Count(&total) } else if mode == 2 { query = ` SELECT pp.dialysis_no as dialysis_no, pp.name as patient_name, FROM_UNIXTIME(o.dialysis_date) as dialysis_date, CONCAT(p.dialysis_duration_hour, 'h', p.dialysis_duration_minute,'min') as dialysis_duration, CONCAT(a.actual_treatment_hour, 'h', a.actual_treatment_minute,'min') as actual_duration, ABS(TIMESTAMPDIFF(MINUTE, MAKETIME(p.dialysis_duration_hour, p.dialysis_duration_minute, 0), MAKETIME(a.actual_treatment_hour, a.actual_treatment_minute, 0))) as diff, p.prescription_doctor as doctor, o.finish_nurse as nurse FROM xt_dialysis_order o JOIN xt_patients pp ON o.patient_id = pp.id AND pp.user_org_id = ? JOIN xt_dialysis_prescription p ON o.dialysis_date = p.record_date AND o.patient_id = p.patient_id AND p.user_org_id = ? JOIN xt_assessment_after_dislysis a ON o.dialysis_date = a.assessment_date AND o.patient_id = a.patient_id AND a.user_org_id = ? WHERE o.stage = 2 AND o.user_org_id = ? AND o.dialysis_date >= ? AND o.dialysis_date <= ? AND TIMESTAMPDIFF(MINUTE, MAKETIME(p.dialysis_duration_hour, p.dialysis_duration_minute, 0), MAKETIME(a.actual_treatment_hour, a.actual_treatment_minute, 0)) < 0 ` readDb.Table("xt_dialysis_order o"). Joins("JOIN xt_patients pp ON o.patient_id = pp.id AND pp.user_org_id = ?", org_id). Joins("JOIN xt_dialysis_prescription p ON o.dialysis_date = p.record_date AND o.patient_id = p.patient_id AND p.user_org_id = ?", org_id). Joins("JOIN xt_assessment_after_dislysis a ON o.dialysis_date = a.assessment_date AND o.patient_id = a.patient_id AND a.user_org_id = ?", org_id). Where("o.stage = 2 AND o.user_org_id = ? AND o.dialysis_date >= ? AND o.dialysis_date <= ? and TIMESTAMPDIFF(MINUTE, MAKETIME(p.dialysis_duration_hour, p.dialysis_duration_minute, 0), MAKETIME(a.actual_treatment_hour, a.actual_treatment_minute, 0)) < 0", org_id, start_time, end_time).Count(&total) } else if mode == 3 { query = ` SELECT pp.dialysis_no as dialysis_no, pp.name as patient_name, FROM_UNIXTIME(o.dialysis_date) as dialysis_date, CONCAT(p.dialysis_duration_hour, 'h', p.dialysis_duration_minute,'min') as dialysis_duration, CONCAT(a.actual_treatment_hour, 'h', a.actual_treatment_minute,'min') as actual_duration, ABS(TIMESTAMPDIFF(MINUTE, MAKETIME(p.dialysis_duration_hour, p.dialysis_duration_minute, 0), MAKETIME(a.actual_treatment_hour, a.actual_treatment_minute, 0))) as diff, p.prescription_doctor as doctor, o.finish_nurse as nurse FROM xt_dialysis_order o JOIN xt_patients pp ON o.patient_id = pp.id AND pp.user_org_id = ? JOIN xt_dialysis_prescription p ON o.dialysis_date = p.record_date AND o.patient_id = p.patient_id AND p.user_org_id = ? JOIN xt_assessment_after_dislysis a ON o.dialysis_date = a.assessment_date AND o.patient_id = a.patient_id AND a.user_org_id = ? WHERE o.stage = 2 AND o.user_org_id = ? AND o.dialysis_date >= ? AND o.dialysis_date <= ? AND TIMESTAMPDIFF(MINUTE, MAKETIME(p.dialysis_duration_hour, p.dialysis_duration_minute, 0), MAKETIME(a.actual_treatment_hour, a.actual_treatment_minute, 0)) > 15 ` readDb.Table("xt_dialysis_order o"). Joins("JOIN xt_patients pp ON o.patient_id = pp.id AND pp.user_org_id = ?", org_id). Joins("JOIN xt_dialysis_prescription p ON o.dialysis_date = p.record_date AND o.patient_id = p.patient_id AND p.user_org_id = ?", org_id). Joins("JOIN xt_assessment_after_dislysis a ON o.dialysis_date = a.assessment_date AND o.patient_id = a.patient_id AND a.user_org_id = ?", org_id). Where("o.stage = 2 AND o.user_org_id = ? AND o.dialysis_date >= ? AND o.dialysis_date <= ? and TIMESTAMPDIFF(MINUTE, MAKETIME(p.dialysis_duration_hour, p.dialysis_duration_minute, 0), MAKETIME(a.actual_treatment_hour, a.actual_treatment_minute, 0)) > 15", org_id, start_time, end_time).Count(&total) } offset := (page - 1) * limit rows, err := readDb.Raw(query, org_id, org_id, org_id, org_id, start_time, end_time).Offset(offset).Limit(limit).Rows() if err != nil { fmt.Println(err) } defer rows.Close() // Define a map to hold the dynamic fields fields := map[string]interface{}{ "dialysis_no": "", "patient_name": "", "dialysis_date": "", "dialysis_duration": "", "actual_duration": "", "diff": 0, "doctor": "", "nurse": "", } // Create the dynamic struct type dynamicStructType := createDynamicStruct(fields) // Slice to hold the results //var results []interface{} // Iterate over the rows and scan into the dynamic struct for rows.Next() { // Create a new instance of the dynamic struct result := reflect.New(dynamicStructType).Interface() // Create a slice of pointers to the fields in the struct fieldPtrs := []interface{}{ reflect.ValueOf(result).Elem().FieldByName("Dialysis_no").Addr().Interface(), reflect.ValueOf(result).Elem().FieldByName("Patient_name").Addr().Interface(), reflect.ValueOf(result).Elem().FieldByName("Dialysis_date").Addr().Interface(), reflect.ValueOf(result).Elem().FieldByName("Dialysis_duration").Addr().Interface(), reflect.ValueOf(result).Elem().FieldByName("Actual_duration").Addr().Interface(), reflect.ValueOf(result).Elem().FieldByName("Diff").Addr().Interface(), reflect.ValueOf(result).Elem().FieldByName("Doctor").Addr().Interface(), reflect.ValueOf(result).Elem().FieldByName("Nurse").Addr().Interface(), } // Scan the row into the struct if err := rows.Scan(fieldPtrs...); err != nil { //log.Fatalf("failed to scan row: %v", err) fmt.Println(err) } // Append the result to the slice results = append(results, result) } return results, total, err } type QualityControlStandard struct { ItemName string `json:"item_name"` ProjectMame string `json:"project_name"` InspectionMajor int64 `json:"inspection_major"` InspectionMinor int64 `json:"inspection_minor"` } func getQualityControlStandards(org_id int64) ([]QualityControlStandard, error) { var standards []QualityControlStandard if err := readDb.Model(&models.XtQualityControlStandard{}).Select("re.project_name as project_name,re.item_name as item_name,xt_quality_control_standard.inspection_major as inspection_major,xt_quality_control_standard.inspection_minor as inspection_minor").Joins("join xt_inspection_reference re on re.project_id = xt_quality_control_standard.inspection_major and re.item_id = xt_quality_control_standard.inspection_minor and re.org_id = ?", org_id).Where("xt_quality_control_standard.user_org_id = ? and xt_quality_control_standard.status = 1", org_id).Scan(&standards).Error; err != nil { return nil, err } return standards, nil } type DialysisQualityStat struct { Month string `json:"月"` Name string `json:"姓名"` Counts map[string]float64 `json:"counts"` } func GetLatestInspectionValues(org_id int64, yearMonth string) ([]map[string]interface{}, error) { standards, err := getQualityControlStandards(org_id) if err != nil { return nil, err } var selectFields []string for _, standard := range standards { field := fmt.Sprintf("IFNULL(MAX(CASE WHEN i.item_name = %s THEN i.inspect_value END),'') AS `%s`", "'"+standard.ItemName+"'", standard.ItemName) selectFields = append(selectFields, field) } query := fmt.Sprintf(` SELECT p.name as '姓名', %s FROM xt_inspection i JOIN xt_patients p On p.id = i.patient_id WHERE DATE_FORMAT(FROM_UNIXTIME(i.inspect_date), '%%Y-%%m') = ? and org_id = ? GROUP BY i.patient_id `, strings.Join(selectFields, ", ")) var results []map[string]interface{} rows, err := readDb.Raw(query, yearMonth, org_id).Rows() if err != nil { return nil, err } defer rows.Close() columns, err := rows.Columns() if err != nil { return nil, err } for rows.Next() { // 创建一个长度为列数的切片,用于存储每一行的值 columnValues := make([]interface{}, len(columns)) columnPointers := make([]interface{}, len(columns)) for i := range columnValues { columnPointers[i] = &columnValues[i] } // 扫描当前行的值 if err := rows.Scan(columnPointers...); err != nil { return nil, err } // 将扫描到的值放入结果 map 中 result := make(map[string]interface{}) for i, colName := range columns { val := columnPointers[i].(*interface{}) result[colName] = *val } results = append(results, result) } return results, nil } func createDynamicStruct(fields map[string]interface{}) reflect.Type { var structFields []reflect.StructField for name, value := range fields { structFields = append(structFields, reflect.StructField{ Name: strings.Title(name), Type: reflect.TypeOf(value), Tag: reflect.StructTag(fmt.Sprintf(`json:"%s"`, name)), }) } return reflect.StructOf(structFields) } func GetDialysisPrescriptionInfo(start_date string, end_date string, mode int64, org_id int64, page int64, limit int64) (qcp []models.QCPrescription, total int64, err error) { offset := (page - 1) * limit err = readDb.Model(&models.QCPrescription{}).Preload("UserAdminRole", func(db *gorm.DB) *gorm.DB { return readUserDb.Where("status = 1 and org_id=?", org_id) }).Preload("QCPatients", "status = 1 and user_org_id = ?", org_id).Preload("QCDialysisOrder", func(db *gorm.DB) *gorm.DB { return db.Preload("UserAdminRole", func(db *gorm.DB) *gorm.DB { return readUserDb.Where("status = 1 and org_id=?", org_id) }).Preload("DeviceNumber", "status = 1 and org_id = ?", org_id).Where("status = 1 AND user_org_id = ?", org_id) }).Preload("QCAssessmentAfterDislysis", "status = 1 and user_org_id = ?", org_id).Where("FROM_UNIXTIME(record_date, '%Y-%m-%d') >= ? and FROM_UNIXTIME(record_date, '%Y-%m-%d') <= ? and user_org_id = ? and mode_id = ? and status = 1", start_date, end_date, org_id, mode).Count(&total).Offset(offset).Limit(limit).Find(&qcp).Error return } func GetScheduleInfo(start_date string, end_date string, mode int64, org_id int64, page int64, limit int64) (qcp []models.QCSchedule, total int64, err error) { offset := (page - 1) * limit err = readDb.Model(&models.QCSchedule{}).Preload("QCPatients", "status = 1 and user_org_id =?", org_id).Preload("QCSPrescription", func(db *gorm.DB) *gorm.DB { return db.Preload("UserAdminRole", func(db *gorm.DB) *gorm.DB { return readUserDb.Where("status = 1 and org_id=?", org_id) }).Where("status = 1 AND user_org_id = ?", org_id) }).Preload("QCAssessmentAfterDislysis", "status = 1 and user_org_id = ?", org_id).Preload("QCDialysisOrder", func(db *gorm.DB) *gorm.DB { return db.Preload("DeviceNumber", "status = 1").Preload("UserAdminRole", func(db *gorm.DB) *gorm.DB { return readUserDb.Where("status = 1 and org_id=?", org_id) }).Where("status = 1 AND user_org_id = ?", org_id) }).Where("FROM_UNIXTIME(schedule_date, '%Y-%m-%d') >= ? and FROM_UNIXTIME(schedule_date, '%Y-%m-%d') <= ? and user_org_id = ? and mode_id = ? and status = 1", start_date, end_date, org_id, mode).Count(&total).Offset(offset).Limit(limit).Find(&qcp).Error return }