|
1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192 |
- package accessstat
-
- import (
- "sync"
- "time"
-
- "gitlink.org.cn/cloudream/common/pkgs/async"
- "gitlink.org.cn/cloudream/common/pkgs/logger"
- "gitlink.org.cn/cloudream/jcs-pub/client/internal/db"
- clitypes "gitlink.org.cn/cloudream/jcs-pub/client/types"
- )
-
- type AccessStatEventChan = async.UnboundChannel[AccessStatEvent]
-
- type AccessStatEvent interface {
- IsAccessStatEvent() bool
- }
-
- type ExitEvent struct {
- AccessStatEvent
- Err error
- }
-
- type AccessStat struct {
- cfg Config
- done chan any
- stats []db.AddAccessStatEntry
- lock sync.Mutex
- db *db.DB
- }
-
- func NewAccessStat(cfg Config, db *db.DB) *AccessStat {
- return &AccessStat{
- cfg: cfg,
- done: make(chan any),
- db: db,
- }
- }
-
- func (p *AccessStat) AddAccessCounter(objID clitypes.ObjectID, pkgID clitypes.PackageID, spaceID clitypes.UserSpaceID, value float64) {
- p.lock.Lock()
- defer p.lock.Unlock()
-
- p.stats = append(p.stats, db.AddAccessStatEntry{
- ObjectID: objID,
- PackageID: pkgID,
- UserSpaceID: spaceID,
- Counter: value,
- })
- }
-
- func (p *AccessStat) Start() *AccessStatEventChan {
- ch := async.NewUnboundChannel[AccessStatEvent]()
-
- go func() {
- ticker := time.NewTicker(p.cfg.ReportInterval)
- defer ticker.Stop()
-
- for {
- select {
- case <-ticker.C:
- case <-p.done:
- ch.Send(ExitEvent{})
- return
- }
-
- p.lock.Lock()
- st := p.stats
- p.stats = nil
- p.lock.Unlock()
-
- if len(st) == 0 {
- continue
- }
-
- err := db.DoTx10(p.db, p.db.Package().BatchAddPackageAccessStat, st)
- if err != nil {
- logger.Errorf("add all package access stat counter: %v", err)
-
- p.lock.Lock()
- p.stats = append(p.stats, st...)
- p.lock.Unlock()
- continue
- }
- }
- }()
- return ch
- }
-
- func (p *AccessStat) Stop() {
- close(p.done)
- }
|