Merge pull request #16104 from vdemeester/httputils-withmock
Update httputils tests
This commit is contained in:
commit
6231b0f8eb
2 changed files with 273 additions and 9 deletions
|
@ -1,25 +1,65 @@
|
||||||
package httputils
|
package httputils
|
||||||
|
|
||||||
import "testing"
|
import (
|
||||||
|
"fmt"
|
||||||
|
"io/ioutil"
|
||||||
|
"net/http"
|
||||||
|
"net/http/httptest"
|
||||||
|
"strings"
|
||||||
|
"testing"
|
||||||
|
)
|
||||||
|
|
||||||
func TestDownload(t *testing.T) {
|
func TestDownload(t *testing.T) {
|
||||||
_, err := Download("http://docker.com")
|
expected := "Hello, docker !"
|
||||||
|
ts := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
|
||||||
|
fmt.Fprintf(w, expected)
|
||||||
|
}))
|
||||||
|
defer ts.Close()
|
||||||
|
response, err := Download(ts.URL)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
t.Fatalf("Expected error to not exist when Download(http://docker.com)")
|
t.Fatal(err)
|
||||||
}
|
}
|
||||||
|
|
||||||
// Expected status code = 404
|
actual, err := ioutil.ReadAll(response.Body)
|
||||||
if _, err = Download("http://docker.com/abc1234567"); err == nil {
|
response.Body.Close()
|
||||||
t.Fatalf("Expected error to exist when Download(http://docker.com/abc1234567)")
|
|
||||||
|
if err != nil || string(actual) != expected {
|
||||||
|
t.Fatalf("Expected the response %q, got err:%v, response:%v, actual:%s", expected, err, response, string(actual))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestDownload400Errors(t *testing.T) {
|
||||||
|
expectedError := "Got HTTP status code >= 400: 403 Forbidden"
|
||||||
|
ts := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
|
||||||
|
// 403
|
||||||
|
http.Error(w, "something failed (forbidden)", http.StatusForbidden)
|
||||||
|
}))
|
||||||
|
defer ts.Close()
|
||||||
|
// Expected status code = 403
|
||||||
|
if _, err := Download(ts.URL); err == nil || err.Error() != expectedError {
|
||||||
|
t.Fatalf("Expected the the error %q, got %v", expectedError, err)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestDownloadOtherErrors(t *testing.T) {
|
||||||
|
if _, err := Download("I'm not an url.."); err == nil || !strings.Contains(err.Error(), "unsupported protocol scheme") {
|
||||||
|
t.Fatalf("Expected an error with 'unsupported protocol scheme', got %v", err)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func TestNewHTTPRequestError(t *testing.T) {
|
func TestNewHTTPRequestError(t *testing.T) {
|
||||||
errorMessage := "Some error message"
|
errorMessage := "Some error message"
|
||||||
httpResponse, _ := Download("http://docker.com")
|
ts := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
|
||||||
|
// 403
|
||||||
|
http.Error(w, errorMessage, http.StatusForbidden)
|
||||||
|
}))
|
||||||
|
defer ts.Close()
|
||||||
|
httpResponse, err := http.Get(ts.URL)
|
||||||
|
if err != nil {
|
||||||
|
t.Fatal(err)
|
||||||
|
}
|
||||||
if err := NewHTTPRequestError(errorMessage, httpResponse); err.Error() != errorMessage {
|
if err := NewHTTPRequestError(errorMessage, httpResponse); err.Error() != errorMessage {
|
||||||
t.Fatalf("Expected err to equal error Message")
|
t.Fatalf("Expected err to be %q, got %v", errorMessage, err)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -2,6 +2,7 @@ package httputils
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"fmt"
|
"fmt"
|
||||||
|
"io"
|
||||||
"io/ioutil"
|
"io/ioutil"
|
||||||
"net/http"
|
"net/http"
|
||||||
"net/http/httptest"
|
"net/http/httptest"
|
||||||
|
@ -9,6 +10,229 @@ import (
|
||||||
"testing"
|
"testing"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
func TestResumableRequestHeaderSimpleErrors(t *testing.T) {
|
||||||
|
ts := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
|
||||||
|
fmt.Fprintln(w, "Hello, world !")
|
||||||
|
}))
|
||||||
|
defer ts.Close()
|
||||||
|
|
||||||
|
client := &http.Client{}
|
||||||
|
|
||||||
|
var req *http.Request
|
||||||
|
req, err := http.NewRequest("GET", ts.URL, nil)
|
||||||
|
if err != nil {
|
||||||
|
t.Fatal(err)
|
||||||
|
}
|
||||||
|
|
||||||
|
expectedError := "client and request can't be nil\n"
|
||||||
|
resreq := &resumableRequestReader{}
|
||||||
|
_, err = resreq.Read([]byte{})
|
||||||
|
if err == nil || err.Error() != expectedError {
|
||||||
|
t.Fatalf("Expected an error with '%s', got %v.", expectedError, err)
|
||||||
|
}
|
||||||
|
|
||||||
|
resreq = &resumableRequestReader{
|
||||||
|
client: client,
|
||||||
|
request: req,
|
||||||
|
totalSize: -1,
|
||||||
|
}
|
||||||
|
expectedError = "failed to auto detect content length"
|
||||||
|
_, err = resreq.Read([]byte{})
|
||||||
|
if err == nil || err.Error() != expectedError {
|
||||||
|
t.Fatalf("Expected an error with '%s', got %v.", expectedError, err)
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
// Not too much failures, bails out after some wait
|
||||||
|
func TestResumableRequestHeaderNotTooMuchFailures(t *testing.T) {
|
||||||
|
client := &http.Client{}
|
||||||
|
|
||||||
|
var badReq *http.Request
|
||||||
|
badReq, err := http.NewRequest("GET", "I'm not an url", nil)
|
||||||
|
if err != nil {
|
||||||
|
t.Fatal(err)
|
||||||
|
}
|
||||||
|
|
||||||
|
resreq := &resumableRequestReader{
|
||||||
|
client: client,
|
||||||
|
request: badReq,
|
||||||
|
failures: 0,
|
||||||
|
maxFailures: 2,
|
||||||
|
}
|
||||||
|
read, err := resreq.Read([]byte{})
|
||||||
|
if err != nil || read != 0 {
|
||||||
|
t.Fatalf("Expected no error and no byte read, got err:%v, read:%v.", err, read)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Too much failures, returns the error
|
||||||
|
func TestResumableRequestHeaderTooMuchFailures(t *testing.T) {
|
||||||
|
client := &http.Client{}
|
||||||
|
|
||||||
|
var badReq *http.Request
|
||||||
|
badReq, err := http.NewRequest("GET", "I'm not an url", nil)
|
||||||
|
if err != nil {
|
||||||
|
t.Fatal(err)
|
||||||
|
}
|
||||||
|
|
||||||
|
resreq := &resumableRequestReader{
|
||||||
|
client: client,
|
||||||
|
request: badReq,
|
||||||
|
failures: 0,
|
||||||
|
maxFailures: 1,
|
||||||
|
}
|
||||||
|
defer resreq.Close()
|
||||||
|
|
||||||
|
expectedError := `Get I%27m%20not%20an%20url: unsupported protocol scheme ""`
|
||||||
|
read, err := resreq.Read([]byte{})
|
||||||
|
if err == nil || err.Error() != expectedError || read != 0 {
|
||||||
|
t.Fatalf("Expected the error '%s', got err:%v, read:%v.", expectedError, err, read)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
type errorReaderCloser struct{}
|
||||||
|
|
||||||
|
func (errorReaderCloser) Close() error { return nil }
|
||||||
|
|
||||||
|
func (errorReaderCloser) Read(p []byte) (n int, err error) {
|
||||||
|
return 0, fmt.Errorf("A error occured")
|
||||||
|
}
|
||||||
|
|
||||||
|
// If a an unknown error is encountered, return 0, nil and log it
|
||||||
|
func TestResumableRequestReaderWithReadError(t *testing.T) {
|
||||||
|
var req *http.Request
|
||||||
|
req, err := http.NewRequest("GET", "", nil)
|
||||||
|
if err != nil {
|
||||||
|
t.Fatal(err)
|
||||||
|
}
|
||||||
|
|
||||||
|
client := &http.Client{}
|
||||||
|
|
||||||
|
response := &http.Response{
|
||||||
|
Status: "500 Internal Server",
|
||||||
|
StatusCode: 500,
|
||||||
|
ContentLength: 0,
|
||||||
|
Close: true,
|
||||||
|
Body: errorReaderCloser{},
|
||||||
|
}
|
||||||
|
|
||||||
|
resreq := &resumableRequestReader{
|
||||||
|
client: client,
|
||||||
|
request: req,
|
||||||
|
currentResponse: response,
|
||||||
|
lastRange: 1,
|
||||||
|
totalSize: 1,
|
||||||
|
}
|
||||||
|
defer resreq.Close()
|
||||||
|
|
||||||
|
buf := make([]byte, 1)
|
||||||
|
read, err := resreq.Read(buf)
|
||||||
|
if err != nil {
|
||||||
|
t.Fatal(err)
|
||||||
|
}
|
||||||
|
|
||||||
|
if read != 0 {
|
||||||
|
t.Fatalf("Expected to have read nothing, but read %v", read)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestResumableRequestReaderWithEOFWith416Response(t *testing.T) {
|
||||||
|
var req *http.Request
|
||||||
|
req, err := http.NewRequest("GET", "", nil)
|
||||||
|
if err != nil {
|
||||||
|
t.Fatal(err)
|
||||||
|
}
|
||||||
|
|
||||||
|
client := &http.Client{}
|
||||||
|
|
||||||
|
response := &http.Response{
|
||||||
|
Status: "416 Requested Range Not Satisfiable",
|
||||||
|
StatusCode: 416,
|
||||||
|
ContentLength: 0,
|
||||||
|
Close: true,
|
||||||
|
Body: ioutil.NopCloser(strings.NewReader("")),
|
||||||
|
}
|
||||||
|
|
||||||
|
resreq := &resumableRequestReader{
|
||||||
|
client: client,
|
||||||
|
request: req,
|
||||||
|
currentResponse: response,
|
||||||
|
lastRange: 1,
|
||||||
|
totalSize: 1,
|
||||||
|
}
|
||||||
|
defer resreq.Close()
|
||||||
|
|
||||||
|
buf := make([]byte, 1)
|
||||||
|
_, err = resreq.Read(buf)
|
||||||
|
if err == nil || err != io.EOF {
|
||||||
|
t.Fatalf("Expected an io.EOF error, got %v", err)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestResumableRequestReaderWithServerDoesntSupportByteRanges(t *testing.T) {
|
||||||
|
ts := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
|
||||||
|
if r.Header.Get("Range") == "" {
|
||||||
|
t.Fatalf("Expected a Range HTTP header, got nothing")
|
||||||
|
}
|
||||||
|
}))
|
||||||
|
defer ts.Close()
|
||||||
|
|
||||||
|
var req *http.Request
|
||||||
|
req, err := http.NewRequest("GET", ts.URL, nil)
|
||||||
|
if err != nil {
|
||||||
|
t.Fatal(err)
|
||||||
|
}
|
||||||
|
|
||||||
|
client := &http.Client{}
|
||||||
|
|
||||||
|
resreq := &resumableRequestReader{
|
||||||
|
client: client,
|
||||||
|
request: req,
|
||||||
|
lastRange: 1,
|
||||||
|
}
|
||||||
|
defer resreq.Close()
|
||||||
|
|
||||||
|
buf := make([]byte, 2)
|
||||||
|
_, err = resreq.Read(buf)
|
||||||
|
if err == nil || err.Error() != "the server doesn't support byte ranges" {
|
||||||
|
t.Fatalf("Expected an error 'the server doesn't support byte ranges', got %v", err)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestResumableRequestReaderWithZeroTotalSize(t *testing.T) {
|
||||||
|
|
||||||
|
srvtxt := "some response text data"
|
||||||
|
|
||||||
|
ts := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
|
||||||
|
fmt.Fprintln(w, srvtxt)
|
||||||
|
}))
|
||||||
|
defer ts.Close()
|
||||||
|
|
||||||
|
var req *http.Request
|
||||||
|
req, err := http.NewRequest("GET", ts.URL, nil)
|
||||||
|
if err != nil {
|
||||||
|
t.Fatal(err)
|
||||||
|
}
|
||||||
|
|
||||||
|
client := &http.Client{}
|
||||||
|
retries := uint32(5)
|
||||||
|
|
||||||
|
resreq := ResumableRequestReader(client, req, retries, 0)
|
||||||
|
defer resreq.Close()
|
||||||
|
|
||||||
|
data, err := ioutil.ReadAll(resreq)
|
||||||
|
if err != nil {
|
||||||
|
t.Fatal(err)
|
||||||
|
}
|
||||||
|
|
||||||
|
resstr := strings.TrimSuffix(string(data), "\n")
|
||||||
|
|
||||||
|
if resstr != srvtxt {
|
||||||
|
t.Errorf("resstr != srvtxt")
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
func TestResumableRequestReader(t *testing.T) {
|
func TestResumableRequestReader(t *testing.T) {
|
||||||
|
|
||||||
srvtxt := "some response text data"
|
srvtxt := "some response text data"
|
||||||
|
|
Loading…
Reference in a new issue