package canceler import ( "context" "time" ) type Instance struct { ctx context.Context cancelFunc context.CancelFunc timer *time.Timer timeout time.Duration } func New(ctx context.Context, cancelFunc context.CancelFunc, timeout time.Duration) *Instance { instance := &Instance{ ctx, cancelFunc, time.NewTimer(timeout), timeout, } go instance.wait() return instance } func (i *Instance) Update() bool { if !i.timer.Stop() { return false } if !i.timer.Reset(i.timeout) { return false } return true } func (i *Instance) wait() { select { case <-i.timer.C: case <-i.ctx.Done(): } i.Close() } func (i *Instance) Close() error { i.timer.Stop() i.cancelFunc() return nil }