Skip to content

Commit

Permalink
add mock header present/not present matchers
Browse files Browse the repository at this point in the history
  • Loading branch information
steinfletcher committed May 12, 2019
1 parent 5bf3a13 commit 80a1e22
Show file tree
Hide file tree
Showing 2 changed files with 138 additions and 21 deletions.
48 changes: 48 additions & 0 deletions mocks.go
Original file line number Diff line number Diff line change
Expand Up @@ -200,8 +200,11 @@ type MockRequest struct {
url *url.URL
method string
headers map[string][]string
headerPresent []string
headerNotPresent []string
query map[string][]string
queryPresent []string
queryNotPresent []string
cookie []Cookie
cookiePresent []string
cookieNotPresent []string
Expand Down Expand Up @@ -336,6 +339,16 @@ func (r *MockRequest) Headers(headers map[string]string) *MockRequest {
return r
}

func (r *MockRequest) HeaderPresent(key string) *MockRequest {
r.headerPresent = append(r.headerPresent, key)
return r
}

func (r *MockRequest) HeaderNotPresent(key string) *MockRequest {
r.headerNotPresent = append(r.headerNotPresent, key)
return r
}

func (r *MockRequest) Query(key, value string) *MockRequest {
r.query[key] = append(r.query[key], value)
return r
Expand All @@ -353,6 +366,11 @@ func (r *MockRequest) QueryPresent(key string) *MockRequest {
return r
}

func (r *MockRequest) QueryNotPresent(key string) *MockRequest {
r.queryNotPresent = append(r.queryNotPresent, key)
return r
}

func (r *MockRequest) Cookie(name, value string) *MockRequest {
r.cookie = append(r.cookie, Cookie{name: &name, value: &value})
return r
Expand Down Expand Up @@ -519,6 +537,24 @@ var headerMatcher = func(req *http.Request, spec *MockRequest) error {
return nil
}

var headerPresentMatcher = func(req *http.Request, spec *MockRequest) error {
for _, header := range spec.headerPresent {
if req.Header.Get(header) == "" {
return fmt.Errorf("expected header '%s' was not present", header)
}
}
return nil
}

var headerNotPresentMatcher = func(req *http.Request, spec *MockRequest) error {
for _, header := range spec.headerNotPresent {
if req.Header.Get(header) != "" {
return fmt.Errorf("unexpected header '%s' was present", header)
}
}
return nil
}

var queryParamMatcher = func(req *http.Request, spec *MockRequest) error {
mockQueryParams := spec.query
for key, values := range mockQueryParams {
Expand Down Expand Up @@ -556,6 +592,15 @@ var queryPresentMatcher = func(req *http.Request, spec *MockRequest) error {
return nil
}

var queryNotPresentMatcher = func(req *http.Request, spec *MockRequest) error {
for _, query := range spec.queryNotPresent {
if req.URL.Query().Get(query) != "" {
return fmt.Errorf("unexpected query param '%s' present", query)
}
}
return nil
}

var cookieMatcher = func(req *http.Request, spec *MockRequest) error {
for _, c := range spec.cookie {
foundCookie, _ := req.Cookie(*c.name)
Expand Down Expand Up @@ -651,8 +696,11 @@ var defaultMatchers = []Matcher{
schemeMatcher,
methodMatcher,
headerMatcher,
headerPresentMatcher,
headerNotPresentMatcher,
queryParamMatcher,
queryPresentMatcher,
queryNotPresentMatcher,
bodyMatcher,
cookieMatcher,
cookiePresentMatcher,
Expand Down
111 changes: 90 additions & 21 deletions mocks_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -15,27 +15,6 @@ import (
"github.com/stretchr/testify/assert"
)

func TestMocks_QueryPresent(t *testing.T) {
tests := []struct {
requestUrl string
queryParam string
expectedError error
}{
{"http://test.com/v1/path?a=1", "a", nil},
{"http://test.com/v1/path", "a", errors.New("expected query param a not received")},
{"http://test.com/v1/path?c=1", "b", errors.New("expected query param b not received")},
{"http://test.com/v2/path?b=2&a=1", "a", nil},
}
for _, test := range tests {
t.Run(test.requestUrl, func(t *testing.T) {
req := httptest.NewRequest(http.MethodGet, test.requestUrl, nil)
mockRequest := NewMock().Get(test.requestUrl).QueryPresent(test.queryParam)
matchError := queryPresentMatcher(req, mockRequest)
assert.Equal(t, test.expectedError, matchError)
})
}
}

func TestMocks_Cookie_Matches(t *testing.T) {
reqURL := "http://test.com/v1/path"
req := httptest.NewRequest(http.MethodGet, reqURL, nil)
Expand Down Expand Up @@ -213,6 +192,54 @@ func TestMocks_MockRequest_Header_WorksWithHeaders(t *testing.T) {
assert.Nil(t, matchError)
}

func TestMocks_HeaderPresentMatcher(t *testing.T) {
tests := map[string]struct {
requestHeaders map[string]string
headerPresent string
expectedError error
}{
"present": {map[string]string{"A": "123", "X": "456"}, "X", nil},
"not present": {map[string]string{"A": "123"}, "C", errors.New("expected header 'C' was not present")},
}
for name, test := range tests {
t.Run(name, func(t *testing.T) {
req := httptest.NewRequest(http.MethodGet, "/assert", nil)
for k, v := range test.requestHeaders {
req.Header.Add(k, v)
}
mockRequest := NewMock().Get("/assert").HeaderPresent(test.headerPresent)

matchError := headerPresentMatcher(req, mockRequest)

assert.Equal(t, test.expectedError, matchError)
})
}
}

func TestMocks_HeaderNotPresentMatcher(t *testing.T) {
tests := map[string]struct {
requestHeaders map[string]string
headerNotPresent string
expectedError error
}{
"not present": {map[string]string{"A": "123"}, "C", nil},
"present": {map[string]string{"A": "123", "X": "456"}, "X", errors.New("unexpected header 'X' was present")},
}
for name, test := range tests {
t.Run(name, func(t *testing.T) {
req := httptest.NewRequest(http.MethodGet, "/assert", nil)
for k, v := range test.requestHeaders {
req.Header.Add(k, v)
}
mockRequest := NewMock().Get("/assert").HeaderNotPresent(test.headerNotPresent)

matchError := headerNotPresentMatcher(req, mockRequest)

assert.Equal(t, test.expectedError, matchError)
})
}
}

func TestMocks_QueryMatcher(t *testing.T) {
tests := []struct {
requestUrl string
Expand Down Expand Up @@ -247,6 +274,48 @@ func TestMocks_QueryParams_DoesNotOverwriteQuery(t *testing.T) {
assert.Nil(t, matchError)
}

func TestMocks_QueryPresent(t *testing.T) {
tests := []struct {
requestUrl string
queryParam string
expectedError error
}{
{"http://test.com/v1/path?a=1", "a", nil},
{"http://test.com/v1/path", "a", errors.New("expected query param a not received")},
{"http://test.com/v1/path?c=1", "b", errors.New("expected query param b not received")},
{"http://test.com/v2/path?b=2&a=1", "a", nil},
}
for _, test := range tests {
t.Run(test.requestUrl, func(t *testing.T) {
req := httptest.NewRequest(http.MethodGet, test.requestUrl, nil)
mockRequest := NewMock().Get(test.requestUrl).QueryPresent(test.queryParam)
matchError := queryPresentMatcher(req, mockRequest)
assert.Equal(t, test.expectedError, matchError)
})
}
}

func TestMocks_QueryNotPresent(t *testing.T) {
tests := []struct {
queryString string
queryParam string
expectedError error
}{
{"http://test.com/v1/path?a=1", "a", errors.New("unexpected query param 'a' present")},
{"http://test.com/v1/path", "a", nil},
{"http://test.com/v1/path?c=1", "b", nil},
{"http://test.com/v2/path?b=2&a=1", "a", errors.New("unexpected query param 'a' present")},
}
for _, test := range tests {
t.Run(test.queryString, func(t *testing.T) {
req := httptest.NewRequest(http.MethodGet, test.queryString, nil)
mockRequest := NewMock().Get("http://test.com/v1/path" + test.queryString).QueryNotPresent(test.queryParam)
matchError := queryNotPresentMatcher(req, mockRequest)
assert.Equal(t, test.expectedError, matchError)
})
}
}

func TestMocks_SchemeMatcher(t *testing.T) {
tests := []struct {
requestUrl string
Expand Down

0 comments on commit 80a1e22

Please sign in to comment.