69 lines
1.3 KiB
Go
69 lines
1.3 KiB
Go
|
// Copyright (C) 2019 Storj Labs, Inc.
|
||
|
// See LICENSE for copying information.
|
||
|
|
||
|
package metainfo
|
||
|
|
||
|
import (
|
||
|
"strings"
|
||
|
"sync"
|
||
|
|
||
|
"github.com/spacemonkeygo/monkit/v3"
|
||
|
"github.com/zeebo/errs"
|
||
|
|
||
|
"storj.io/common/useragent"
|
||
|
)
|
||
|
|
||
|
const uplinkProduct = "uplink"
|
||
|
|
||
|
type versionOccurrence struct {
|
||
|
Version string
|
||
|
Method string
|
||
|
}
|
||
|
|
||
|
type versionCollector struct {
|
||
|
mu sync.Mutex
|
||
|
versions map[versionOccurrence]*monkit.Meter
|
||
|
}
|
||
|
|
||
|
func newVersionCollector() *versionCollector {
|
||
|
return &versionCollector{
|
||
|
versions: make(map[versionOccurrence]*monkit.Meter),
|
||
|
}
|
||
|
}
|
||
|
|
||
|
func (vc *versionCollector) collect(useragentRaw []byte, method string) error {
|
||
|
var meter *monkit.Meter
|
||
|
|
||
|
version := "unknown"
|
||
|
if len(useragentRaw) != 0 {
|
||
|
entries, err := useragent.ParseEntries(useragentRaw)
|
||
|
if err != nil {
|
||
|
return errs.New("invalid user agent %q: %v", string(useragentRaw), err)
|
||
|
}
|
||
|
|
||
|
for _, entry := range entries {
|
||
|
if strings.EqualFold(entry.Product, uplinkProduct) {
|
||
|
version = entry.Version
|
||
|
break
|
||
|
}
|
||
|
}
|
||
|
}
|
||
|
|
||
|
vo := versionOccurrence{
|
||
|
Version: version,
|
||
|
Method: method,
|
||
|
}
|
||
|
|
||
|
vc.mu.Lock()
|
||
|
meter, ok := vc.versions[vo]
|
||
|
if !ok {
|
||
|
meter = monkit.NewMeter(monkit.NewSeriesKey("uplink_versions").WithTag("version", version).WithTag("method", method))
|
||
|
mon.Chain(meter)
|
||
|
vc.versions[vo] = meter
|
||
|
}
|
||
|
vc.mu.Unlock()
|
||
|
|
||
|
meter.Mark(1)
|
||
|
return nil
|
||
|
}
|