// WithBackoff implements retry with exponential backoff using // the supplied options as parameters. When fn returns Continue // and the number of retry attempts haven't been exhausted, fn is // retried. When fn returns Break, retry ends. As a special case, // if fn returns Reset, the backoff and retry count are reset to // starting values and the next retry occurs immediately. Returns an // error if the maximum number of retries is exceeded or if the fn // returns an error. func WithBackoff(opts Options, fn func() (Status, error)) error { backoff := opts.Backoff tag := opts.Tag if tag == "" { tag = "invocation" } for count := 1; true; count++ { status, err := fn() if status == Break { return err } if err != nil && (!opts.UseV1Info || log.V(1) == true) { log.InfoDepth(1, tag, " failed an iteration: ", err) } var wait time.Duration if status == Reset { backoff = opts.Backoff wait = 0 count = 0 if !opts.UseV1Info || log.V(1) == true { log.InfoDepth(1, tag, " failed; retrying immediately") } } else { if opts.MaxAttempts > 0 && count >= opts.MaxAttempts { return &MaxAttemptsError{opts.MaxAttempts} } if !opts.UseV1Info || log.V(1) == true { log.InfoDepth(1, tag, " failed; retrying in ", backoff) } wait = backoff + time.Duration(rand.Float64()*float64(backoff.Nanoseconds())*retryJitter) // Increase backoff for next iteration. backoff = time.Duration(float64(backoff) * opts.Constant) if backoff > opts.MaxBackoff { backoff = opts.MaxBackoff } } // Wait before retry. select { case <-time.After(wait): // Continue retrying. case <-opts.Stopper.ShouldStop(): return util.Errorf("%s retry loop stopped", tag) } } return nil }
func (r *raftLogger) Infof(format string, v ...interface{}) { if log.V(1) { s := r.prependContext(format, v) log.InfoDepth(1, s) } }
func (*raftLogger) Info(v ...interface{}) { if log.V(1) { log.InfoDepth(1, v...) } }
func (*raftLogger) Debug(v ...interface{}) { if log.V(2) { log.InfoDepth(1, v...) } }
func (*raftLogger) Infof(format string, v ...interface{}) { if log.V(1) { s := fmt.Sprintf(format, v...) log.InfoDepth(1, s) } }