package main import ( "bufio" "fmt" "os" "strconv" "strings" ) type MemoryMetrics struct { TotalBytes uint64 `json:"totalBytes"` UsedBytes uint64 `json:"usedBytes"` AvailableBytes uint64 `json:"availableBytes"` CachedBytes uint64 `json:"cachedBytes"` BuffersBytes uint64 `json:"buffersBytes"` SwapTotalBytes uint64 `json:"swapTotalBytes"` SwapUsedBytes uint64 `json:"swapUsedBytes"` UsagePercent float64 `json:"usagePercent"` SwapPercent float64 `json:"swapPercent"` } func readMemoryMetrics(path string) (MemoryMetrics, error) { file, err := os.Open(path) if err != nil { return MemoryMetrics{}, err } defer file.Close() values := make(map[string]uint64) scanner := bufio.NewScanner(file) for scanner.Scan() { fields := strings.Fields(scanner.Text()) if len(fields) < 2 { continue } key := strings.TrimSuffix(fields[0], ":") value, err := strconv.ParseUint(fields[1], 10, 64) if err == nil { values[key] = value * 1024 } } if err := scanner.Err(); err != nil { return MemoryMetrics{}, err } total := values["MemTotal"] available := values["MemAvailable"] if total == 0 { return MemoryMetrics{}, fmt.Errorf("MemTotal не найден в %s", path) } if available > total { available = total } used := total - available swapTotal := values["SwapTotal"] swapFree := values["SwapFree"] if swapFree > swapTotal { swapFree = swapTotal } swapUsed := swapTotal - swapFree result := MemoryMetrics{ TotalBytes: total, UsedBytes: used, AvailableBytes: available, CachedBytes: values["Cached"] + values["SReclaimable"], BuffersBytes: values["Buffers"], SwapTotalBytes: swapTotal, SwapUsedBytes: swapUsed, UsagePercent: float64(used) / float64(total) * 100, } if swapTotal > 0 { result.SwapPercent = float64(swapUsed) / float64(swapTotal) * 100 } return result, nil }