feat: publish sanitized custom.97 source
This commit is contained in:
1022 files changed
+69903
-19207
No files matched your search
@@ -0,0 +1,113 @@
|
||||
package common
|
||||
|
||||
import (
|
||||
"crypto/tls"
|
||||
"maps"
|
||||
"net/http/httptrace"
|
||||
"sync"
|
||||
"time"
|
||||
)
|
||||
|
||||
const UpstreamTimingContextKey = "responses_upstream_timing"
|
||||
|
||||
// UpstreamTiming contains only transport metadata and request-relative times.
|
||||
// HTTP callbacks can run concurrently with streaming and log checkpoints.
|
||||
type UpstreamTiming struct {
|
||||
mu sync.Mutex
|
||||
start time.Time
|
||||
events map[string]float64
|
||||
attempt int
|
||||
channel int
|
||||
bodyBytes int64
|
||||
reused bool
|
||||
gotConn bool
|
||||
getConnCount int
|
||||
writeCount int
|
||||
writeFailed bool
|
||||
protocol string
|
||||
status int
|
||||
}
|
||||
|
||||
func NewUpstreamTiming(start time.Time, attempt, channel int, bodyBytes int64) *UpstreamTiming {
|
||||
if start.IsZero() {
|
||||
start = time.Now()
|
||||
}
|
||||
t := &UpstreamTiming{start: start, events: make(map[string]float64), attempt: attempt, channel: channel, bodyBytes: bodyBytes}
|
||||
t.Mark("upstream_start")
|
||||
return t
|
||||
}
|
||||
|
||||
func (t *UpstreamTiming) Mark(event string) {
|
||||
if t == nil {
|
||||
return
|
||||
}
|
||||
t.mu.Lock()
|
||||
defer t.mu.Unlock()
|
||||
if _, exists := t.events[event]; !exists {
|
||||
t.events[event] = float64(time.Since(t.start).Microseconds()) / 1000
|
||||
}
|
||||
}
|
||||
|
||||
func (t *UpstreamTiming) ClientTrace() *httptrace.ClientTrace {
|
||||
return &httptrace.ClientTrace{
|
||||
GetConn: func(string) {
|
||||
t.Mark("get_connection")
|
||||
t.mu.Lock()
|
||||
t.getConnCount++
|
||||
t.mu.Unlock()
|
||||
},
|
||||
DNSStart: func(httptrace.DNSStartInfo) { t.Mark("dns_start") },
|
||||
DNSDone: func(httptrace.DNSDoneInfo) { t.Mark("dns_done") },
|
||||
ConnectStart: func(string, string) { t.Mark("tcp_start") },
|
||||
ConnectDone: func(string, string, error) { t.Mark("tcp_done") },
|
||||
TLSHandshakeStart: func() { t.Mark("tls_start") },
|
||||
TLSHandshakeDone: func(tls.ConnectionState, error) { t.Mark("tls_done") },
|
||||
GotConn: func(info httptrace.GotConnInfo) {
|
||||
t.Mark("connection_ready")
|
||||
t.mu.Lock()
|
||||
t.reused, t.gotConn = info.Reused, true
|
||||
t.mu.Unlock()
|
||||
},
|
||||
WroteRequest: func(info httptrace.WroteRequestInfo) {
|
||||
t.mu.Lock()
|
||||
defer t.mu.Unlock()
|
||||
t.writeCount++
|
||||
t.writeFailed = t.writeFailed || info.Err != nil
|
||||
if info.Err == nil {
|
||||
t.events["request_sent"] = float64(time.Since(t.start).Microseconds()) / 1000
|
||||
}
|
||||
},
|
||||
GotFirstResponseByte: func() { t.Mark("response_first_byte") },
|
||||
}
|
||||
}
|
||||
|
||||
func (t *UpstreamTiming) Response(protocol string, status int) {
|
||||
if t == nil {
|
||||
return
|
||||
}
|
||||
t.Mark("response_headers")
|
||||
t.mu.Lock()
|
||||
defer t.mu.Unlock()
|
||||
t.protocol, t.status = protocol, status
|
||||
}
|
||||
|
||||
func (t *UpstreamTiming) Snapshot() map[string]any {
|
||||
if t == nil {
|
||||
return nil
|
||||
}
|
||||
t.mu.Lock()
|
||||
defer t.mu.Unlock()
|
||||
events := maps.Clone(t.events)
|
||||
result := map[string]any{
|
||||
"events_ms": events, "attempt": t.attempt, "channel_id": t.channel,
|
||||
"request_body_bytes": t.bodyBytes, "get_connection_count": t.getConnCount,
|
||||
"write_count": t.writeCount, "write_failed": t.writeFailed,
|
||||
}
|
||||
if t.gotConn {
|
||||
result["connection_reused"] = t.reused
|
||||
}
|
||||
if t.protocol != "" {
|
||||
result["protocol"], result["status"] = t.protocol, t.status
|
||||
}
|
||||
return result
|
||||
}
|
||||
Reference in new issue
Block a user