Skip to content

Commit ad323f5

Browse files
committed
Update.
1 parent ae53605 commit ad323f5

File tree

5 files changed

+199
-64
lines changed

5 files changed

+199
-64
lines changed

cmd/dashboard/main.go

Lines changed: 61 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,10 @@
11
package main
22

33
import (
4-
"os"
54
"context"
65
"fmt"
76
"log"
7+
"os"
88
"time"
99
_ "time/tzdata"
1010

@@ -21,6 +21,7 @@ type DashboardCliParam struct {
2121
Version bool // 当前版本号
2222
ConfigFile string // 配置文件路径
2323
DatebaseLocation string // Sqlite3 数据库文件路径
24+
ResetTraffic bool // 重置所有服务器的累计流量数据
2425
}
2526

2627
var (
@@ -32,6 +33,7 @@ func init() {
3233
flag.BoolVarP(&dashboardCliParam.Version, "version", "v", false, "查看当前版本号")
3334
flag.StringVarP(&dashboardCliParam.ConfigFile, "config", "c", "data/config.yaml", "配置文件路径")
3435
flag.StringVar(&dashboardCliParam.DatebaseLocation, "db", "data/sqlite.db", "Sqlite3数据库文件路径")
36+
flag.BoolVar(&dashboardCliParam.ResetTraffic, "reset-traffic", false, "重置所有服务器的累计流量数据")
3537
flag.Parse()
3638
}
3739

@@ -61,6 +63,13 @@ func main() {
6163
singleton.InitTimezoneAndCache()
6264
singleton.InitDBFromPath(dashboardCliParam.DatebaseLocation)
6365
singleton.InitLocalizer()
66+
67+
// 处理重置流量命令
68+
if dashboardCliParam.ResetTraffic {
69+
resetAllServerTraffic()
70+
return
71+
}
72+
6473
initSystem()
6574

6675
// TODO 使用 cmux 在同一端口服务 HTTP 和 gRPC
@@ -100,3 +109,54 @@ func dispatchReportInfoTask() {
100109
})
101110
}
102111
}
112+
113+
// resetAllServerTraffic 重置所有服务器的累计流量数据
114+
func resetAllServerTraffic() {
115+
fmt.Println("正在重置所有服务器的累计流量数据...")
116+
117+
// 首先清空数据库中的累计流量数据
118+
err := singleton.DB.Model(&model.Server{}).Updates(map[string]interface{}{
119+
"cumulative_net_in_transfer": 0,
120+
"cumulative_net_out_transfer": 0,
121+
}).Error
122+
123+
if err != nil {
124+
fmt.Printf("重置数据库中的累计流量失败: %v\n", err)
125+
return
126+
}
127+
128+
// 加载服务器列表
129+
singleton.LoadSingleton()
130+
131+
// 重置内存中的累计流量数据
132+
singleton.ServerLock.Lock()
133+
defer singleton.ServerLock.Unlock()
134+
135+
count := 0
136+
for _, server := range singleton.ServerList {
137+
if server.CumulativeNetInTransfer > 0 || server.CumulativeNetOutTransfer > 0 {
138+
fmt.Printf("重置服务器 [%s] 的累计流量: 入站 %d → 0, 出站 %d → 0\n",
139+
server.Name,
140+
server.CumulativeNetInTransfer,
141+
server.CumulativeNetOutTransfer)
142+
143+
server.CumulativeNetInTransfer = 0
144+
server.CumulativeNetOutTransfer = 0
145+
146+
// 同时重置状态中的流量数据
147+
if server.State != nil {
148+
server.State.NetInTransfer = 0
149+
server.State.NetOutTransfer = 0
150+
}
151+
152+
// 重置增量计算的基准点
153+
server.PrevTransferInSnapshot = 0
154+
server.PrevTransferOutSnapshot = 0
155+
156+
count++
157+
}
158+
}
159+
160+
fmt.Printf("成功重置了 %d 个服务器的累计流量数据\n", count)
161+
fmt.Println("重置完成,请重启应用程序以使更改生效")
162+
}

resource/template/theme-default/home.html

