Created
May 18, 2020 05:52
-
-
Save rotemtam/f21e17e03f21468895fe59000fe5f8c5 to your computer and use it in GitHub Desktop.
Over DRY
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
package loader | |
import ( | |
"fmt" | |
"io/ioutil" | |
"net/http" | |
"net/http/httptest" | |
"testing" | |
) | |
type Requester func(t *testing.T, srv *httptest.Server) *http.Response | |
type Validator struct { | |
predicate func(r *http.Response) (bool, error) | |
errorMessage string | |
} | |
func (v Validator) Validate(t *testing.T, resp *http.Response) { | |
if valid, err := v.predicate(resp); err != nil { | |
t.Fatal(err) | |
} else if !valid { | |
t.Fatal(v.errorMessage) | |
} | |
} | |
func runWebserverTest(t *testing.T, request Requester, validators []Validator) { | |
srv := createTestWebserver() | |
defer srv.Close() | |
response := request(t, srv) | |
for _, validator := range validators { | |
validator.Validate(t, response) | |
} | |
} | |
func getRequester(path string) Requester { | |
return func(t *testing.T, srv *httptest.Server) *http.Response { | |
resp, err := http.Get(srv.URL + path) | |
if err != nil { | |
t.Fatal("failed calling test server") | |
return nil | |
} | |
return resp | |
} | |
} | |
func getBodyValidator(expectedBody string) Validator { | |
return Validator{ | |
predicate: func(r *http.Response) (bool, error) { | |
body, err := ioutil.ReadAll(r.Body) | |
if err != nil { | |
return false, err | |
} | |
fmt.Println(string(body)) | |
return string(body) == expectedBody, nil | |
}, | |
errorMessage: fmt.Sprintf("Expected body to be [%s]", expectedBody), | |
} | |
} | |
func getStatusCodeValidator(expectedStatus int) Validator { | |
return Validator{ | |
predicate: func(r *http.Response) (bool, error) { | |
return r.StatusCode == expectedStatus, nil | |
}, | |
errorMessage: fmt.Sprintf("Expected status to be [%d]", expectedStatus), | |
} | |
} | |
func getHeaderValidator(headerName string, expectedValue string) Validator { | |
return Validator{ | |
predicate: func(r *http.Response) (bool, error) { | |
return r.Header.Get(headerName) == expectedValue, nil | |
}, | |
errorMessage: fmt.Sprintf("Expected header [%s] to be [%s]", headerName, expectedValue), | |
} | |
} | |
func Test_DRY_bad_path_500(t *testing.T) { | |
runWebserverTest(t, | |
getRequester("/bad/path"), | |
[]Validator{ | |
getStatusCodeValidator(500), | |
getBodyValidator("500 internal server error: failed handling /bad/path"), | |
}) | |
} | |
func Test_DRY_unknown_path_404(t *testing.T) { | |
runWebserverTest(t, | |
getRequester("/unknown/path"), | |
[]Validator{ | |
getStatusCodeValidator(404), | |
getHeaderValidator("X-Sensitive-Header", ""), | |
}) | |
} | |
func TestWebserver_bad_path_500(t *testing.T) { | |
srv := createTestWebserver() | |
defer srv.Close() | |
resp, err := http.Get(srv.URL + "/bad/path") | |
if err != nil { | |
t.Fatal("failed calling test server") | |
} | |
if resp.StatusCode != 500 { | |
t.Fatalf("expected response code to be 500") | |
} | |
body, err := ioutil.ReadAll(resp.Body) | |
if err != nil { | |
t.Fatal("failed reading body bytes") | |
} | |
if string(body) != "500 internal server error: failed handling /bad/path" { | |
t.Fatalf("body does not match expected") | |
} | |
} | |
func TestWebserver_unknown_path_404(t *testing.T) { | |
srv := createTestWebserver() | |
defer srv.Close() | |
resp, err := http.Get(srv.URL + "/unknown/path") | |
if err != nil { | |
t.Fatal("failed calling test server") | |
} | |
if resp.StatusCode != 404 { | |
t.Fatalf("expected response code to be 400") | |
} | |
if resp.Header.Get("X-Sensitive-Header") != "" { | |
t.Fatalf("expecting sensitive header not to be sent") | |
} | |
} | |
func createTestWebserver() *httptest.Server { | |
mux := http.NewServeMux() | |
mux.HandleFunc("/bad/path", func(writer http.ResponseWriter, request *http.Request) { | |
writer.WriteHeader(500) | |
body := fmt.Sprintf("500 internal server error: failed handling %s", request.URL.Path) | |
_, _ = writer.Write([]byte(body)) | |
}) | |
return httptest.NewServer(mux) | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment