@@ -199,55 +199,67 @@ func TestThrottleMaximum(t *testing.T) {
199199wg .Wait ()
200200}
201201
202- // NOTE: test is disabled as it requires some refactoring. It is prone to intermittent failure.
203- /*func TestThrottleRetryAfter(t *testing.T) {
202+ func TestThrottleRetryAfter (t * testing.T ) {
204203r := chi .NewRouter ()
204+ retryAfterFn := func (ctxDone bool ) time.Duration { return time .Hour }
205205
206- retryAfterFn := func(ctxDone bool) time.Duration { return time.Hour * 1 }
207- r.Use(ThrottleWithOpts(ThrottleOpts{Limit: 10, RetryAfterFn: retryAfterFn}))
206+ r .Use (ThrottleWithOpts (ThrottleOpts {
207+ Limit : 5 ,
208+ BacklogLimit : 0 ,
209+ RetryAfterFn : retryAfterFn ,
210+ }))
208211
209212r .Get ("/" , func (w http.ResponseWriter , r * http.Request ) {
213+ time .Sleep (time .Second * 1 ) // Expensive operation.
210214w .WriteHeader (http .StatusOK )
211- time.Sleep(time.Second * 4) // Expensive operation.
212- w.Write(testContent)
215+ w .Write ([]byte ("ok" ))
213216})
214217
215218server := httptest .NewServer (r )
216219defer server .Close ()
220+ client := http.Client {}
217221
218- client := http.Client{
219- Timeout: time.Second * 60, // Maximum waiting time.
222+ type result struct {
223+ status int
224+ header http.Header
220225}
221226
222227var wg sync.WaitGroup
228+ totalRequests := 10
229+ resultsCh := make (chan result , totalRequests )
223230
224- for i := 0; i < 10 ; i++ {
231+ for i := 0 ; i < totalRequests ; i ++ {
225232wg .Add (1 )
226- go func(i int ) {
233+ go func () {
227234defer wg .Done ()
228-
229- res, err := client.Get(server.URL)
230- assertNoError(t, err)
231- assertEqual(t, http.StatusOK, res.StatusCode)
232- }(i)
235+ res , _ := client .Get (server .URL )
236+ resultsCh <- result {status : res .StatusCode , header : res .Header }
237+ }()
233238}
234239
235- time.Sleep(time.Second * 1)
236-
237- for i := 0; i < 10; i++ {
238- wg.Add(1)
239- go func(i int) {
240- defer wg.Done()
241-
242- res, err := client.Get(server.URL)
243- assertNoError(t, err)
244- assertEqual(t, http.StatusTooManyRequests, res.StatusCode)
245- assertEqual(t, res.Header.Get("Retry-After"), "3600")
246- }(i)
240+ wg .Wait ()
241+ close (resultsCh )
242+
243+ count200 := 0
244+ count429 := 0
245+ for res := range resultsCh {
246+ switch res .status {
247+ case http .StatusOK :
248+ count200 ++
249+ continue
250+ case http .StatusTooManyRequests :
251+ count429 ++
252+ assertEqual (t , "3600" , res .header .Get ("Retry-After" ))
253+ continue
254+ default :
255+ t .Fatalf ("Unexpected status code: %d" , res .status )
256+ continue
257+ }
247258}
248259
249- wg.Wait()
250- }*/
260+ assertEqual (t , 5 , count200 )
261+ assertEqual (t , 5 , count429 )
262+ }
251263
252264func TestThrottleCustomStatusCode (t * testing.T ) {
253265const timeout = time .Second * 3
0 commit comments