Lines changed: 50 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -49,8 +49,15 @@
4949
@#formatByteSize(server.Host.SwapTotal)#@<br />
5050
{{tr "DiskUsed"}}:@#formatByteSize(server.State.DiskUsed)#@ /
5151
@#formatByteSize(server.Host.DiskTotal)#@<br />
52-
52+
<template v-if="getTrafficTooltip(server.ID)">
5353
{{tr "TrafficTotal"}}:@#getTrafficTooltip(server.ID)#@<br />
54+
</template>
55+
<template v-if="server.Host.GPU">
56+
{{tr "GPU"}}:@#server.Host.GPU#@<br />
57+
</template>
58+
<template v-if="hasTemperature(server.State.Temperatures, sensorList)">
59+
{{tr "Temperature"}}:@#getTemperature(server.State.Temperatures, sensorList)#@°C<br />
60+
</template>
5461

5562
{{tr "Load"}}:@#toFixed2(server.State.Load1)#@ | @#toFixed2(server.State.Load5)#@ | @#toFixed2(server.State.Load15)#@<br />
5663
{{tr "ConnCount"}}:TCP @#server.State.TcpConnCount#@ {{tr "Count"}} | UDP @#server.State.UdpConnCount#@ {{tr "Count"}}
@@ -923,6 +930,48 @@
923930
// Force Vue to recognize the data change
924931
this.$forceUpdate();
925932
},
933+
hasTemperature(temperatureList, sensorList) {
934+
// 如果没有温度数据,返回false
935+
if (!temperatureList || !Array.isArray(temperatureList) || temperatureList.length === 0) {
936+
return false;
937+
}
938+
939+
// 检查是否存在任何非零温度数据
940+
return temperatureList.some(item => item.Temperature !== 0);
941+
},
942+
getTemperature(temperatureList, sensorList) {
943+
// 如果没有温度数据,返回空字符串
944+
if (!temperatureList || !Array.isArray(temperatureList) || temperatureList.length === 0) {
945+
return '';
946+
}
947+
948+
// 将 sensorList 中的所有项转换为小写
949+
const lowerCaseSensorList = sensorList.map(sensor => sensor.toLowerCase());
950+
951+
// 合并过滤逻辑:过滤出 Temperature 不为 0 且 Name 在 sensorList 中的元素(忽略大小写)
952+
const filtered = temperatureList.filter(item => item.Temperature !== 0 && lowerCaseSensorList.includes(item.Name.toLowerCase()));
953+
954+
// 如果有匹配的元素,则计算这些元素的 Temperature 的最大值
955+
if (filtered.length > 0) {
956+
const maxTemp = filtered.reduce((max, current) => {
957+
return current.Temperature > max ? current.Temperature : max;
958+
}, filtered[0].Temperature);
959+
return maxTemp.toFixed(1);
960+
}
961+
962+
// 如果没有匹配的元素,则计算 temperatureList 中所有 Temperature 不为 0 的元素的最大值
963+
const nonZeroTemps = temperatureList.filter(item => item.Temperature !== 0);
964+
965+
if (nonZeroTemps.length > 0) {
966+
const maxTemp = nonZeroTemps.reduce((max, current) => {
967+
return current.Temperature > max ? current.Temperature : max;
968+
}, nonZeroTemps[0].Temperature);
969+
return maxTemp.toFixed(1);
970+
}
971+
972+
// 如果所有元素的 Temperature 都为 0,则返回空字符串
973+
return '';
974+
},
926975
initTrafficDataWatcher() {
927976
this.trafficWatcherInterval = setInterval(() => {
928977
if (window.serverTrafficData &&
@@ -1005,7 +1054,5 @@
10051054
$(document).ready(function() {
10061055
$('.ui.accordion').accordion({ "exclusive": false });
10071056
});
1008-
1009-
// Note: Traffic formatting function has been moved to main.js
10101057
</script>
10111058
{{end}}

service/rpc/server.go

Lines changed: 21 additions & 28 deletions
Original file line numberDiff line numberDiff line change
@@ -116,16 +116,6 @@ func (s *ServerHandler) ReportSystemState(c context.Context, r *pb.State) (*pb.R
116116
singleton.ServerList[clientID].IsOnline = true
117117
singleton.ServerList[clientID].LastActive = time.Now()
118118

119-
// 输出完整状态数据,用于调试
120-
log.Printf("NG>> 服务器 %s 状态上报: CPU:%.2f%% 内存:%d 硬盘:%d 进程:%d 原始流量:入站 %d / 出站 %d",
121-
singleton.ServerList[clientID].Name,
122-
state.CPU,
123-
state.MemUsed,
124-
state.DiskUsed,
125-
state.ProcessCount,
126-
state.NetInTransfer,
127-
state.NetOutTransfer)
128-
129119
// 保存原始流量数据用于增量计算
130120
originalNetInTransfer := state.NetInTransfer
131121
originalNetOutTransfer := state.NetOutTransfer
@@ -135,12 +125,6 @@ func (s *ServerHandler) ReportSystemState(c context.Context, r *pb.State) (*pb.R
135125
state.NetInTransfer += singleton.ServerList[clientID].CumulativeNetInTransfer
136126
state.NetOutTransfer += singleton.ServerList[clientID].CumulativeNetOutTransfer
137127

138-
// 记录实际展示的流量值
139-
log.Printf("NG>> 服务器 %s 实际展示流量: 入站 %d / 出站 %d",
140-
singleton.ServerList[clientID].Name,
141-
state.NetInTransfer,
142-
state.NetOutTransfer)
143-
144128
// 保存当前状态
145129
singleton.ServerList[clientID].State = &state
146130

@@ -161,18 +145,32 @@ func (s *ServerHandler) ReportSystemState(c context.Context, r *pb.State) (*pb.R
161145
"last_online": singleton.ServerList[clientID].LastOnline,
162146
})
163147

164-
log.Printf("NG>> 服务器 %s 最后状态已保存到数据库", singleton.ServerList[clientID].Name)
148+
// 确认Host信息是否已保存,如果该服务器尚未保存Host信息,尝试保存当前内存中的信息
149+
if singleton.ServerList[clientID].Host != nil {
150+
var count int64
151+
singleton.DB.Raw("SELECT COUNT(*) FROM last_reported_host WHERE server_id = ?", clientID).Scan(&count)
152+
153+
if count == 0 {
154+
hostJSON, hostErr := utils.Json.Marshal(singleton.ServerList[clientID].Host)
155+
if hostErr == nil && len(hostJSON) > 0 {
156+
singleton.DB.Exec(`
157+
INSERT INTO last_reported_host (server_id, host_json)
158+
VALUES (?, ?)
159+
ON CONFLICT(server_id)
160+
DO UPDATE SET host_json = ?
161+
`, clientID, string(hostJSON), string(hostJSON))
162+
}
163+
}
164+
}
165+
} else {
166+
log.Printf("NG>> 序列化服务器 %s 的最后状态失败: %v", singleton.ServerList[clientID].Name, err)
165167
}
166168

167169
// 确保PrevTransferSnapshot值被正确初始化
168170
// 这些值用于计算每小时的增量流量
169171
if singleton.ServerList[clientID].PrevTransferInSnapshot == 0 || singleton.ServerList[clientID].PrevTransferOutSnapshot == 0 {
170172
singleton.ServerList[clientID].PrevTransferInSnapshot = int64(originalNetInTransfer)
171173
singleton.ServerList[clientID].PrevTransferOutSnapshot = int64(originalNetOutTransfer)
172-
log.Printf("NG>> 服务器 %s 初始化流量基准点: 入站 %d / 出站 %d",
173-
singleton.ServerList[clientID].Name,
174-
singleton.ServerList[clientID].PrevTransferInSnapshot,
175-
singleton.ServerList[clientID].PrevTransferOutSnapshot)
176174
}
177175

178176
return &pb.Receipt{Proced: true}, nil
@@ -235,11 +233,6 @@ func (s *ServerHandler) ReportSystemInfo(c context.Context, r *pb.Host) (*pb.Rec
235233
// 服务器重启时保持累计流量不变,只重置上次记录点
236234
singleton.ServerList[clientID].PrevTransferInSnapshot = 0
237235
singleton.ServerList[clientID].PrevTransferOutSnapshot = 0
238-
239-
log.Printf("NG>> 服务器 %s 重置了流量计数点,累计流量保持不变: 入站 %d / 出站 %d",
240-
singleton.ServerList[clientID].Name,
241-
singleton.ServerList[clientID].CumulativeNetInTransfer,
242-
singleton.ServerList[clientID].CumulativeNetOutTransfer)
243236
}
244237

245238
// 不要冲掉国家码
@@ -257,8 +250,8 @@ func (s *ServerHandler) ReportSystemInfo(c context.Context, r *pb.Host) (*pb.Rec
257250
ON CONFLICT(server_id)
258251
DO UPDATE SET host_json = ?
259252
`, clientID, string(hostJSON), string(hostJSON))
260-
261-
log.Printf("NG>> 服务器 %s Host信息已保存到数据库", singleton.ServerList[clientID].Name)
253+
} else {
254+
log.Printf("NG>> 序列化服务器 %s 的Host信息失败: %v", singleton.ServerList[clientID].Name, err)
262255
}
263256

264257
singleton.ServerList[clientID].Host = &host

service/singleton/server.go

Lines changed: 35 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -45,11 +45,7 @@ func loadServers() {
4545
if err := DB.Raw("SELECT host_json FROM last_reported_host WHERE server_id = ?", innerS.ID).Scan(&hostJSON).Error; err == nil && len(hostJSON) > 0 {
4646
if err := utils.Json.Unmarshal(hostJSON, innerS.Host); err != nil {
4747
log.Printf("NG>> 解析服务器 %s 的Host数据失败: %v", innerS.Name, err)
48-
} else {
49-
log.Printf("NG>> 服务器 %s 加载了Host数据", innerS.Name)
5048
}
51-
} else {
52-
log.Printf("NG>> 服务器 %s 没有找到历史Host数据", innerS.Name)
5349
}
5450

5551
// 加载离线前的最后状态
@@ -85,14 +81,6 @@ func loadServers() {
8581
// 将保存的流量数据初始化到State中,确保显示流量数据
8682
innerS.State.NetInTransfer = innerS.CumulativeNetInTransfer
8783
innerS.State.NetOutTransfer = innerS.CumulativeNetOutTransfer
88-
89-
log.Printf("NG>> 服务器 %s 加载了离线前的最后状态,CPU:%.2f%% 内存:%d 硬盘:%d 流量入站:%d 出站:%d",
90-
innerS.Name,
91-
innerS.State.CPU,
92-
innerS.State.MemUsed,
93-
innerS.State.DiskUsed,
94-
innerS.CumulativeNetInTransfer,
95-
innerS.CumulativeNetOutTransfer)
9684
} else {
9785
log.Printf("NG>> 解析服务器 %s 的最后状态失败: %v", innerS.Name, err)
9886
}
@@ -104,6 +92,11 @@ func loadServers() {
10492
ServerTagToIDList[innerS.Tag] = append(ServerTagToIDList[innerS.Tag], innerS.ID)
10593
}
10694
ReSortServer()
95+
96+
// 仅在Debug模式下输出详细信息
97+
if Conf.Debug {
98+
printServerLoadSummary()
99+
}
107100
}
108101

109102
// ReSortServer 根据服务器ID 对服务器列表进行排序(ID越大越靠前)
@@ -137,3 +130,33 @@ func ReSortServer() {
137130
return SortedServerListForGuest[i].DisplayIndex > SortedServerListForGuest[j].DisplayIndex
138131
})
139132
}
133+
134+
// printServerLoadSummary 输出服务器状态加载情况的摘要信息
135+
func printServerLoadSummary() {
136+
log.Println("NG>> 服务器状态加载情况:")
137+
138+
// 统计信息
139+
loaded := 0
140+
withState := 0
141+
withHost := 0
142+
143+
for _, server := range ServerList {
144+
if server.Host != nil && server.Host.MemTotal > 0 {
145+
withHost++
146+
}
147+
148+
if server.State != nil &&
149+
(server.State.CPU > 0 ||
150+
server.State.MemUsed > 0 ||
151+
server.State.NetInTransfer > 0) {
152+
withState++
153+
}
154+
155+
if server.LastStateBeforeOffline != nil {
156+
loaded++
157+
}
158+
}
159+
160+
log.Printf("NG>> 总共加载了 %d 台服务器: 有Host信息=%d, 有State信息=%d, 有离线前状态=%d",
161+
len(ServerList), withHost, withState, loaded)
162+
}

0 commit comments

Comments
 (0)