mirror of
https://github.com/0xJacky/nginx-ui.git
synced 2025-05-11 02:15:48 +02:00
refactor(analytic): improved network stat #913
This commit is contained in:
parent
789698a0d4
commit
efc9b1c365
3 changed files with 69 additions and 6 deletions
|
@ -2,6 +2,7 @@ package analytic
|
||||||
|
|
||||||
import (
|
import (
|
||||||
stdnet "net"
|
stdnet "net"
|
||||||
|
"strings"
|
||||||
|
|
||||||
"github.com/shirou/gopsutil/v4/net"
|
"github.com/shirou/gopsutil/v4/net"
|
||||||
"github.com/uozi-tech/cosy/logger"
|
"github.com/uozi-tech/cosy/logger"
|
||||||
|
@ -46,6 +47,17 @@ func GetNetworkStat() (data *net.IOCountersStat, err error) {
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Skip common virtual interfaces by name pattern
|
||||||
|
if isVirtualInterface(iface.Name) {
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
|
||||||
|
// Handle container main interfaces like eth0 in container environments
|
||||||
|
if isContainerInterface(iface.Name) {
|
||||||
|
externalInterfaces[iface.Name] = true
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
|
||||||
// Get addresses for this interface
|
// Get addresses for this interface
|
||||||
addrs, err := iface.Addrs()
|
addrs, err := iface.Addrs()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
@ -106,6 +118,50 @@ func GetNetworkStat() (data *net.IOCountersStat, err error) {
|
||||||
}, nil
|
}, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// isVirtualInterface checks if the interface is a virtual one based on name patterns
|
||||||
|
func isVirtualInterface(name string) bool {
|
||||||
|
// Common virtual interface name patterns
|
||||||
|
virtualPatterns := []string{
|
||||||
|
"veth", "virbr", "vnet", "vmnet", "vboxnet", "docker",
|
||||||
|
"br-", "bridge", "tun", "tap", "bond", "dummy",
|
||||||
|
"vpn", "ipsec", "gre", "sit", "vlan", "virt",
|
||||||
|
"wg", "vmk", "ib", "vxlan", "geneve", "ovs",
|
||||||
|
"hyperv", "hyper-v", "awdl", "llw", "utun",
|
||||||
|
"vpn", "zt", "zerotier", "wireguard",
|
||||||
|
}
|
||||||
|
|
||||||
|
for _, pattern := range virtualPatterns {
|
||||||
|
if strings.Contains(strings.ToLower(name), pattern) {
|
||||||
|
return true
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
|
||||||
|
// isContainerInterface checks if this is a main container interface
|
||||||
|
func isContainerInterface(name string) bool {
|
||||||
|
// Common main container interface patterns
|
||||||
|
// eth0 is usually the main interface inside containers
|
||||||
|
// en0, en1 are common physical interfaces on macOS
|
||||||
|
// ens/enp/eno are common physical interfaces on Linux
|
||||||
|
containerPatterns := []string{
|
||||||
|
"eth0", "en0", "en1",
|
||||||
|
"ens", "enp", "eno",
|
||||||
|
"eth1", "eth2", // Potential physical interfaces
|
||||||
|
"wlan", "wifi", "wl", // Wireless interfaces
|
||||||
|
"bond0", // Bonded interfaces that might be external
|
||||||
|
}
|
||||||
|
|
||||||
|
for _, pattern := range containerPatterns {
|
||||||
|
if strings.HasPrefix(strings.ToLower(name), pattern) {
|
||||||
|
return true
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
|
||||||
// isRealExternalIP checks if an IP is a genuine external (public) IP
|
// isRealExternalIP checks if an IP is a genuine external (public) IP
|
||||||
func isRealExternalIP(ip stdnet.IP, ipNet *stdnet.IPNet) bool {
|
func isRealExternalIP(ip stdnet.IP, ipNet *stdnet.IPNet) bool {
|
||||||
// Skip if it's not a global unicast address
|
// Skip if it's not a global unicast address
|
||||||
|
|
|
@ -68,25 +68,32 @@ func recordCpu(now time.Time) {
|
||||||
}
|
}
|
||||||
|
|
||||||
func recordNetwork(now time.Time) {
|
func recordNetwork(now time.Time) {
|
||||||
// Get separate statistics for each interface
|
// Get network statistics using GetNetworkStat which includes Ethernet interfaces
|
||||||
networkStats, err := GetNetworkStat()
|
networkStats, err := GetNetworkStat()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
logger.Error(err)
|
logger.Error(err)
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
LastNetRecv = networkStats.BytesRecv
|
// Calculate usage since last record
|
||||||
LastNetSent = networkStats.BytesSent
|
bytesRecv := networkStats.BytesRecv - LastNetRecv
|
||||||
|
bytesSent := networkStats.BytesSent - LastNetSent
|
||||||
|
|
||||||
|
// Update records
|
||||||
NetRecvRecord = append(NetRecvRecord, Usage[uint64]{
|
NetRecvRecord = append(NetRecvRecord, Usage[uint64]{
|
||||||
Time: now,
|
Time: now,
|
||||||
Usage: networkStats.BytesRecv - LastNetRecv,
|
Usage: bytesRecv,
|
||||||
})
|
})
|
||||||
NetSentRecord = append(NetSentRecord, Usage[uint64]{
|
NetSentRecord = append(NetSentRecord, Usage[uint64]{
|
||||||
Time: now,
|
Time: now,
|
||||||
Usage: networkStats.BytesSent - LastNetSent,
|
Usage: bytesSent,
|
||||||
})
|
})
|
||||||
|
|
||||||
|
// Update last values
|
||||||
|
LastNetRecv = networkStats.BytesRecv
|
||||||
|
LastNetSent = networkStats.BytesSent
|
||||||
|
|
||||||
|
// Limit record size
|
||||||
if len(NetRecvRecord) > 100 {
|
if len(NetRecvRecord) > 100 {
|
||||||
NetRecvRecord = NetRecvRecord[1:]
|
NetRecvRecord = NetRecvRecord[1:]
|
||||||
}
|
}
|
||||||
|
|
|
@ -15,7 +15,7 @@ func TestCreatesTransportWithDefaultSettings(t *testing.T) {
|
||||||
require.NoError(t, err)
|
require.NoError(t, err)
|
||||||
assert.NotNil(t, transport)
|
assert.NotNil(t, transport)
|
||||||
assert.ObjectsAreEqual(http.ProxyFromEnvironment, transport.Proxy)
|
assert.ObjectsAreEqual(http.ProxyFromEnvironment, transport.Proxy)
|
||||||
assert.Equal(t, settings.ServerSettings.InsecureSkipVerify, transport.TLSClientConfig.InsecureSkipVerify)
|
assert.Equal(t, settings.HTTPSettings.InsecureSkipVerify, transport.TLSClientConfig.InsecureSkipVerify)
|
||||||
}
|
}
|
||||||
|
|
||||||
func TestCreatesTransportWithCustomProxy(t *testing.T) {
|
func TestCreatesTransportWithCustomProxy(t *testing.T) {
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue