1package backoff 2 3import ( 4 "context" 5 "errors" 6 "fmt" 7 "log" 8 "testing" 9 "time" 10) 11 12func TestRetry(t *testing.T) { 13 const successOn = 3 14 var i = 0 15 16 // This function is successful on "successOn" calls. 17 f := func() error { 18 i++ 19 log.Printf("function is called %d. time\n", i) 20 21 if i == successOn { 22 log.Println("OK") 23 return nil 24 } 25 26 log.Println("error") 27 return errors.New("error") 28 } 29 30 err := Retry(f, NewExponentialBackOff()) 31 if err != nil { 32 t.Errorf("unexpected error: %s", err.Error()) 33 } 34 if i != successOn { 35 t.Errorf("invalid number of retries: %d", i) 36 } 37} 38 39func TestRetryContext(t *testing.T) { 40 var cancelOn = 3 41 var i = 0 42 43 ctx, cancel := context.WithCancel(context.Background()) 44 defer cancel() 45 46 // This function cancels context on "cancelOn" calls. 47 f := func() error { 48 i++ 49 log.Printf("function is called %d. time\n", i) 50 51 // cancelling the context in the operation function is not a typical 52 // use-case, however it allows to get predictable test results. 53 if i == cancelOn { 54 cancel() 55 } 56 57 log.Println("error") 58 return fmt.Errorf("error (%d)", i) 59 } 60 61 err := Retry(f, WithContext(NewConstantBackOff(time.Millisecond), ctx)) 62 if err == nil { 63 t.Errorf("error is unexpectedly nil") 64 } 65 if err.Error() != "error (3)" { 66 t.Errorf("unexpected error: %s", err.Error()) 67 } 68 if i != cancelOn { 69 t.Errorf("invalid number of retries: %d", i) 70 } 71} 72 73func TestRetryPermenent(t *testing.T) { 74 const permanentOn = 3 75 var i = 0 76 77 // This function fails permanently after permanentOn tries 78 f := func() error { 79 i++ 80 log.Printf("function is called %d. time\n", i) 81 82 if i == permanentOn { 83 log.Println("permanent error") 84 return Permanent(errors.New("permanent error")) 85 } 86 87 log.Println("error") 88 return errors.New("error") 89 } 90 91 err := Retry(f, NewExponentialBackOff()) 92 if err == nil || err.Error() != "permanent error" { 93 t.Errorf("unexpected error: %s", err) 94 } 95 if i != permanentOn { 96 t.Errorf("invalid number of retries: %d", i) 97 } 98} 99