diff --git a/CHANGELOG.md b/CHANGELOG.md index da2b6b6..ae2b0c9 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -9,7 +9,9 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0 ### Added -### Changed +## [1.4.0] - 2024-05-09 + +- Support retry after as a date. ## [1.3.3] - 2024-03-19 diff --git a/retry_handler.go b/retry_handler.go index aa9faf4..141a8c0 100644 --- a/retry_handler.go +++ b/retry_handler.go @@ -184,6 +184,12 @@ func (middleware RetryHandler) getRetryDelay(req *nethttp.Request, resp *nethttp if err == nil { return time.Duration(retryAfterDelay) * time.Second } - } //TODO parse the header if it's a date + + // parse the header if it's a date + t, err := time.Parse(time.RFC1123, retryAfter) + if err == nil { + return t.Sub(time.Now()) + } + } return time.Duration(math.Pow(float64(options.GetDelaySeconds()), float64(executionCount))) * time.Second } diff --git a/retry_handler_test.go b/retry_handler_test.go index d76bc12..0ff8746 100644 --- a/retry_handler_test.go +++ b/retry_handler_test.go @@ -106,6 +106,34 @@ func TestItHonoursMaxRetries(t *testing.T) { assert.Equal(t, defaultMaxRetries, retryAttemptInt) } +func TestItHonoursRetryAfterDate(t *testing.T) { + retryAttemptInt := -1 + start := time.Now() + retryAfterTimeStr := start.Add(4 * time.Second).Format(time.RFC1123) + testServer := httptest.NewServer(nethttp.HandlerFunc(func(res nethttp.ResponseWriter, req *nethttp.Request) { + res.Header().Set("Retry-After", retryAfterTimeStr) + res.WriteHeader(429) + retryAttemptInt++ + res.Write([]byte("body")) + })) + + defer func() { testServer.Close() }() + handler := NewRetryHandler() + req, err := nethttp.NewRequest(nethttp.MethodGet, testServer.URL, nil) + if err != nil { + t.Error(err) + } + resp, err := handler.Intercept(newNoopPipeline(), 0, req) + if err != nil { + t.Error(err) + } + assert.NotNil(t, resp) + end := time.Now() + + assert.Equal(t, defaultMaxRetries, retryAttemptInt) + assert.Greater(t, end.Sub(start), 3*time.Second) // delay should be greater than 3 seconds (ignoring microsecond differences) +} + func TestItHonoursContextExpiry(t *testing.T) { retryAttemptInt := -1 testServer := httptest.NewServer(nethttp.HandlerFunc(func(res nethttp.ResponseWriter, req *nethttp.Request) {