75 lines
3.5 KiB
Go
75 lines
3.5 KiB
Go
package model
|
|
|
|
import (
|
|
"encoding/json"
|
|
"time"
|
|
)
|
|
|
|
// Consultation 专家会诊单
|
|
type Consultation struct {
|
|
ID string `gorm:"type:uuid;primaryKey;default:gen_random_uuid()" json:"id"`
|
|
RoomID *string `gorm:"column:room_id;type:uuid;index" json:"roomId,omitempty"`
|
|
BatchID *string `gorm:"column:batch_id;type:uuid;index" json:"batchId,omitempty"`
|
|
LampTestID *string `gorm:"column:lamp_test_id;type:uuid;index" json:"lampTestId,omitempty"`
|
|
Title string `gorm:"size:128" json:"title"`
|
|
Summary *string `gorm:"type:text" json:"summary,omitempty"`
|
|
Snapshot json.RawMessage `gorm:"type:jsonb" json:"snapshot,omitempty"`
|
|
Status string `gorm:"size:16;default:pending" json:"status"` // pending/consulting/resolved/archived
|
|
ExpertID *string `gorm:"column:expert_id;type:uuid" json:"expertId,omitempty"`
|
|
AssigneeID *string `gorm:"column:assignee_id;type:uuid" json:"assigneeId,omitempty"`
|
|
AssignedAt *time.Time `gorm:"column:assigned_at;type:timestamptz" json:"assignedAt,omitempty"`
|
|
AcceptedAt *time.Time `gorm:"column:accepted_at;type:timestamptz" json:"acceptedAt,omitempty"`
|
|
NeedsInfoAt *time.Time `gorm:"column:needs_info_at;type:timestamptz" json:"needsInfoAt,omitempty"`
|
|
SLADeadline *time.Time `gorm:"column:sla_deadline;type:timestamptz" json:"slaDeadline,omitempty"`
|
|
OverdueAt *time.Time `gorm:"column:overdue_at;type:timestamptz" json:"overdueAt,omitempty"`
|
|
LastSLAEventAt *time.Time `gorm:"column:last_sla_event_at;type:timestamptz" json:"lastSlaEventAt,omitempty"`
|
|
Opinion *string `gorm:"type:text" json:"opinion,omitempty"`
|
|
Plan *string `gorm:"type:text" json:"plan,omitempty"`
|
|
ResolvedAt *time.Time `gorm:"column:resolved_at;type:timestamptz" json:"resolvedAt,omitempty"`
|
|
ArchivedAt *time.Time `gorm:"column:archived_at;type:timestamptz" json:"archivedAt,omitempty"`
|
|
CreatedAt time.Time `gorm:"type:timestamptz" json:"createdAt"`
|
|
UpdatedAt time.Time `gorm:"type:timestamptz" json:"updatedAt"`
|
|
RoomName *string `gorm:"-" json:"roomName,omitempty"`
|
|
}
|
|
|
|
func (Consultation) TableName() string { return "consultations" }
|
|
|
|
// ValidConsultationTransition 状态流转规则:unassigned/assigned/accepted/needs_info/resolved/archived。
|
|
func ValidConsultationTransition(from, to string) bool {
|
|
switch from {
|
|
case "unassigned":
|
|
return to == "assigned"
|
|
case "assigned":
|
|
return to == "accepted" || to == "needs_info"
|
|
case "accepted":
|
|
return to == "needs_info" || to == "resolved"
|
|
case "needs_info":
|
|
return to == "accepted" || to == "resolved"
|
|
case "resolved":
|
|
return to == "archived" || to == "needs_info"
|
|
default:
|
|
return false
|
|
}
|
|
}
|
|
|
|
// ConsultationSLAState 返回会诊 SLA 状态;超时只标记,不自动伪造专家结论。
|
|
func ConsultationSLAState(t Consultation, now time.Time) string {
|
|
if t.SLADeadline == nil {
|
|
return "unscheduled"
|
|
}
|
|
if now.After(*t.SLADeadline) {
|
|
return "overdue"
|
|
}
|
|
return "on_time"
|
|
}
|
|
|
|
// ConsultationSnapshot 病例快照(会诊时打包,避免引用数据变化)
|
|
type ConsultationSnapshot struct {
|
|
RoomName string `json:"roomName,omitempty"`
|
|
LampTest *LampTest `json:"lampTest,omitempty"`
|
|
Inspection *InspectionRecord `json:"inspection,omitempty"`
|
|
Batch *Batch `json:"batch,omitempty"`
|
|
WeatherAlerts []WeatherAlert `json:"weatherAlerts,omitempty"`
|
|
CreatedAt time.Time `json:"createdAt"`
|
|
}
|