[agent-go] [status] add status module
This commit is contained in:
49
agent-go/status/CPU.go
Normal file
49
agent-go/status/CPU.go
Normal file
@@ -0,0 +1,49 @@
|
||||
package status
|
||||
|
||||
import (
|
||||
"github.com/shirou/gopsutil/v3/cpu"
|
||||
"github.com/shirou/gopsutil/v3/load"
|
||||
)
|
||||
|
||||
type CPUStatus struct {
|
||||
NumCores int
|
||||
CPUInfo []cpu.InfoStat
|
||||
CPUPercent float64
|
||||
CPULoads *load.AvgStat
|
||||
SystemLoads *load.AvgStat
|
||||
}
|
||||
|
||||
func GetCPUStatus() (*CPUStatus, error) {
|
||||
numCores, err := cpu.Counts(true)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
cpuInfo, err := cpu.Info()
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
cpuPercent, err := cpu.Percent(0, false)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
cpuLoads, err := load.Avg()
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
systemLoads, err := load.Avg()
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
return &CPUStatus{
|
||||
NumCores: numCores,
|
||||
CPUInfo: cpuInfo,
|
||||
CPUPercent: cpuPercent[0],
|
||||
CPULoads: cpuLoads,
|
||||
SystemLoads: systemLoads,
|
||||
}, nil
|
||||
}
|
||||
22
agent-go/status/CPU_test.go
Normal file
22
agent-go/status/CPU_test.go
Normal file
@@ -0,0 +1,22 @@
|
||||
package status
|
||||
|
||||
import (
|
||||
"encoding/json"
|
||||
"fmt"
|
||||
"testing"
|
||||
)
|
||||
|
||||
func TestGetCPUStatus(t *testing.T) {
|
||||
cpuStatus, err := GetCPUStatus()
|
||||
if err != nil {
|
||||
return
|
||||
}
|
||||
|
||||
marshalIndent, err := json.MarshalIndent(cpuStatus, "", " ")
|
||||
if err != nil {
|
||||
fmt.Printf("error")
|
||||
}
|
||||
|
||||
fmt.Println(string(marshalIndent))
|
||||
|
||||
}
|
||||
44
agent-go/status/Memory.go
Normal file
44
agent-go/status/Memory.go
Normal file
@@ -0,0 +1,44 @@
|
||||
package status
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"github.com/shirou/gopsutil/v3/mem"
|
||||
)
|
||||
|
||||
type MemoryStatus struct {
|
||||
TotalMemory uint64
|
||||
UsedMemory uint64
|
||||
AvailableMemory uint64
|
||||
TotalVirtualMemory uint64
|
||||
UsedVirtualMemory uint64
|
||||
}
|
||||
|
||||
func GetMemoryStatus() (MemoryStatus, error) {
|
||||
var memoryStatus MemoryStatus
|
||||
|
||||
virtualMemoryStat, err := mem.VirtualMemory()
|
||||
if err != nil {
|
||||
return memoryStatus, err
|
||||
}
|
||||
|
||||
memoryStatus.TotalMemory = virtualMemoryStat.Total
|
||||
memoryStatus.UsedMemory = virtualMemoryStat.Used
|
||||
memoryStatus.AvailableMemory = virtualMemoryStat.Available
|
||||
memoryStatus.TotalVirtualMemory = virtualMemoryStat.Total
|
||||
memoryStatus.UsedVirtualMemory = virtualMemoryStat.Used
|
||||
|
||||
return memoryStatus, nil
|
||||
}
|
||||
|
||||
func FormatMemorySize(size uint64) string {
|
||||
const unit = 1024
|
||||
if size < unit {
|
||||
return fmt.Sprintf("%d B", size)
|
||||
}
|
||||
div, exp := int64(unit), 0
|
||||
for n := size / unit; n >= unit; n /= unit {
|
||||
div *= unit
|
||||
exp++
|
||||
}
|
||||
return fmt.Sprintf("%.1f %cB", float64(size)/float64(div), "KMGTPE"[exp])
|
||||
}
|
||||
20
agent-go/status/Memory_test.go
Normal file
20
agent-go/status/Memory_test.go
Normal file
@@ -0,0 +1,20 @@
|
||||
package status
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"testing"
|
||||
)
|
||||
|
||||
func TestGetMemoryStatus(t *testing.T) {
|
||||
|
||||
memoryStatus, err := GetMemoryStatus()
|
||||
if err != nil {
|
||||
return
|
||||
}
|
||||
|
||||
fmt.Printf("Total Memory: %s\n", FormatMemorySize(memoryStatus.TotalMemory))
|
||||
fmt.Printf("Used Memory: %s\n", FormatMemorySize(memoryStatus.UsedMemory))
|
||||
fmt.Printf("Available Memory: %s\n", FormatMemorySize(memoryStatus.AvailableMemory))
|
||||
fmt.Printf("Total Virtual Memory: %s\n", FormatMemorySize(memoryStatus.TotalVirtualMemory))
|
||||
fmt.Printf("Used Virtual Memory: %s\n", FormatMemorySize(memoryStatus.UsedVirtualMemory))
|
||||
}
|
||||
103
agent-go/status/Network.go
Normal file
103
agent-go/status/Network.go
Normal file
@@ -0,0 +1,103 @@
|
||||
package status
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"github.com/shirou/gopsutil/v3/net"
|
||||
"strings"
|
||||
"time"
|
||||
)
|
||||
|
||||
type NetworkInfo struct {
|
||||
Name string `json:"name,omitempty"`
|
||||
InternalIP string `json:"internal_ip,omitempty"`
|
||||
ExternalIP string `json:"external_ip,omitempty"`
|
||||
Mac string `json:"mac,omitempty"`
|
||||
Sent uint64 `json:"sent,omitempty"`
|
||||
Recv uint64 `json:"recv,omitempty"`
|
||||
SentRate string `json:"sent_rate,omitempty"`
|
||||
RecvRate string `json:"recv_rate,omitempty"`
|
||||
}
|
||||
|
||||
func main() {
|
||||
info, err := GetNetworkInfo()
|
||||
if err != nil {
|
||||
panic(err)
|
||||
}
|
||||
fmt.Printf("%+v\n", info)
|
||||
}
|
||||
|
||||
func GetNetworkInfo() (*NetworkInfo, error) {
|
||||
interfaces, err := net.Interfaces()
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
var mainInterface net.InterfaceStat
|
||||
for _, intf := range interfaces {
|
||||
if strings.HasPrefix(intf.Name, "ens") || strings.HasPrefix(intf.Name, "eth") || strings.HasPrefix(intf.Name, "eno") {
|
||||
mainInterface = intf
|
||||
break
|
||||
}
|
||||
}
|
||||
var internalIP string
|
||||
log.DebugF("all main interface address are %v", mainInterface.Addrs)
|
||||
for _, addr := range mainInterface.Addrs {
|
||||
if strings.Contains(addr.Addr, ".") {
|
||||
internalIP = addr.Addr
|
||||
break
|
||||
}
|
||||
}
|
||||
counters, err := net.IOCounters(true)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
var sent uint64
|
||||
var recv uint64
|
||||
for _, counter := range counters {
|
||||
if counter.Name == mainInterface.Name {
|
||||
sent = counter.BytesSent
|
||||
recv = counter.BytesRecv
|
||||
break
|
||||
}
|
||||
}
|
||||
|
||||
// 休眠3秒
|
||||
|
||||
time.Sleep(3 * time.Second)
|
||||
|
||||
var sentAfter uint64
|
||||
var recvAfter uint64
|
||||
for _, counter := range counters {
|
||||
if counter.Name == mainInterface.Name {
|
||||
sentAfter = counter.BytesSent
|
||||
recvAfter = counter.BytesRecv
|
||||
break
|
||||
}
|
||||
}
|
||||
sendRate := fmt.Sprintf(formatBytes((sentAfter - sent) / 3))
|
||||
recvRate := fmt.Sprintf(formatBytes((recvAfter - recv) / 3))
|
||||
|
||||
info := &NetworkInfo{
|
||||
Name: mainInterface.Name,
|
||||
InternalIP: internalIP,
|
||||
ExternalIP: "",
|
||||
Mac: mainInterface.HardwareAddr,
|
||||
Sent: sent,
|
||||
Recv: recv,
|
||||
SentRate: sendRate,
|
||||
RecvRate: recvRate,
|
||||
}
|
||||
return info, nil
|
||||
}
|
||||
|
||||
func formatBytes(bytes uint64) string {
|
||||
const unit = 1024
|
||||
if bytes < unit {
|
||||
return fmt.Sprintf("%d B", bytes)
|
||||
}
|
||||
div, exp := int64(unit), 0
|
||||
for n := bytes / unit; n >= unit; n /= unit {
|
||||
div *= unit
|
||||
exp++
|
||||
}
|
||||
return fmt.Sprintf("%.1f %cB", float64(bytes)/float64(div), "KMGTPE"[exp])
|
||||
}
|
||||
22
agent-go/status/Network_test.go
Normal file
22
agent-go/status/Network_test.go
Normal file
@@ -0,0 +1,22 @@
|
||||
package status
|
||||
|
||||
import (
|
||||
"encoding/json"
|
||||
"fmt"
|
||||
"testing"
|
||||
)
|
||||
|
||||
func TestGetNetworkInfo(t *testing.T) {
|
||||
|
||||
networkInfo, err := GetNetworkInfo()
|
||||
if err != nil {
|
||||
return
|
||||
}
|
||||
|
||||
marshalIndent, err := json.MarshalIndent(networkInfo, "", " ")
|
||||
if err != nil {
|
||||
fmt.Printf("error")
|
||||
}
|
||||
|
||||
fmt.Println(string(marshalIndent))
|
||||
}
|
||||
7
agent-go/status/Status.go
Normal file
7
agent-go/status/Status.go
Normal file
@@ -0,0 +1,7 @@
|
||||
package status
|
||||
|
||||
import (
|
||||
logger2 "agent-go/logger"
|
||||
)
|
||||
|
||||
var log = logger2.Log
|
||||
@@ -1,47 +0,0 @@
|
||||
package status
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
linuxproc "github.com/c9s/goprocinfo/linux"
|
||||
"time"
|
||||
)
|
||||
|
||||
func GetCpuMap() (map[string]uint64, error) {
|
||||
statA, err := linuxproc.ReadStat("/proc/stat")
|
||||
statErrMsg := "failed to stat CPU data, received error: %s"
|
||||
if err != nil {
|
||||
return nil, fmt.Errorf(statErrMsg, err.Error())
|
||||
}
|
||||
|
||||
time.Sleep(time.Second)
|
||||
|
||||
statB, err := linuxproc.ReadStat("/proc/stat")
|
||||
if err != nil {
|
||||
return nil, fmt.Errorf(statErrMsg, err.Error())
|
||||
}
|
||||
|
||||
resultMap := make(map[string]uint64)
|
||||
resultMap["all_active_percent"] = cpuStatToPercent(statA.CPUStatAll, statB.CPUStatAll)
|
||||
for idx, statB := range statB.CPUStats {
|
||||
statA := statA.CPUStats[idx]
|
||||
resultMap[statB.Id+"_active_percent"] = cpuStatToPercent(statA, statB)
|
||||
}
|
||||
|
||||
return resultMap, nil
|
||||
}
|
||||
|
||||
func cpuStatToPercent(statA, statB linuxproc.CPUStat) uint64 {
|
||||
aIdle := statA.Idle + statA.IOWait
|
||||
bIdle := statB.Idle + statB.IOWait
|
||||
|
||||
aNonIdle := statA.User + statA.Nice + statA.System + statA.IRQ + statA.SoftIRQ + statA.Steal
|
||||
bNonIdle := statB.User + statB.Nice + statB.System + statB.IRQ + statB.SoftIRQ + statB.Steal
|
||||
|
||||
aTotal := aIdle + aNonIdle
|
||||
bTotal := bIdle + bNonIdle
|
||||
|
||||
totalDiff := bTotal - aTotal
|
||||
idleDiff := bIdle - aIdle
|
||||
|
||||
return uint64((float64(totalDiff-idleDiff) / float64(totalDiff)) * 100)
|
||||
}
|
||||
Reference in New Issue
Block a user