Skip to content

Commit ddae56a

Browse files
committed
Retry on EOF errors
The retry mechanism should be active when the server closes the connection unexpectedly, eg. when an Elasticsearch node is restarting, or the underlying connection gets stale. Fixes #111 (cherry picked from commit cb4ea94)
1 parent 3e59300 commit ddae56a

File tree

2 files changed

+46
-1
lines changed

2 files changed

+46
-1
lines changed

estransport/estransport.go

+6-1
Original file line numberDiff line numberDiff line change
@@ -254,7 +254,12 @@ func (c *Client) Perform(req *http.Request) (*http.Response, error) {
254254
c.pool.OnFailure(conn)
255255
c.Unlock()
256256

257-
// Retry only on network errors, but don't retry on timeout errors, unless configured
257+
// Retry on EOF errors
258+
if err == io.EOF {
259+
shouldRetry = true
260+
}
261+
262+
// Retry on network errors, but not on timeout errors, unless configured
258263
if err, ok := err.(net.Error); ok {
259264
if (!err.Timeout() || c.enableRetryOnTimeout) && !c.disableRetry {
260265
shouldRetry = true

estransport/estransport_internal_test.go

+40
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,7 @@ package estransport
88

99
import (
1010
"fmt"
11+
"io"
1112
"io/ioutil"
1213
"math/rand"
1314
"net/http"
@@ -393,6 +394,45 @@ func TestTransportPerformRetries(t *testing.T) {
393394
}
394395
})
395396

397+
t.Run("Retry request on EOF error and return the response", func(t *testing.T) {
398+
var (
399+
i int
400+
numReqs = 2
401+
)
402+
403+
u, _ := url.Parse("http://foo.bar")
404+
tp := New(Config{
405+
URLs: []*url.URL{u, u, u},
406+
Transport: &mockTransp{
407+
RoundTripFunc: func(req *http.Request) (*http.Response, error) {
408+
i++
409+
fmt.Printf("Request #%d", i)
410+
if i == numReqs {
411+
fmt.Print(": OK\n")
412+
return &http.Response{Status: "OK"}, nil
413+
}
414+
fmt.Print(": ERR\n")
415+
return nil, io.EOF
416+
},
417+
}})
418+
419+
req, _ := http.NewRequest("GET", "/abc", nil)
420+
421+
res, err := tp.Perform(req)
422+
423+
if err != nil {
424+
t.Fatalf("Unexpected error: %s", err)
425+
}
426+
427+
if res.Status != "OK" {
428+
t.Errorf("Unexpected response: %+v", res)
429+
}
430+
431+
if i != numReqs {
432+
t.Errorf("Unexpected number of requests, want=%d, got=%d", numReqs, i)
433+
}
434+
})
435+
396436
t.Run("Retry request on 5xx response and return new response", func(t *testing.T) {
397437
var (
398438
i int

0 commit comments

Comments
 (0)