add traffic reset for stats

This commit is contained in:
ginuerzh
2024-12-24 20:11:22 +08:00
parent 914a4622fd
commit 06d993023f
41 changed files with 407 additions and 143 deletions
+7 -3
View File
@@ -2,13 +2,14 @@ package observer
import (
"context"
"errors"
"io"
"github.com/go-gost/core/logger"
"github.com/go-gost/core/observer"
"github.com/go-gost/core/observer/stats"
"github.com/go-gost/plugin/observer/proto"
"github.com/go-gost/x/internal/plugin"
xstats "github.com/go-gost/x/observer/stats"
"github.com/go-gost/x/service"
"google.golang.org/grpc"
)
@@ -67,7 +68,7 @@ func (p *grpcPlugin) Observe(ctx context.Context, events []observer.Event, opts
},
})
case observer.EventStats:
ev := event.(stats.StatsEvent)
ev := event.(xstats.StatsEvent)
req.Events = append(req.Events, &proto.Event{
Kind: ev.Kind,
Service: ev.Service,
@@ -83,11 +84,14 @@ func (p *grpcPlugin) Observe(ctx context.Context, events []observer.Event, opts
})
}
}
_, err := p.client.Observe(ctx, &req)
reply, err := p.client.Observe(ctx, &req)
if err != nil {
p.log.Error(err)
return err
}
if reply == nil || !reply.Ok {
return errors.New("observe failed")
}
return nil
}
+14 -5
View File
@@ -4,14 +4,14 @@ import (
"bytes"
"context"
"encoding/json"
"fmt"
"errors"
"net/http"
"strings"
"github.com/go-gost/core/logger"
"github.com/go-gost/core/observer"
"github.com/go-gost/core/observer/stats"
"github.com/go-gost/x/internal/plugin"
xstats "github.com/go-gost/x/observer/stats"
"github.com/go-gost/x/service"
)
@@ -41,7 +41,7 @@ type statusEvent struct {
Msg string `json:"msg"`
}
type observeResponse struct {
type httpPluginResponse struct {
OK bool `json:"ok"`
}
@@ -94,7 +94,7 @@ func (p *httpPlugin) Observe(ctx context.Context, events []observer.Event, opts
},
})
case observer.EventStats:
ev := e.(stats.StatsEvent)
ev := e.(xstats.StatsEvent)
r.Events = append(r.Events, event{
Kind: ev.Kind,
Service: ev.Service,
@@ -131,7 +131,16 @@ func (p *httpPlugin) Observe(ctx context.Context, events []observer.Event, opts
defer resp.Body.Close()
if resp.StatusCode != http.StatusOK {
return fmt.Errorf(resp.Status)
return errors.New(resp.Status)
}
res := httpPluginResponse{}
if err := json.NewDecoder(resp.Body).Decode(&res); err != nil {
return err
}
if !res.OK {
return errors.New("observe failed")
}
return nil
+102
View File
@@ -0,0 +1,102 @@
package stats
import (
"sync/atomic"
"github.com/go-gost/core/observer"
"github.com/go-gost/core/observer/stats"
)
type Stats struct {
updated atomic.Bool
totalConns atomic.Uint64
currentConns atomic.Uint64
inputBytes atomic.Uint64
outputBytes atomic.Uint64
totalErrs atomic.Uint64
resetTraffic bool
}
func NewStats(resetTraffic bool) stats.Stats {
return &Stats{
resetTraffic: resetTraffic,
}
}
func (s *Stats) Add(kind stats.Kind, n int64) {
if s == nil {
return
}
switch kind {
case stats.KindTotalConns:
if n > 0 {
s.totalConns.Add(uint64(n))
}
case stats.KindCurrentConns:
s.currentConns.Add(uint64(n))
case stats.KindInputBytes:
s.inputBytes.Add(uint64(n))
case stats.KindOutputBytes:
s.outputBytes.Add(uint64(n))
case stats.KindTotalErrs:
if n > 0 {
s.totalErrs.Add(uint64(n))
}
}
s.updated.Store(true)
}
func (s *Stats) Get(kind stats.Kind) uint64 {
if s == nil {
return 0
}
switch kind {
case stats.KindTotalConns:
return s.totalConns.Load()
case stats.KindCurrentConns:
return s.currentConns.Load()
case stats.KindInputBytes:
if s.resetTraffic {
return s.inputBytes.Swap(0)
}
return s.inputBytes.Load()
case stats.KindOutputBytes:
if s.resetTraffic {
return s.outputBytes.Swap(0)
}
return s.outputBytes.Load()
case stats.KindTotalErrs:
return s.totalErrs.Load()
}
return 0
}
func (s *Stats) Reset() {
s.updated.Store(false)
s.totalConns.Store(0)
s.currentConns.Store(0)
s.inputBytes.Store(0)
s.outputBytes.Store(0)
s.totalErrs.Store(0)
}
func (s *Stats) IsUpdated() bool {
return s.updated.Swap(false)
}
type StatsEvent struct {
Kind string
Service string
Client string
TotalConns uint64
CurrentConns uint64
InputBytes uint64
OutputBytes uint64
TotalErrs uint64
}
func (StatsEvent) Type() observer.EventType {
return observer.EventStats
}
+6 -6
View File
@@ -19,12 +19,12 @@ var (
type conn struct {
net.Conn
stats *stats.Stats
stats stats.Stats
closed chan struct{}
mu sync.Mutex
}
func WrapConn(c net.Conn, pStats *stats.Stats) net.Conn {
func WrapConn(c net.Conn, pStats stats.Stats) net.Conn {
if pStats == nil {
return c
}
@@ -84,10 +84,10 @@ func (c *conn) Metadata() metadata.Metadata {
type packetConn struct {
net.PacketConn
stats *stats.Stats
stats stats.Stats
}
func WrapPacketConn(pc net.PacketConn, stats *stats.Stats) net.PacketConn {
func WrapPacketConn(pc net.PacketConn, stats stats.Stats) net.PacketConn {
if stats == nil {
return pc
}
@@ -118,10 +118,10 @@ func (c *packetConn) Metadata() metadata.Metadata {
type udpConn struct {
net.PacketConn
stats *stats.Stats
stats stats.Stats
}
func WrapUDPConn(pc net.PacketConn, stats *stats.Stats) udp.Conn {
func WrapUDPConn(pc net.PacketConn, stats stats.Stats) udp.Conn {
return &udpConn{
PacketConn: pc,
stats: stats,
+2 -2
View File
@@ -9,10 +9,10 @@ import (
// readWriter is an io.ReadWriter with Stats.
type readWriter struct {
io.ReadWriter
stats *stats.Stats
stats stats.Stats
}
func WrapReadWriter(rw io.ReadWriter, stats *stats.Stats) io.ReadWriter {
func WrapReadWriter(rw io.ReadWriter, stats stats.Stats) io.ReadWriter {
if stats == nil {
return rw
}
+2 -2
View File
@@ -7,11 +7,11 @@ import (
)
type listener struct {
stats *stats.Stats
stats stats.Stats
net.Listener
}
func WrapListener(ln net.Listener, stats *stats.Stats) net.Listener {
func WrapListener(ln net.Listener, stats stats.Stats) net.Listener {
if stats == nil {
return ln
}