cloudflare/cloudflared

Public

mirrored from https://github.com/cloudflare/cloudflaredAvailable

CodeCommitsIssuesPull requestsActionsInsightsSecurity
2019.6.0

Branches

Tags

  • No tags available.
0Branches0Tags
Go to file
Add file
Code

Clone

HTTPS

Download ZIP

origin/backoffhandler_test.go

147lines · modecode

1package origin
2
3import (
4 "context"
5 "testing"
6 "time"
7)
8
9func immediateTimeAfter(time.Duration) <-chan time.Time {
10 c := make(chan time.Time, 1)
11 c <- time.Now()
12 return c
13}
14
15func TestBackoffRetries(t *testing.T) {
16 // make backoff return immediately
17 timeAfter = immediateTimeAfter
18 ctx := context.Background()
19 backoff := BackoffHandler{MaxRetries: 3}
20 if !backoff.Backoff(ctx) {
21 t.Fatalf("backoff failed immediately")
22 }
23 if !backoff.Backoff(ctx) {
24 t.Fatalf("backoff failed after 1 retry")
25 }
26 if !backoff.Backoff(ctx) {
27 t.Fatalf("backoff failed after 2 retry")
28 }
29 if backoff.Backoff(ctx) {
30 t.Fatalf("backoff allowed after 3 (max) retries")
31 }
32}
33
34func TestBackoffCancel(t *testing.T) {
35 // prevent backoff from returning normally
36 timeAfter = func(time.Duration) <-chan time.Time { return make(chan time.Time) }
37 ctx, cancelFunc := context.WithCancel(context.Background())
38 backoff := BackoffHandler{MaxRetries: 3}
39 cancelFunc()
40 if backoff.Backoff(ctx) {
41 t.Fatalf("backoff allowed after cancel")
42 }
43 if _, ok := backoff.GetBackoffDuration(ctx); ok {
44 t.Fatalf("backoff allowed after cancel")
45 }
46}
47
48func TestBackoffGracePeriod(t *testing.T) {
49 currentTime := time.Now()
50 // make timeNow return whatever we like
51 timeNow = func() time.Time { return currentTime }
52 // make backoff return immediately
53 timeAfter = immediateTimeAfter
54 ctx := context.Background()
55 backoff := BackoffHandler{MaxRetries: 1}
56 if !backoff.Backoff(ctx) {
57 t.Fatalf("backoff failed immediately")
58 }
59 // the next call to Backoff would fail unless it's after the grace period
60 backoff.SetGracePeriod()
61 // advance time to after the grace period (~4 seconds) and see what happens
62 currentTime = currentTime.Add(time.Second * 5)
63 if !backoff.Backoff(ctx) {
64 t.Fatalf("backoff failed after the grace period expired")
65 }
66 // confirm we ignore grace period after backoff
67 if backoff.Backoff(ctx) {
68 t.Fatalf("backoff allowed after 1 (max) retry")
69 }
70}
71
72func TestGetBackoffDurationRetries(t *testing.T) {
73 // make backoff return immediately
74 timeAfter = immediateTimeAfter
75 ctx := context.Background()
76 backoff := BackoffHandler{MaxRetries: 3}
77 if _, ok := backoff.GetBackoffDuration(ctx); !ok {
78 t.Fatalf("backoff failed immediately")
79 }
80 backoff.Backoff(ctx) // noop
81 if _, ok := backoff.GetBackoffDuration(ctx); !ok {
82 t.Fatalf("backoff failed after 1 retry")
83 }
84 backoff.Backoff(ctx) // noop
85 if _, ok := backoff.GetBackoffDuration(ctx); !ok {
86 t.Fatalf("backoff failed after 2 retry")
87 }
88 backoff.Backoff(ctx) // noop
89 if _, ok := backoff.GetBackoffDuration(ctx); ok {
90 t.Fatalf("backoff allowed after 3 (max) retries")
91 }
92 if backoff.Backoff(ctx) {
93 t.Fatalf("backoff allowed after 3 (max) retries")
94 }
95}
96
97func TestGetBackoffDuration(t *testing.T) {
98 // make backoff return immediately
99 timeAfter = immediateTimeAfter
100 ctx := context.Background()
101 backoff := BackoffHandler{MaxRetries: 3}
102 if duration, ok := backoff.GetBackoffDuration(ctx); !ok || duration != time.Second {
103 t.Fatalf("backoff didn't return 1 second on first retry")
104 }
105 backoff.Backoff(ctx) // noop
106 if duration, ok := backoff.GetBackoffDuration(ctx); !ok || duration != time.Second*2 {
107 t.Fatalf("backoff didn't return 2 seconds on second retry")
108 }
109 backoff.Backoff(ctx) // noop
110 if duration, ok := backoff.GetBackoffDuration(ctx); !ok || duration != time.Second*4 {
111 t.Fatalf("backoff didn't return 4 seconds on third retry")
112 }
113 backoff.Backoff(ctx) // noop
114 if duration, ok := backoff.GetBackoffDuration(ctx); ok || duration != 0 {
115 t.Fatalf("backoff didn't return 0 seconds on fourth retry (exceeding limit)")
116 }
117}
118
119func TestBackoffRetryForever(t *testing.T) {
120 // make backoff return immediately
121 timeAfter = immediateTimeAfter
122 ctx := context.Background()
123 backoff := BackoffHandler{MaxRetries: 3, RetryForever: true}
124 if duration, ok := backoff.GetBackoffDuration(ctx); !ok || duration != time.Second {
125 t.Fatalf("backoff didn't return 1 second on first retry")
126 }
127 backoff.Backoff(ctx) // noop
128 if duration, ok := backoff.GetBackoffDuration(ctx); !ok || duration != time.Second*2 {
129 t.Fatalf("backoff didn't return 2 seconds on second retry")
130 }
131 backoff.Backoff(ctx) // noop
132 if duration, ok := backoff.GetBackoffDuration(ctx); !ok || duration != time.Second*4 {
133 t.Fatalf("backoff didn't return 4 seconds on third retry")
134 }
135 if !backoff.Backoff(ctx) {
136 t.Fatalf("backoff refused on fourth retry despire RetryForever")
137 }
138 if duration, ok := backoff.GetBackoffDuration(ctx); !ok || duration != time.Second*8 {
139 t.Fatalf("backoff returned %v instead of 8 seconds on fourth retry", duration)
140 }
141 if !backoff.Backoff(ctx) {
142 t.Fatalf("backoff refused on fifth retry despire RetryForever")
143 }
144 if duration, ok := backoff.GetBackoffDuration(ctx); !ok || duration != time.Second*8 {
145 t.Fatalf("backoff returned %v instead of 8 seconds on fifth retry", duration)
146 }
147}
148