版本封存

This commit is contained in:
zeaslity
2025-12-06 11:26:05 +08:00
parent 13949e1ba8
commit c0ae5e30c4
57 changed files with 2443 additions and 1428 deletions

View File

@@ -1,163 +1,205 @@
package services
package host_info
import (
"bufio"
"cmii-uav-watchdog-common/models"
"fmt"
"cmii-uav-watchdog-common/wdd_log"
"os"
"os/exec"
"runtime"
"strconv"
"strings"
)
// NewCPUInfo 创建一个默认的 CPUInfo
func NewCPUInfo() models.CPUInfo {
return models.CPUInfo{
ModelName: "unknown",
Cores: 0,
Architecture: "unknown",
UUID: "unknown",
ModelName: "unknown",
Cores: 0,
Architecture: "amd64",
Flags: []string{},
Hypervisor: "unknown",
Virtualization: "unknown",
}
}
const (
exePath = "/proc/self/exe"
elfMagic = 0x7f
elfMagicString = "ELF"
eMachineOffset = 18
)
// parseLine 解析单行 CPU 信息
func parseLine(line string, cpuInfo *models.CPUInfo) {
if strings.HasPrefix(line, "model name") {
cpuInfo.ModelName = strings.TrimSpace(strings.Split(line, ":")[1])
}
}
// getCPUCores 通过 processor 行获取 CPU 核心数
func getCPUCores() (int, error) {
cores := 0
file, err := os.Open("/proc/cpuinfo")
if err != nil {
return cores, err
}
defer file.Close()
scanner := bufio.NewScanner(file)
for scanner.Scan() {
line := scanner.Text()
if strings.HasPrefix(line, "processor") {
cores++
}
}
if err := scanner.Err(); err != nil {
return cores, err
}
return cores, nil
}
// getCPUUUID 获取 CPU UUID
func getCPUUUID() (string, error) {
data, err := os.ReadFile("/sys/class/dmi/id/product_uuid")
if err != nil {
return "unknown", err
}
return strings.TrimSpace(string(data)), nil
}
func getCPUArchitecture() string {
cpuarch := "unknown"
// 打开当前进程的执行文件
file, err := os.Open(exePath)
if err != nil {
_, _ = fmt.Fprintf(os.Stderr, "Error opening %s: %v\n", exePath, err)
return cpuarch
}
defer file.Close()
// 读取前64个字节以获取 ELF 头部信息
header := make([]byte, 64)
if _, err := file.Read(header); err != nil {
_, _ = fmt.Fprintf(os.Stderr, "Error reading header: %v\n", err)
return cpuarch
}
// 检查 ELF 文件标识
if header[0] != elfMagic || string(header[1:4]) != elfMagicString {
_, _ = fmt.Fprintln(os.Stderr, "File is not an ELF file")
return cpuarch
}
// 获取架构信息
arch := header[eMachineOffset] // e_machine 字段的偏移量
switch arch {
case 0x02: // EM_386
cpuarch = "x86(32-bit)"
case 0x03: // EM_X86_64
cpuarch = "x86_64(64-bit)"
case 0x28: // EM_ARM
cpuarch = "ARM"
case 0x2A: // EM_ARM64
cpuarch = "ARM64"
case 0x08: // EM_MIPS
cpuarch = "MIPS"
default:
cpuarch = "unknown architecture"
}
return cpuarch
}
// GetCPUInfo 获取 CPU 信息
// GetCPUInfo 获取CPU信息
// 返回CPU信息结构体
func GetCPUInfo() models.CPUInfo {
wdd_log.Debug("开始获取CPU信息")
// 首先尝试从/proc/cpuinfo文件中读取信息
cpuInfo, err := getCPUInfoFromProc()
if err == nil {
wdd_log.Debug("成功从/proc/cpuinfo获取CPU信息")
return cpuInfo
}
// 如果从文件获取失败尝试使用lscpu命令
wdd_log.Warn("从/proc/cpuinfo获取CPU信息失败: %s尝试使用lscpu命令", err.Error())
cpuInfo, err = getCPUInfoFromLscpu()
if err == nil {
wdd_log.Debug("成功从lscpu命令获取CPU信息")
return cpuInfo
}
// 如果都失败使用runtime包获取基本信息
wdd_log.Warn("从lscpu获取CPU信息失败: %s使用runtime包获取基本信息", err.Error())
return getFallbackCPUInfo()
}
// getCPUInfoFromProc 从/proc/cpuinfo文件中读取CPU信息
// 返回CPU信息结构体和可能的错误
func getCPUInfoFromProc() (models.CPUInfo, error) {
wdd_log.Debug("尝试从/proc/cpuinfo读取CPU信息")
// 创建默认的CPU信息结构体
cpuInfo := NewCPUInfo()
// 读取 /proc/cpuinfo
// 打开/proc/cpuinfo文件
file, err := os.Open("/proc/cpuinfo")
if err != nil {
fmt.Println("Error opening /proc/cpuinfo:", err)
return cpuInfo // 返回默认值
return cpuInfo, err
}
defer func() {
if err := file.Close(); err != nil {
fmt.Println("Error closing /proc/cpuinfo:", err)
}
}()
defer file.Close()
// 使用scanner读取文件
scanner := bufio.NewScanner(file)
// 处理的CPU核心数量
coreCount := 1
var flags []string
// 逐行读取并解析
for scanner.Scan() {
parseLine(scanner.Text(), &cpuInfo)
}
if err := scanner.Err(); err != nil {
fmt.Println("Error reading /proc/cpuinfo:", err)
return cpuInfo // 返回默认值
line := scanner.Text()
parts := strings.Split(line, ":")
if len(parts) < 2 {
continue
}
key := strings.TrimSpace(parts[0])
value := strings.TrimSpace(parts[1])
switch key {
case "processor":
// 计数处理器核心数量
coreCount++
case "model name":
// 获取CPU型号名称
cpuInfo.ModelName = value
// 提取频率信息(如果包含)
if strings.Contains(value, "@") {
freqParts := strings.Split(value, "@")
if len(freqParts) > 1 {
cpuInfo.Frequency = strings.TrimSpace(freqParts[1])
}
}
case "flags":
// 获取CPU标志
flags = strings.Fields(value)
case "cpu cores":
// 获取每个物理CPU的核心数
cores, err := strconv.Atoi(value)
if err == nil && cores > 0 {
cpuInfo.Cores = cores
}
}
}
// 获取 CPU 核心
cores, err := getCPUCores()
// 如果没有从cpu cores字段获取到核心数使用处理器计
if cpuInfo.Cores == 0 && coreCount > 0 {
cpuInfo.Cores = coreCount
}
// 设置CPU标志
cpuInfo.Flags = flags
// 检测虚拟化相关信息
for _, flag := range flags {
if flag == "vmx" {
cpuInfo.Virtualization = "vmx"
} else if flag == "svm" {
cpuInfo.Virtualization = "svm"
} else if flag == "hypervisor" {
cpuInfo.Hypervisor = "present"
}
}
// 设置架构
cpuInfo.Architecture = runtime.GOARCH
return cpuInfo, nil
}
// getCPUInfoFromLscpu 使用lscpu命令获取CPU信息
// 返回CPU信息结构体和可能的错误
func getCPUInfoFromLscpu() (models.CPUInfo, error) {
wdd_log.Debug("尝试使用lscpu命令获取CPU信息")
// 创建默认的CPU信息结构体
cpuInfo := NewCPUInfo()
// 执行lscpu命令
cmd := exec.Command("lscpu")
output, err := cmd.Output()
if err != nil {
fmt.Println("Error getting CPU cores:", err)
} else {
cpuInfo.Cores = cores
return cpuInfo, err
}
// 获取 CPU UUID
uuid, err := getCPUUUID()
if err != nil {
fmt.Println("Error getting CPU UUID:", err)
} else {
cpuInfo.UUID = uuid
// 解析输出
lines := strings.Split(string(output), "\n")
for _, line := range lines {
parts := strings.Split(line, ":")
if len(parts) < 2 {
continue
}
key := strings.TrimSpace(parts[0])
value := strings.TrimSpace(parts[1])
switch key {
case "Model name":
cpuInfo.ModelName = value
// 提取频率信息(如果包含)
if strings.Contains(value, "@") {
freqParts := strings.Split(value, "@")
if len(freqParts) > 1 {
cpuInfo.Frequency = strings.TrimSpace(freqParts[1])
}
}
case "Architecture":
cpuInfo.Architecture = value
case "CPU(s)":
cores, err := strconv.Atoi(value)
if err == nil {
cpuInfo.Cores = cores
}
case "Flags":
cpuInfo.Flags = strings.Fields(value)
case "Hypervisor vendor":
cpuInfo.Hypervisor = value
case "Virtualization":
cpuInfo.Virtualization = value
case "CPU MHz":
if cpuInfo.Frequency == "" {
cpuInfo.Frequency = value + " MHz"
}
}
}
cpuInfo.Architecture = getCPUArchitecture()
return cpuInfo, nil
}
// getFallbackCPUInfo 使用runtime包获取基本CPU信息
// 返回CPU信息结构体
func getFallbackCPUInfo() models.CPUInfo {
wdd_log.Debug("使用runtime包获取基本CPU信息")
cpuInfo := NewCPUInfo()
cpuInfo.Cores = runtime.NumCPU()
cpuInfo.Architecture = runtime.GOARCH
return cpuInfo
}
/*
CPU模型名称: Intel(R) Core(TM) i7-8565U CPU @ 1.80GHz
核心数量: 4
架构信息: x86_64
*/

View File

@@ -1,8 +1,8 @@
package services
package host_info
import (
"cmii-uav-watchdog-common/models"
"fmt"
"cmii-uav-watchdog-common/wdd_log"
"strconv"
"strings"
"syscall"
@@ -68,7 +68,7 @@ func GetDiskInfo() []models.DiskInfo {
// Get disk usage information using stat
var stat syscall.Statfs_t
if err := syscall.Statfs(mountPoint, &stat); err != nil {
fmt.Printf("Warning: error getting statfs for %s: %v\n", mountPoint, err)
wdd_log.Warn("获取 %s 的statfs信息失败: %v", mountPoint, err)
continue
}
@@ -85,7 +85,8 @@ func GetDiskInfo() []models.DiskInfo {
// Calculate percentage used
usePercent := "0%"
if total > 0 {
usePercent = fmt.Sprintf("%.1f%%", float64(used)/float64(total)*100)
percentage := float64(used) / float64(total) * 100
usePercent = strconv.FormatFloat(percentage, 'f', 1, 64) + "%"
}
// Determine the physical device and its size

View File

@@ -1,4 +1,4 @@
package services
package host_info
import "cmii-uav-watchdog-common/models"

View File

@@ -1,8 +1,8 @@
package services
package host_info
import (
"cmii-uav-watchdog-common/models"
"fmt"
"cmii-uav-watchdog-common/wdd_log"
"os"
"strings"
)
@@ -19,7 +19,7 @@ var DefaultMotherboardInfo = models.MotherboardInfo{
func readFileWithWarning(path string) ([]byte, error) {
value, err := os.ReadFile(path)
if err != nil {
fmt.Printf("Warning: unable to read file %s: %v\n", path, err)
wdd_log.Warn("无法读取文件 %s: %v", path, err)
return nil, err
}
return value, nil

View File

@@ -1,8 +1,8 @@
package services
package host_info
import (
"cmii-uav-watchdog-common/models"
"fmt"
"cmii-uav-watchdog-common/wdd_log"
"os"
"strconv"
"strings"
@@ -26,7 +26,7 @@ func GetMemoryInfo() models.MemoryInfo {
memInfo := NewMemoryInfo()
data, err := os.ReadFile("/proc/meminfo")
if err != nil {
fmt.Println("Error reading /proc/meminfo:", err)
wdd_log.Error("读取 /proc/meminfo 失败: %v", err)
return memInfo
}
@@ -39,7 +39,7 @@ func GetMemoryInfo() models.MemoryInfo {
key := fields[0]
value, err := strconv.ParseUint(fields[1], 10, 64)
if err != nil {
fmt.Printf("Error parsing value for %s: %v\n", key, err)
wdd_log.Error("解析 %s 的值失败: %v", key, err)
continue
}

View File

@@ -1,8 +1,8 @@
package services
package host_info
import (
"cmii-uav-watchdog-common/models"
"fmt"
"cmii-uav-watchdog-common/wdd_log"
"net"
"strings"
)
@@ -25,7 +25,7 @@ func GetNetworkInterfaces() []models.NetworkInterfaceInfo {
// 获取所有网络接口
ifaces, err := net.Interfaces()
if err != nil {
fmt.Println("Error getting network interfaces:", err)
wdd_log.Error("获取网络接口失败: %v", err)
return []models.NetworkInterfaceInfo{{Name: "unknown", MACAddress: "00:00:00:00:00:00", IPAddresses: []string{}}}
}
@@ -40,7 +40,7 @@ func GetNetworkInterfaces() []models.NetworkInterfaceInfo {
// 获取 MAC 地址
macAddress, err := getMACAddress(iface)
if err != nil {
fmt.Println("Error getting MAC address for", iface.Name, ":", err)
wdd_log.Error("获取网卡 %s 的MAC地址失败: %v", iface.Name, err)
continue
}
@@ -48,7 +48,7 @@ func GetNetworkInterfaces() []models.NetworkInterfaceInfo {
var ipAddresses []string
addrs, err := iface.Addrs()
if err != nil {
fmt.Println("Error getting addresses for", iface.Name, ":", err)
wdd_log.Error("获取网卡 %s 的IP地址失败: %v", iface.Name, err)
continue
}

View File

@@ -1,8 +1,8 @@
package services
package host_info
import (
"cmii-uav-watchdog-common/models"
"log"
"cmii-uav-watchdog-common/wdd_log"
"os"
"strings"
)
@@ -10,16 +10,12 @@ import (
// NewOSInfo 创建并返回一个 OSInfo 实例,设置默认值
func NewOSInfo() models.OSInfo {
return models.OSInfo{
Name: "unknown",
Version: "unknown",
ID: "unknown",
IDLike: "unknown",
VersionID: "unknown",
PrettyName: "unknown",
HomeURL: "unknown",
SupportURL: "unknown",
BugReportURL: "unknown",
PrivacyURL: "unknown",
Name: "unknown",
Version: "unknown",
ID: "unknown",
IDLike: "unknown",
VersionID: "unknown",
PrettyName: "unknown",
}
}
@@ -41,6 +37,14 @@ func GetSystemInfo() models.SystemInfo {
if machineID != "" {
sysInfo.MachineID = machineID
}
// 获取 machine serial
serialID := getMachineSerial()
if serialID != "" {
sysInfo.MachineSerial = serialID
}
// 获取操作系统版本
sysInfo.OS = getOSVersion()
@@ -50,12 +54,26 @@ func GetSystemInfo() models.SystemInfo {
sysInfo.KernelVersion = kernelVersion
}
// 获取节点名称
sysInfo.NodeName = "unknown"
nodeName := os.Getenv("NODE_NAME")
if nodeName != "" {
sysInfo.NodeName = nodeName
}
// 获取节点IP
sysInfo.NodeIP = "unknown"
ip := os.Getenv("NODE_IP")
if ip != "" {
sysInfo.NodeIP = ip
}
return sysInfo
}
func getOSVersion() models.OSInfo {
data, err := os.ReadFile("/etc/os-release")
if err != nil {
log.Printf("Error reading /etc/os-release: %v", err)
wdd_log.Error("读取 /etc/os-release 失败: %v", err)
return NewOSInfo() // 返回默认值
}
@@ -88,25 +106,27 @@ func getOSVersion() models.OSInfo {
osInfo.VersionID = value
case "PRETTY_NAME":
osInfo.PrettyName = value
case "HOME_URL":
osInfo.HomeURL = value
case "SUPPORT_URL":
osInfo.SupportURL = value
case "BUG_REPORT_URL":
osInfo.BugReportURL = value
case "PRIVACY_URL":
osInfo.PrivacyURL = value
}
}
return osInfo
}
// getMachineID 从 /etc/machine-id 文件中获取机器 ID
// getMachineID 从 /sys/devices/virtual/dmi/id/product_uuid 文件中获取机器 ID
func getMachineID() string {
data, err := os.ReadFile("/etc/machine-id")
data, err := os.ReadFile("/sys/devices/virtual/dmi/id/product_uuid")
if err != nil {
log.Printf("Error reading /etc/machine-id: %v", err)
wdd_log.Error("读取 /sys/devices/virtual/dmi/id/product_uuid 失败: %v", err)
return ""
}
return strings.TrimSpace(string(data)) // 去除多余空格
}
// getMachineID 从 /sys/devices/virtual/dmi/id/product_uuid 文件中获取机器 ID
func getMachineSerial() string {
data, err := os.ReadFile("/sys/devices/virtual/dmi/id/product_serial")
if err != nil {
wdd_log.Error("读取 /sys/devices/virtual/dmi/id/product_serial 失败: %v", err)
return ""
}
return strings.TrimSpace(string(data)) // 去除多余空格
@@ -116,8 +136,8 @@ func getMachineID() string {
func getKernelVersion() string {
data, err := os.ReadFile("/proc/version")
if err != nil {
log.Printf("Error reading /proc/version: %v", err)
wdd_log.Error("读取 /proc/version 失败: %v", err)
return ""
}
return string(data)
return strings.TrimSpace(string(data))
}