github.com/Rookout/GoSDK@v0.1.48/pkg/com_ws/simple_backoff.go (about) 1 package com_ws 2 3 import ( 4 "context" 5 "time" 6 7 "github.com/Rookout/GoSDK/pkg/config" 8 "github.com/Rookout/GoSDK/pkg/logger" 9 ) 10 11 type Backoff interface { 12 AfterConnect() 13 AfterDisconnect(context.Context) 14 } 15 16 type backoff struct { 17 connectTime time.Time 18 connected bool 19 nextBackoff time.Duration 20 } 21 22 func NewBackoff() *backoff { 23 return &backoff{ 24 nextBackoff: config.BackoffConfig().DefaultBackoff, 25 } 26 } 27 28 func (b *backoff) AfterConnect() { 29 b.connectTime = time.Now() 30 b.connected = true 31 } 32 33 func (b *backoff) AfterDisconnect(ctx context.Context) { 34 if b.connected && time.Since(b.connectTime) > config.BackoffConfig().ResetBackoffTimeout { 35 b.reset() 36 } 37 38 b.connected = false 39 logger.Logger().Debugf("Backing off %g seconds\n", b.nextBackoff.Seconds()) 40 timer := time.NewTimer(b.nextBackoff) 41 defer timer.Stop() 42 select { 43 case <-timer.C: 44 case <-ctx.Done(): 45 return 46 } 47 48 b.nextBackoff *= 2 49 maxBackoff := config.BackoffConfig().MaxBackoff 50 if maxBackoff != 0 && b.nextBackoff > maxBackoff { 51 b.nextBackoff = maxBackoff 52 } 53 } 54 55 func (b *backoff) reset() { 56 b.nextBackoff = config.BackoffConfig().DefaultBackoff 57 }