ESP32/tools/pc-metrics/push-metrics-http.ps1
2026-06-23 20:38:23 +08:00

101 lines
3.1 KiB
PowerShell

param(
[string]$HostName = "192.168.4.1",
[int]$Port = 80,
[double]$IntervalSeconds = 1
)
$ErrorActionPreference = "Stop"
function Get-Percent {
param([double]$Value)
if ([double]::IsNaN($Value) -or [double]::IsInfinity($Value)) {
return 0
}
$rounded = [math]::Round($Value)
if ($rounded -lt 0) { return 0 }
if ($rounded -gt 100) { return 100 }
return [int]$rounded
}
function Get-SystemMetricLine {
$cpu = Get-CimInstance Win32_PerfFormattedData_PerfOS_Processor |
Where-Object { $_.Name -eq "_Total" } |
Select-Object -First 1
$os = Get-CimInstance Win32_OperatingSystem
$totalMemory = [double]$os.TotalVisibleMemorySize
$freeMemory = [double]$os.FreePhysicalMemory
$memoryPercent = if ($totalMemory -gt 0) {
(($totalMemory - $freeMemory) / $totalMemory) * 100
} else {
0
}
$disk = Get-CimInstance Win32_LogicalDisk -Filter "DeviceID='C:'"
$diskPercent = if ($disk -and [double]$disk.Size -gt 0) {
(([double]$disk.Size - [double]$disk.FreeSpace) / [double]$disk.Size) * 100
} else {
0
}
$network = Get-CimInstance Win32_PerfFormattedData_Tcpip_NetworkInterface |
Where-Object {
$_.Name -notmatch "Loopback|isatap|Teredo" -and
([double]$_.BytesReceivedPersec -gt 0 -or [double]$_.BytesSentPersec -gt 0)
}
$rxBytes = 0.0
$txBytes = 0.0
foreach ($adapter in $network) {
$rxBytes += [double]$adapter.BytesReceivedPersec
$txBytes += [double]$adapter.BytesSentPersec
}
$cpuPercent = Get-Percent ([double]$cpu.PercentProcessorTime)
$memPercent = Get-Percent $memoryPercent
$diskUsedPercent = Get-Percent $diskPercent
$rxKbps = [int][math]::Max(0, [math]::Round($rxBytes / 1024))
$txKbps = [int][math]::Max(0, [math]::Round($txBytes / 1024))
return "SYS,$cpuPercent,$memPercent,$diskUsedPercent,$rxKbps,$txKbps"
}
function Send-MetricLine {
param([string]$Line)
$body = [System.Text.Encoding]::ASCII.GetBytes($Line)
$header = "POST /metrics HTTP/1.1`r`nHost: $HostName`r`nContent-Type: text/plain`r`nContent-Length: $($body.Length)`r`nConnection: close`r`n`r`n"
$headerBytes = [System.Text.Encoding]::ASCII.GetBytes($header)
$client = [System.Net.Sockets.TcpClient]::new()
$connect = $client.BeginConnect($HostName, $Port, $null, $null)
if (-not $connect.AsyncWaitHandle.WaitOne(1200)) {
$client.Close()
throw "connect timeout"
}
$client.EndConnect($connect)
$client.SendTimeout = 1200
$client.ReceiveTimeout = 1200
try {
$stream = $client.GetStream()
$stream.Write($headerBytes, 0, $headerBytes.Length)
$stream.Write($body, 0, $body.Length)
$stream.Flush()
} finally {
$client.Close()
}
}
Write-Host "Pushing PC metrics to http://$HostName/metrics. Press Ctrl+C to stop."
while ($true) {
$line = Get-SystemMetricLine
try {
Send-MetricLine -Line $line
Write-Host $line
} catch {
Write-Host "send failed: $($_.Exception.Message)"
}
Start-Sleep -Seconds $IntervalSeconds
}