1. 新增跨平台磁盘空间监控能力,每日7点自动检测附件目录剩余空间,触发阈值告警 2. 重构附件存储方案为年/月/日/文件类型分层结构,统一MES与WMS的附件管理逻辑 3. 对齐物料档案与入库单的质量状态校验规则,仅合格品计入库存与出库 4. 实现入库单作废功能与区域库位的多级父子结构管理 5. 删除物料简称字段,补充规格型号与单位必填项,统一系统数据口径 6. 新增附件中心与磁盘状态查询接口,完善权限控制与操作日志
106 lines
3.5 KiB
Go
106 lines
3.5 KiB
Go
package handler
|
||
|
||
import (
|
||
"context"
|
||
"fmt"
|
||
"net/http"
|
||
"os"
|
||
"time"
|
||
|
||
"bj_power_mes/common/httpx"
|
||
"bj_power_mes/internal/svc"
|
||
|
||
"github.com/zeromicro/go-zero/core/logx"
|
||
)
|
||
|
||
// diskStatusView 磁盘空间状态视图(附件中心顶部提示 + 定时告警共用)。
|
||
type diskStatusView struct {
|
||
RootDir string `json:"rootDir"`
|
||
UsedPercent int `json:"usedPercent"`
|
||
FreeBytes uint64 `json:"freeBytes"`
|
||
TotalBytes uint64 `json:"totalBytes"`
|
||
WarnPercent int `json:"warnPercent"`
|
||
CritPercent int `json:"critPercent"`
|
||
Level string `json:"level"` // ok / warn / critical / unknown
|
||
Message string `json:"message"`
|
||
CheckedAt int64 `json:"checkedAt"`
|
||
}
|
||
|
||
// diskStatus 读取附件根目录所在磁盘剩余空间并给出告警级别。
|
||
// 剩余 < DiskCriticalPercent → critical(提示执行备份归档清理);< DiskWarnPercent → warn。
|
||
func diskStatus(svcCtx *svc.ServiceContext) diskStatusView {
|
||
cfg := svcCtx.Config.Upload
|
||
root := cfg.Dir
|
||
if root == "" {
|
||
root = "uploads"
|
||
}
|
||
v := diskStatusView{
|
||
RootDir: root, WarnPercent: cfg.DiskWarnPercent, CritPercent: cfg.DiskCriticalPercent,
|
||
Level: "ok", Message: "磁盘空间正常", CheckedAt: time.Now().Unix(),
|
||
}
|
||
used, free, total, err := diskUsage(root)
|
||
if err != nil {
|
||
_ = os.MkdirAll(root, 0o755)
|
||
used, free, total, err = diskUsage(root)
|
||
}
|
||
if err != nil {
|
||
v.Level = "unknown"
|
||
v.Message = "磁盘空间检测失败:" + err.Error()
|
||
return v
|
||
}
|
||
v.UsedPercent, v.FreeBytes, v.TotalBytes = used, free, total
|
||
freePercent := 100 - used
|
||
switch {
|
||
case freePercent < cfg.DiskCriticalPercent:
|
||
v.Level = "critical"
|
||
v.Message = fmt.Sprintf("磁盘剩余空间仅 %d%%,低于 %d%%,请立即执行备份归档清理(附件中心可一键归档)", freePercent, cfg.DiskCriticalPercent)
|
||
case freePercent < cfg.DiskWarnPercent:
|
||
v.Level = "warn"
|
||
v.Message = fmt.Sprintf("磁盘剩余空间 %d%%,低于 %d%% 告警线,请及时清理", freePercent, cfg.DiskWarnPercent)
|
||
}
|
||
return v
|
||
}
|
||
|
||
// DiskStatusHandler GET /attachment/disk-status
|
||
func DiskStatusHandler(svcCtx *svc.ServiceContext) http.HandlerFunc {
|
||
return func(w http.ResponseWriter, r *http.Request) {
|
||
httpx.Ok(w, diskStatus(svcCtx))
|
||
}
|
||
}
|
||
|
||
// StartDiskMonitor 启动磁盘空间监控:每天 DiskCheckHour(默认 7 点) 检测一次,
|
||
// 剩余 <20% 告警、<10% 提示清理(写服务日志 + 操作日志,附件中心顶部同步展示)。
|
||
func StartDiskMonitor(svcCtx *svc.ServiceContext) {
|
||
go func() {
|
||
hour := svcCtx.Config.Upload.DiskCheckHour
|
||
if hour < 0 || hour > 23 {
|
||
hour = 7
|
||
}
|
||
for {
|
||
now := time.Now()
|
||
next := time.Date(now.Year(), now.Month(), now.Day(), hour, 0, 0, 0, time.Local)
|
||
if !next.After(now) {
|
||
next = next.Add(24 * time.Hour)
|
||
}
|
||
time.Sleep(time.Until(next))
|
||
checkDiskOnce(svcCtx)
|
||
}
|
||
}()
|
||
}
|
||
|
||
func checkDiskOnce(svcCtx *svc.ServiceContext) {
|
||
st := diskStatus(svcCtx)
|
||
switch st.Level {
|
||
case "critical":
|
||
logx.Errorf("[磁盘监控] %s(已用 %d%%,剩余 %d%%)", st.Message, st.UsedPercent, 100-st.UsedPercent)
|
||
svcCtx.EventLog.Write(context.Background(), "system.disk", "", "system", "attachment", "disk", st.Message,
|
||
map[string]any{"usedPercent": st.UsedPercent, "freeBytes": st.FreeBytes})
|
||
case "warn":
|
||
logx.Alert("[磁盘监控] " + st.Message)
|
||
svcCtx.EventLog.Write(context.Background(), "system.disk", "", "system", "attachment", "disk", st.Message,
|
||
map[string]any{"usedPercent": st.UsedPercent, "freeBytes": st.FreeBytes})
|
||
default:
|
||
logx.Infof("[磁盘监控] 正常:剩余 %d%%(%s)", 100-st.UsedPercent, st.RootDir)
|
||
}
|
||
}
|