From 1078828482c92f4d9b9051a1c46576e8c9fe546c Mon Sep 17 00:00:00 2001
From: Mark Bates <mark@markbates.com>
Date: Thu, 23 Aug 2018 13:33:39 -0400
Subject: [PATCH] moved from markbates/willie to gobuffalo/httptest

---
 Dockerfile.build                       |   2 +-
 Dockerfile.slim.build                  |   2 +-
 SHOULDERS.md                           | 124 ++++++++++++++++++++++++-
 default_context_test.go                |  25 +++--
 errors_test.go                         |   7 +-
 flash_test.go                          |  22 ++---
 go.mod                                 |  14 +--
 go.sum                                 |  47 +++-------
 method_override_test.go                |   6 +-
 middleware/basicauth/basicauth_test.go |  14 +--
 middleware/content_type_test.go        |  14 +--
 middleware/csrf/csrf_test.go           |  24 ++---
 middleware/i18n/i18n_test.go           |  50 +++++-----
 middleware/param_logger_test.go        |   4 +-
 middleware/tokenauth/tokenauth_test.go |  26 +++---
 middleware_test.go                     |  24 ++---
 not_found_test.go                      |  12 +--
 render/auto_test.go                    |  33 ++++---
 route_info_test.go                     |   4 +-
 router_test.go                         |  37 ++++----
 wrappers_test.go                       |  11 +--
 21 files changed, 296 insertions(+), 206 deletions(-)

diff --git a/Dockerfile.build b/Dockerfile.build
index ab9720687..442cb250d 100644
--- a/Dockerfile.build
+++ b/Dockerfile.build
@@ -22,7 +22,7 @@ RUN go get -u github.com/golang/dep/cmd/dep \
 && go get -v -u github.com/markbates/grift \
 && go get -v -u github.com/markbates/inflect \
 && go get -v -u github.com/markbates/refresh \
-&& go get -v -u github.com/markbates/willie \
+&& go get -v -u github.com/gobuffalo/httptest \
 && go get -v -u github.com/gorilla/sessions \
 && go get -v -u golang.org/x/vgo \
 && go get -u github.com/alecthomas/gometalinter \
diff --git a/Dockerfile.slim.build b/Dockerfile.slim.build
index 9db682a34..38bb7a70b 100644
--- a/Dockerfile.slim.build
+++ b/Dockerfile.slim.build
@@ -18,7 +18,7 @@ RUN go get -u github.com/golang/dep/cmd/dep \
 && go get -v -u github.com/markbates/grift \
 && go get -v -u github.com/markbates/inflect \
 && go get -v -u github.com/markbates/refresh \
-&& go get -v -u github.com/markbates/willie \
+&& go get -v -u github.com/gobuffalo/httptest \
 && go get -v -u github.com/gorilla/sessions \
 && go get -v -u golang.org/x/vgo \
 && go get -u github.com/alecthomas/gometalinter \
diff --git a/SHOULDERS.md b/SHOULDERS.md
index f2c3b1512..763ba9860 100644
--- a/SHOULDERS.md
+++ b/SHOULDERS.md
@@ -1,6 +1,6 @@
 # `github.com/gobuffalo/buffalo` Stands on the Shoulders of Giants
 
-`github.com/gobuffalo/buffalo` does not try to reinvent the wheel! Instead, it uses the already great wheels developed by the Go community and puts them altogether in the best way possible. Without these giants this project would not be possible. Please make sure to check them out and thank them for all of their hard work.
+`github.com/gobuffalo/buffalo` does not try to reinvent the wheel! Instead, it uses the already great wheels developed by the Go community and puts them all together in the best way possible. Without these giants this project would not be possible. Please make sure to check them out and thank them for all of their hard work.
 
 Thank you to the following **GIANTS**:
 
@@ -39,6 +39,8 @@ Thank you to the following **GIANTS**:
 
 * [github.com/gobuffalo/github_flavored_markdown](https://godoc.org/github.com/gobuffalo/github_flavored_markdown)
 
+* [github.com/gobuffalo/httptest](https://godoc.org/github.com/gobuffalo/httptest)
+
 * [github.com/gobuffalo/makr](https://godoc.org/github.com/gobuffalo/makr)
 
 * [github.com/gobuffalo/mw-contenttype](https://godoc.org/github.com/gobuffalo/mw-contenttype)
@@ -47,8 +49,6 @@ Thank you to the following **GIANTS**:
 
 * [github.com/gobuffalo/mw-paramlogger](https://godoc.org/github.com/gobuffalo/mw-paramlogger)
 
-* [github.com/gobuffalo/mw-poptx](https://godoc.org/github.com/gobuffalo/mw-poptx)
-
 * [github.com/gobuffalo/mw-tokenauth](https://godoc.org/github.com/gobuffalo/mw-tokenauth)
 
 * [github.com/gobuffalo/packr](https://godoc.org/github.com/gobuffalo/packr)
@@ -95,8 +95,12 @@ Thank you to the following **GIANTS**:
 
 * [github.com/gobuffalo/validate/validators](https://godoc.org/github.com/gobuffalo/validate/validators)
 
+* [github.com/gobuffalo/x/defaults](https://godoc.org/github.com/gobuffalo/x/defaults)
+
 * [github.com/gobuffalo/x/httpx](https://godoc.org/github.com/gobuffalo/x/httpx)
 
+* [github.com/gobuffalo/x/randx](https://godoc.org/github.com/gobuffalo/x/randx)
+
 * [github.com/gorilla/context](https://godoc.org/github.com/gorilla/context)
 
 * [github.com/gorilla/mux](https://godoc.org/github.com/gorilla/mux)
@@ -127,6 +131,18 @@ Thank you to the following **GIANTS**:
 
 * [github.com/hashicorp/hcl/json/token](https://godoc.org/github.com/hashicorp/hcl/json/token)
 
+* [github.com/hpcloud/tail](https://godoc.org/github.com/hpcloud/tail)
+
+* [github.com/hpcloud/tail/ratelimiter](https://godoc.org/github.com/hpcloud/tail/ratelimiter)
+
+* [github.com/hpcloud/tail/util](https://godoc.org/github.com/hpcloud/tail/util)
+
+* [github.com/hpcloud/tail/vendor/gopkg.in/fsnotify/fsnotify.v1](https://godoc.org/github.com/hpcloud/tail/vendor/gopkg.in/fsnotify/fsnotify.v1)
+
+* [github.com/hpcloud/tail/vendor/gopkg.in/tomb.v1](https://godoc.org/github.com/hpcloud/tail/vendor/gopkg.in/tomb.v1)
+
+* [github.com/hpcloud/tail/watch](https://godoc.org/github.com/hpcloud/tail/watch)
+
 * [github.com/jmoiron/sqlx](https://godoc.org/github.com/jmoiron/sqlx)
 
 * [github.com/jmoiron/sqlx/reflectx](https://godoc.org/github.com/jmoiron/sqlx/reflectx)
@@ -135,6 +151,8 @@ Thank you to the following **GIANTS**:
 
 * [github.com/kr/pretty](https://godoc.org/github.com/kr/pretty)
 
+* [github.com/kr/text](https://godoc.org/github.com/kr/text)
+
 * [github.com/lib/pq](https://godoc.org/github.com/lib/pq)
 
 * [github.com/lib/pq/oid](https://godoc.org/github.com/lib/pq/oid)
@@ -149,8 +167,6 @@ Thank you to the following **GIANTS**:
 
 * [github.com/markbates/going/randx](https://godoc.org/github.com/markbates/going/randx)
 
-* [github.com/markbates/going/wait](https://godoc.org/github.com/markbates/going/wait)
-
 * [github.com/markbates/grift/cmd](https://godoc.org/github.com/markbates/grift/cmd)
 
 * [github.com/markbates/grift/grift](https://godoc.org/github.com/markbates/grift/grift)
@@ -187,8 +203,62 @@ Thank you to the following **GIANTS**:
 
 * [github.com/onsi/ginkgo](https://godoc.org/github.com/onsi/ginkgo)
 
+* [github.com/onsi/ginkgo/config](https://godoc.org/github.com/onsi/ginkgo/config)
+
+* [github.com/onsi/ginkgo/internal/codelocation](https://godoc.org/github.com/onsi/ginkgo/internal/codelocation)
+
+* [github.com/onsi/ginkgo/internal/containernode](https://godoc.org/github.com/onsi/ginkgo/internal/containernode)
+
+* [github.com/onsi/ginkgo/internal/failer](https://godoc.org/github.com/onsi/ginkgo/internal/failer)
+
+* [github.com/onsi/ginkgo/internal/leafnodes](https://godoc.org/github.com/onsi/ginkgo/internal/leafnodes)
+
+* [github.com/onsi/ginkgo/internal/remote](https://godoc.org/github.com/onsi/ginkgo/internal/remote)
+
+* [github.com/onsi/ginkgo/internal/spec](https://godoc.org/github.com/onsi/ginkgo/internal/spec)
+
+* [github.com/onsi/ginkgo/internal/spec_iterator](https://godoc.org/github.com/onsi/ginkgo/internal/spec_iterator)
+
+* [github.com/onsi/ginkgo/internal/specrunner](https://godoc.org/github.com/onsi/ginkgo/internal/specrunner)
+
+* [github.com/onsi/ginkgo/internal/suite](https://godoc.org/github.com/onsi/ginkgo/internal/suite)
+
+* [github.com/onsi/ginkgo/internal/testingtproxy](https://godoc.org/github.com/onsi/ginkgo/internal/testingtproxy)
+
+* [github.com/onsi/ginkgo/internal/writer](https://godoc.org/github.com/onsi/ginkgo/internal/writer)
+
+* [github.com/onsi/ginkgo/reporters](https://godoc.org/github.com/onsi/ginkgo/reporters)
+
+* [github.com/onsi/ginkgo/reporters/stenographer](https://godoc.org/github.com/onsi/ginkgo/reporters/stenographer)
+
+* [github.com/onsi/ginkgo/reporters/stenographer/support/go-colorable](https://godoc.org/github.com/onsi/ginkgo/reporters/stenographer/support/go-colorable)
+
+* [github.com/onsi/ginkgo/types](https://godoc.org/github.com/onsi/ginkgo/types)
+
 * [github.com/onsi/gomega](https://godoc.org/github.com/onsi/gomega)
 
+* [github.com/onsi/gomega/format](https://godoc.org/github.com/onsi/gomega/format)
+
+* [github.com/onsi/gomega/internal/assertion](https://godoc.org/github.com/onsi/gomega/internal/assertion)
+
+* [github.com/onsi/gomega/internal/asyncassertion](https://godoc.org/github.com/onsi/gomega/internal/asyncassertion)
+
+* [github.com/onsi/gomega/internal/oraclematcher](https://godoc.org/github.com/onsi/gomega/internal/oraclematcher)
+
+* [github.com/onsi/gomega/internal/testingtsupport](https://godoc.org/github.com/onsi/gomega/internal/testingtsupport)
+
+* [github.com/onsi/gomega/matchers](https://godoc.org/github.com/onsi/gomega/matchers)
+
+* [github.com/onsi/gomega/matchers/support/goraph/bipartitegraph](https://godoc.org/github.com/onsi/gomega/matchers/support/goraph/bipartitegraph)
+
+* [github.com/onsi/gomega/matchers/support/goraph/edge](https://godoc.org/github.com/onsi/gomega/matchers/support/goraph/edge)
+
+* [github.com/onsi/gomega/matchers/support/goraph/node](https://godoc.org/github.com/onsi/gomega/matchers/support/goraph/node)
+
+* [github.com/onsi/gomega/matchers/support/goraph/util](https://godoc.org/github.com/onsi/gomega/matchers/support/goraph/util)
+
+* [github.com/onsi/gomega/types](https://godoc.org/github.com/onsi/gomega/types)
+
 * [github.com/pelletier/go-toml](https://godoc.org/github.com/pelletier/go-toml)
 
 * [github.com/pkg/errors](https://godoc.org/github.com/pkg/errors)
@@ -247,20 +317,64 @@ Thank you to the following **GIANTS**:
 
 * [golang.org/x/net/html/atom](https://godoc.org/golang.org/x/net/html/atom)
 
+* [golang.org/x/net/html/charset](https://godoc.org/golang.org/x/net/html/charset)
+
 * [golang.org/x/sync/errgroup](https://godoc.org/golang.org/x/sync/errgroup)
 
 * [golang.org/x/sys/unix](https://godoc.org/golang.org/x/sys/unix)
 
+* [golang.org/x/text/cases](https://godoc.org/golang.org/x/text/cases)
+
+* [golang.org/x/text/encoding](https://godoc.org/golang.org/x/text/encoding)
+
+* [golang.org/x/text/encoding/charmap](https://godoc.org/golang.org/x/text/encoding/charmap)
+
+* [golang.org/x/text/encoding/htmlindex](https://godoc.org/golang.org/x/text/encoding/htmlindex)
+
+* [golang.org/x/text/encoding/internal](https://godoc.org/golang.org/x/text/encoding/internal)
+
+* [golang.org/x/text/encoding/internal/enctest](https://godoc.org/golang.org/x/text/encoding/internal/enctest)
+
+* [golang.org/x/text/encoding/internal/identifier](https://godoc.org/golang.org/x/text/encoding/internal/identifier)
+
+* [golang.org/x/text/encoding/japanese](https://godoc.org/golang.org/x/text/encoding/japanese)
+
+* [golang.org/x/text/encoding/korean](https://godoc.org/golang.org/x/text/encoding/korean)
+
+* [golang.org/x/text/encoding/simplifiedchinese](https://godoc.org/golang.org/x/text/encoding/simplifiedchinese)
+
+* [golang.org/x/text/encoding/traditionalchinese](https://godoc.org/golang.org/x/text/encoding/traditionalchinese)
+
+* [golang.org/x/text/encoding/unicode](https://godoc.org/golang.org/x/text/encoding/unicode)
+
+* [golang.org/x/text/internal](https://godoc.org/golang.org/x/text/internal)
+
 * [golang.org/x/text/internal/gen](https://godoc.org/golang.org/x/text/internal/gen)
 
+* [golang.org/x/text/internal/language](https://godoc.org/golang.org/x/text/internal/language)
+
+* [golang.org/x/text/internal/language/compact](https://godoc.org/golang.org/x/text/internal/language/compact)
+
+* [golang.org/x/text/internal/tag](https://godoc.org/golang.org/x/text/internal/tag)
+
 * [golang.org/x/text/internal/testtext](https://godoc.org/golang.org/x/text/internal/testtext)
 
+* [golang.org/x/text/internal/ucd](https://godoc.org/golang.org/x/text/internal/ucd)
+
+* [golang.org/x/text/internal/utf8internal](https://godoc.org/golang.org/x/text/internal/utf8internal)
+
+* [golang.org/x/text/language](https://godoc.org/golang.org/x/text/language)
+
+* [golang.org/x/text/runes](https://godoc.org/golang.org/x/text/runes)
+
 * [golang.org/x/text/transform](https://godoc.org/golang.org/x/text/transform)
 
 * [golang.org/x/text/unicode/cldr](https://godoc.org/golang.org/x/text/unicode/cldr)
 
 * [golang.org/x/text/unicode/norm](https://godoc.org/golang.org/x/text/unicode/norm)
 
+* [golang.org/x/text/unicode/rangetable](https://godoc.org/golang.org/x/text/unicode/rangetable)
+
 * [gopkg.in/check.v1](https://godoc.org/gopkg.in/check.v1)
 
 * [gopkg.in/russross/blackfriday.v1](https://godoc.org/gopkg.in/russross/blackfriday.v1)
diff --git a/default_context_test.go b/default_context_test.go
index 6ba9473c3..514d08d3f 100644
--- a/default_context_test.go
+++ b/default_context_test.go
@@ -4,12 +4,11 @@ import (
 	"bytes"
 	"context"
 	"net/http"
-	"net/http/httptest"
 	"net/url"
 	"testing"
 
 	"github.com/gobuffalo/buffalo/render"
-	"github.com/markbates/willie"
+	"github.com/gobuffalo/httptest"
 	"github.com/pkg/errors"
 	"github.com/stretchr/testify/require"
 )
@@ -31,8 +30,8 @@ func Test_DefaultContext_Redirect(t *testing.T) {
 		return c.Redirect(302, u)
 	})
 
-	w := willie.New(a)
-	res := w.Request("/").Get()
+	w := httptest.New(a)
+	res := w.HTML("/").Get()
 	r.Equal(u, res.Location())
 }
 
@@ -66,12 +65,12 @@ func Test_DefaultContext_Redirect_Helper(t *testing.T) {
 			return c.Redirect(302, "rootPath()")
 		})
 
-		w := willie.New(a)
-		res := w.Request("/").Get()
+		w := httptest.New(a)
+		res := w.HTML("/").Get()
 		r.Equal(tt.S, res.Code)
 		r.Equal(tt.E, res.Location())
 
-		res = w.Request("/nomap").Get()
+		res = w.HTML("/nomap").Get()
 		r.Equal(302, res.Code)
 		r.Equal("/", res.Location())
 	}
@@ -98,7 +97,7 @@ func Test_DefaultContext_Param_form(t *testing.T) {
 		return nil
 	})
 
-	w := willie.New(app)
+	w := httptest.New(app)
 	res := w.HTML("/").Post(map[string]string{
 		"name": "Mark",
 	})
@@ -160,9 +159,9 @@ func Test_DefaultContext_Bind_Default(t *testing.T) {
 		return c.Render(201, nil)
 	})
 
-	w := willie.New(a)
+	w := httptest.New(a)
 	uv := url.Values{"first_name": []string{"Mark"}}
-	res := w.Request("/").Post(uv)
+	res := w.HTML("/").Post(uv)
 	r.Equal(201, res.Code)
 
 	r.Equal("Mark", user.FirstName)
@@ -243,9 +242,9 @@ func Test_DefaultContext_Bind_Default_BlankFields(t *testing.T) {
 		return c.Render(201, nil)
 	})
 
-	w := willie.New(a)
+	w := httptest.New(a)
 	uv := url.Values{"first_name": []string{""}}
-	res := w.Request("/").Post(uv)
+	res := w.HTML("/").Post(uv)
 	r.Equal(201, res.Code)
 
 	r.Equal("", user.FirstName)
@@ -267,7 +266,7 @@ func Test_DefaultContext_Bind_JSON(t *testing.T) {
 		return c.Render(201, nil)
 	})
 
-	w := willie.New(a)
+	w := httptest.New(a)
 	res := w.JSON("/").Post(map[string]string{
 		"first_name": "Mark",
 	})
diff --git a/errors_test.go b/errors_test.go
index fd69ea61b..658be47cb 100644
--- a/errors_test.go
+++ b/errors_test.go
@@ -3,7 +3,8 @@ package buffalo
 import (
 	"testing"
 
-	"github.com/markbates/willie"
+	"github.com/gobuffalo/httptest"
+
 	"github.com/pkg/errors"
 	"github.com/stretchr/testify/require"
 )
@@ -15,7 +16,7 @@ func Test_defaultErrorHandler_SetsContentType(t *testing.T) {
 		return c.Error(401, errors.New("boom"))
 	})
 
-	w := willie.New(app)
+	w := httptest.New(app)
 	res := w.HTML("/").Get()
 	r.Equal(401, res.Code)
 	ct := res.Header().Get("content-type")
@@ -41,7 +42,7 @@ func Test_PanicHandler(t *testing.T) {
 
 	const stack = `github.com/gobuffalo/buffalo.(*App).PanicHandler`
 
-	w := willie.New(app)
+	w := httptest.New(app)
 	for _, tt := range table {
 		t.Run(tt.path, func(st *testing.T) {
 			r := require.New(st)
diff --git a/flash_test.go b/flash_test.go
index 1712dd124..81d9f8707 100644
--- a/flash_test.go
+++ b/flash_test.go
@@ -4,7 +4,7 @@ import (
 	"testing"
 
 	"github.com/gobuffalo/buffalo/render"
-	"github.com/markbates/willie"
+	"github.com/gobuffalo/httptest"
 	"github.com/stretchr/testify/require"
 )
 
@@ -37,8 +37,8 @@ func Test_FlashRender(t *testing.T) {
 		return c.Render(201, rr.String(errorsTPL))
 	})
 
-	w := willie.New(a)
-	res := w.Request("/").Get()
+	w := httptest.New(a)
+	res := w.HTML("/").Get()
 
 	r.Contains(res.Body.String(), "Error AJ set")
 	r.Contains(res.Body.String(), "Error DAL set")
@@ -53,9 +53,9 @@ func Test_FlashRenderEmpty(t *testing.T) {
 		return c.Render(201, rr.String(errorsTPL))
 	})
 
-	w := willie.New(a)
+	w := httptest.New(a)
 
-	res := w.Request("/").Get()
+	res := w.HTML("/").Get()
 	r.NotContains(res.Body.String(), "Flash:")
 }
 
@@ -76,8 +76,8 @@ func Test_FlashRenderEntireFlash(t *testing.T) {
 		return c.Render(201, rr.String(keyTPL))
 	})
 
-	w := willie.New(a)
-	res := w.Request("/").Get()
+	w := httptest.New(a)
+	res := w.HTML("/").Get()
 	r.Contains(res.Body.String(), "something to say!")
 }
 
@@ -97,8 +97,8 @@ func Test_FlashRenderCustomKey(t *testing.T) {
 		return c.Render(201, rr.String(keyTPL))
 	})
 
-	w := willie.New(a)
-	res := w.Request("/").Get()
+	w := httptest.New(a)
+	res := w.HTML("/").Get()
 	r.Contains(res.Body.String(), "something to say!")
 }
 
@@ -111,8 +111,8 @@ func Test_FlashRenderCustomKeyNotDefined(t *testing.T) {
 		return c.Render(201, rr.String(customKeyTPL))
 	})
 
-	w := willie.New(a)
-	res := w.Request("/").Get()
+	w := httptest.New(a)
+	res := w.HTML("/").Get()
 	r.NotContains(res.Body.String(), "something to say!")
 }
 
diff --git a/go.mod b/go.mod
index b5f143e8d..95c854082 100644
--- a/go.mod
+++ b/go.mod
@@ -5,11 +5,12 @@ require (
 	github.com/dgrijalva/jwt-go v3.2.0+incompatible
 	github.com/dustin/go-humanize v0.0.0-20180713052910-9f541cc9db5d
 	github.com/fatih/color v1.7.0
-	github.com/gobuffalo/buffalo-plugins v0.0.0-20180820141205-03ceb944b112
+	github.com/gobuffalo/buffalo-plugins v0.0.0-20180823153124-4e86bafb6c76
 	github.com/gobuffalo/buffalo-pop v0.0.0-20180818124224-e3bbd0b11d3e
 	github.com/gobuffalo/envy v1.6.4
 	github.com/gobuffalo/fizz v1.0.10 // indirect
 	github.com/gobuffalo/github_flavored_markdown v1.0.0
+	github.com/gobuffalo/httptest v1.0.1
 	github.com/gobuffalo/makr v1.1.4
 	github.com/gobuffalo/mw-basicauth v0.0.0-20180802152105-15d67c4ac152
 	github.com/gobuffalo/mw-contenttype v0.0.0-20180802152300-74f5a47f4d56
@@ -18,24 +19,21 @@ require (
 	github.com/gobuffalo/mw-i18n v0.0.0-20180802152014-e3060b7e13d6
 	github.com/gobuffalo/mw-paramlogger v0.0.0-20180807082017-6b90b69a724a
 	github.com/gobuffalo/mw-tokenauth v0.0.0-20180802152212-d09751da96e0
-	github.com/gobuffalo/packr v1.13.2
+	github.com/gobuffalo/packr v1.13.3
 	github.com/gobuffalo/plush v3.7.16+incompatible
 	github.com/gobuffalo/pop v4.6.8+incompatible
 	github.com/gobuffalo/shoulders v0.0.0-20180815165021-5569039eac2f
-	github.com/gobuffalo/tags v2.0.9+incompatible
+	github.com/gobuffalo/tags v2.0.10+incompatible
 	github.com/gobuffalo/x v0.0.0-20180816203319-dc54d929c4a2
-	github.com/golang/protobuf v1.2.0 // indirect
 	github.com/gorilla/context v1.1.1
 	github.com/gorilla/mux v1.6.2
 	github.com/gorilla/sessions v1.1.1
-	github.com/lib/pq v0.0.0-20180822103908-55f6f2718ccb // indirect
+	github.com/lib/pq v1.0.0 // indirect
 	github.com/markbates/deplist v1.0.2
 	github.com/markbates/grift v1.0.1
 	github.com/markbates/inflect v1.0.0
 	github.com/markbates/refresh v1.4.2
 	github.com/markbates/sigtx v1.0.0
-	github.com/markbates/willie v1.0.7
-	github.com/microcosm-cc/bluemonday v1.0.1 // indirect
 	github.com/monoculum/formam v0.0.0-20180818005819-0a5cdaa81e2e
 	github.com/pkg/errors v0.8.0
 	github.com/sirupsen/logrus v1.0.6
@@ -44,8 +42,6 @@ require (
 	github.com/spf13/viper v1.1.0
 	github.com/stretchr/testify v1.2.2
 	golang.org/x/crypto v0.0.0-20180820150726-614d502a4dac
-	golang.org/x/net v0.0.0-20180821023952-922f4815f713 // indirect
 	golang.org/x/sync v0.0.0-20180314180146-1d60e4601c6f
-	golang.org/x/sys v0.0.0-20180821140842-3b58ed4ad339 // indirect
 	gopkg.in/mail.v2 v2.0.0-20180731213649-a0242b2233b4
 )
diff --git a/go.sum b/go.sum
index 5210f03cf..dabb4f10a 100644
--- a/go.sum
+++ b/go.sum
@@ -8,7 +8,6 @@ github.com/cockroachdb/cockroach-go v0.0.0-20180212155653-59c0560478b7 h1:XFqp7V
 github.com/cockroachdb/cockroach-go v0.0.0-20180212155653-59c0560478b7/go.mod h1:XGLbWH/ujMcbPbhZq52Nv6UrCghb1yGn//133kEsvDk=
 github.com/codegangsta/negroni v0.3.0 h1:ByBtJaE0u71x6Ebli7lm95c8oCkrmF88+s5qB2o6j8I=
 github.com/codegangsta/negroni v0.3.0/go.mod h1:v0y3T5G7Y1UlFfyxFn/QLRU4a2EuNau2iZY63YTKWo0=
-github.com/davecgh/go-spew v1.1.0 h1:ZDRjVQ15GmhC3fiQ8ni8+OwkZQO4DARzQgrnXU1Liz8=
 github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=
 github.com/davecgh/go-spew v1.1.1 h1:vj9j/u1bqnvCEfJOwUhtlOARqs3+rkHYY13jYWTU97c=
 github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=
@@ -25,25 +24,23 @@ github.com/fsnotify/fsnotify v1.4.7/go.mod h1:jwhsz4b93w/PPRr/qN1Yymfu8t87LnFCMo
 github.com/go-sql-driver/mysql v1.4.0 h1:7LxgVwFb2hIQtMm87NdgAVfXjnt4OePseqT1tKx+opk=
 github.com/go-sql-driver/mysql v1.4.0/go.mod h1:zAC/RDZ24gD3HViQzih4MyKcchzm+sOG5ZlKdlhCg5w=
 github.com/gobuffalo/buffalo v0.12.6/go.mod h1:kp1qgfbzOQGfN+iXKPiVsKHXx16/XsnF9eB8nZawdEs=
-github.com/gobuffalo/buffalo-plugins v0.0.0-20180820141205-03ceb944b112 h1:HNySaHk5G5x0Eoq9A/oGQq+600zgWVHHXibEWmYzIWc=
-github.com/gobuffalo/buffalo-plugins v0.0.0-20180820141205-03ceb944b112/go.mod h1:zRqRWL38hEJux6FsYHQHYRqANAsQlKxzcPrfHKQycmA=
+github.com/gobuffalo/buffalo-plugins v0.0.0-20180823153124-4e86bafb6c76 h1:N0Muj3qGxK+tSsRHhRIhIBqLfqVhzdDvmImzmANHoVc=
+github.com/gobuffalo/buffalo-plugins v0.0.0-20180823153124-4e86bafb6c76/go.mod h1:2wygsI1hf7vvK2S+Tvo5UhPnE2JT0pYx3JDSqux/QSw=
 github.com/gobuffalo/buffalo-pop v0.0.0-20180818124224-e3bbd0b11d3e h1:UkZtClt8Oy83+v5N8dJ3zDPNbGk7K3fHJpagXgcNx6k=
 github.com/gobuffalo/buffalo-pop v0.0.0-20180818124224-e3bbd0b11d3e/go.mod h1:pjzWxoot16IF9xupOei/JRVox5XQTOM8YJjKR1fr/VA=
-github.com/gobuffalo/envy v1.6.3 h1:I9iyNACF0Tovfta7iqLrUAXFHYBDBWveQrjpEv2XeWs=
 github.com/gobuffalo/envy v1.6.3/go.mod h1:gOxUQY+OEwqH1a2m25Sqax1GIhj31tPNOIdFzj8QThs=
 github.com/gobuffalo/envy v1.6.4 h1:kxamN+VYjPMzEdjc2mn4CIKiuYXGxc8VIwXJNixFlNY=
 github.com/gobuffalo/envy v1.6.4/go.mod h1:Abh+Jfw475/NWtYMEt+hnJWRiC8INKWibIMyNt1w2Mc=
-github.com/gobuffalo/fizz v1.0.7 h1:xvG4eDlZvwzFq1cUk13VsveNNBHAIxOBDYBW3MGCLtg=
 github.com/gobuffalo/fizz v1.0.7/go.mod h1:fbtmvB0dcsGJUxM/S8biqkQtvykqPQGdkcg94zVu8GA=
 github.com/gobuffalo/fizz v1.0.10 h1:MspJcEEBN2eApqiFd4tuoTpYZF6wM5B6/Ink/rJcqOI=
 github.com/gobuffalo/fizz v1.0.10/go.mod h1:jpD+pJ065MDYCc4nA86aUQ/ovwCjGGNl4zq4xrAxJa0=
 github.com/gobuffalo/flect v0.0.0-20180728145722-2949e73d74b0/go.mod h1:B1X1r2SsFPE8Idc2OCoc+/eGmiknyq6oWDXLAYzRFLE=
-github.com/gobuffalo/genny v0.0.0-20180818195054-34f68115d51f h1:G4IHVYSIej7Xil0jTed2UFwBdIy6Zg7fBrTbja8OjUc=
-github.com/gobuffalo/genny v0.0.0-20180818195054-34f68115d51f/go.mod h1:b6zAEpWtCPxZisqb6/WRqvGOQ7Mg5SlUwoQZySx1w1U=
+github.com/gobuffalo/genny v0.0.0-20180823134419-80135003197d/go.mod h1:XMTCgXTkogNQIpTexc1f6T6iQ1MCjRc/1gzLTpWIjJ0=
 github.com/gobuffalo/github_flavored_markdown v1.0.0 h1:e2dK+SoHgOc/vfXuYMdXwEg2vAUlFzp8SBRwTOXckQ0=
 github.com/gobuffalo/github_flavored_markdown v1.0.0/go.mod h1:c8/8gRnd6MSyyk+fp6E8O8cUTHd7P2cnDnH4G7o91l0=
+github.com/gobuffalo/httptest v1.0.1 h1:F7KibLzHAHy1UZVpqwcd95aKcoI3gbSj7FgkDZ9lHow=
+github.com/gobuffalo/httptest v1.0.1/go.mod h1:ZLh197oiAQAJO2L7WYaZhllanqUUkWsUQ75bU6D1J6A=
 github.com/gobuffalo/makr v1.1.1/go.mod h1:1Ga9O4Gqd5xXc+AoI3eLwgu7k+gWamSUXd2Ps942KkM=
-github.com/gobuffalo/makr v1.1.2 h1:Dix34nvNM3v4EHNmoVysaAZBgPbMFJTwKXBrVonw2Kg=
 github.com/gobuffalo/makr v1.1.2/go.mod h1:5/uvRIyR+DQHJrX0UPCPF0WhQGMJG5/xd9XT9qEXQE8=
 github.com/gobuffalo/makr v1.1.4 h1:REIMYySfhRCK0He5MdDaIN/4NpfCtrt8g/ENLcmmzPg=
 github.com/gobuffalo/makr v1.1.4/go.mod h1:Y+o0btAH1kYAMDJW/TX3+oAXEu0bmSLLoC9mIFxtzOw=
@@ -62,8 +59,9 @@ github.com/gobuffalo/mw-paramlogger v0.0.0-20180807082017-6b90b69a724a/go.mod h1
 github.com/gobuffalo/mw-tokenauth v0.0.0-20180802152212-d09751da96e0 h1:v5r9HjKo88iTByIoeNARxrzfZbrQzm/yKlCBXB/RkMw=
 github.com/gobuffalo/mw-tokenauth v0.0.0-20180802152212-d09751da96e0/go.mod h1:UqBF00IfKvd39ni5+yI5MLMjAf4gX7cDKN/26zDOD6c=
 github.com/gobuffalo/packr v1.13.1/go.mod h1:m3J/Q/tkaODAQq3r6NyWhDhJs2cVZS/lU0+0Edmfv3c=
-github.com/gobuffalo/packr v1.13.2 h1:fQmeSiOMhl+4U+da7VmX2AjdcCaSOi5IvnqsSXdKYmQ=
 github.com/gobuffalo/packr v1.13.2/go.mod h1:qdqw8AgJyKw60qj56fnEBiS9fIqqCaP/vWJQvR4Jcss=
+github.com/gobuffalo/packr v1.13.3 h1:XjxS2G7cI2kb1KtGwO+ziCdB/D0kAuU/eG3BAieQT+4=
+github.com/gobuffalo/packr v1.13.3/go.mod h1:qdqw8AgJyKw60qj56fnEBiS9fIqqCaP/vWJQvR4Jcss=
 github.com/gobuffalo/plush v0.0.0-20180810170812-274552812256/go.mod h1:vdLIKHIw/7fnuNo9clH7hkIP50T27JgtfrcD2mnqIBM=
 github.com/gobuffalo/plush v3.7.16+incompatible h1:nonpy24axg04np13bYi0zNu3gr812cXKJDNLSkKcEwk=
 github.com/gobuffalo/plush v3.7.16+incompatible/go.mod h1:rQ4zdtUUyZNqULlc6bqd5scsPfLKfT0+TGMChgduDvI=
@@ -73,20 +71,18 @@ github.com/gobuffalo/pop v4.6.8+incompatible/go.mod h1:DwBz3SD5SsHpTZiTubcsFWcVD
 github.com/gobuffalo/shoulders v0.0.0-20180815165021-5569039eac2f h1:FdNwdqDxs4t4GKKS1yG3krQRVWSmJ9tntDhm69wfVq4=
 github.com/gobuffalo/shoulders v0.0.0-20180815165021-5569039eac2f/go.mod h1:6BOi9bQ44FOef+BnbjTps9APr8fZE1Yvcs4BdeY940U=
 github.com/gobuffalo/tags v2.0.6+incompatible/go.mod h1:9XmhOkyaB7UzvuY4UoZO4s67q8/xRMVJEaakauVQYeY=
-github.com/gobuffalo/tags v2.0.9+incompatible h1:Jca4JTk3YttPt8fIMnXen9QFBNN0T5pXH6M/87b4bww=
 github.com/gobuffalo/tags v2.0.9+incompatible/go.mod h1:9XmhOkyaB7UzvuY4UoZO4s67q8/xRMVJEaakauVQYeY=
+github.com/gobuffalo/tags v2.0.10+incompatible h1:gLcbJPHlzAiuZVsxDvTSwoXz/vJmNjgelxP5zrADb9o=
+github.com/gobuffalo/tags v2.0.10+incompatible/go.mod h1:9XmhOkyaB7UzvuY4UoZO4s67q8/xRMVJEaakauVQYeY=
 github.com/gobuffalo/uuid v2.0.0+incompatible/go.mod h1:ErhIzkRhm0FtRuiE/PeORqcw4cVi1RtSpnwYrxuvkfE=
 github.com/gobuffalo/uuid v2.0.3+incompatible h1:W83ymTRbzM+XNntIsjC8j63FyzGytcfKTudU1Cg6xyk=
 github.com/gobuffalo/uuid v2.0.3+incompatible/go.mod h1:ErhIzkRhm0FtRuiE/PeORqcw4cVi1RtSpnwYrxuvkfE=
-github.com/gobuffalo/validate v2.0.0+incompatible h1:KllrOhUUzAeTil8MaaQorZOH0Bx6KOvi8mRVlwFHRA4=
 github.com/gobuffalo/validate v2.0.0+incompatible/go.mod h1:N+EtDe0J8252BgfzQUChBgfd6L93m9weay53EWFVsMM=
 github.com/gobuffalo/validate v2.0.3+incompatible h1:6f4JCEz11Zi6iIlexMv7Jz10RBPvgI795AOaubtCwTE=
 github.com/gobuffalo/validate v2.0.3+incompatible/go.mod h1:N+EtDe0J8252BgfzQUChBgfd6L93m9weay53EWFVsMM=
-github.com/gobuffalo/x v0.0.0-20180117215853-11ca13c05abd h1:0AiAe/jaKqMCar/zjOQFewW33iOLsCD6lPbqYlTcr2Q=
 github.com/gobuffalo/x v0.0.0-20180117215853-11ca13c05abd/go.mod h1:WevpGD+5YOreDJznWevcn8NTmQEW5STSBgIkpkjzqXc=
 github.com/gobuffalo/x v0.0.0-20180816203319-dc54d929c4a2 h1:L4IIzLTXHRmnCnH4/OOa7yeDL9kk6dK+tnLcXfu8nDo=
 github.com/gobuffalo/x v0.0.0-20180816203319-dc54d929c4a2/go.mod h1:oX3kj94UfTZqmz9XowUgR7Ghpz5I+JmkMDpWJlwa9h8=
-github.com/golang/protobuf v1.1.0 h1:0iH4Ffd/meGoXqF2lSAhZHt8X+cPgkfn/cb6Cce5Vpc=
 github.com/golang/protobuf v1.1.0/go.mod h1:6lQm79b+lXiMfvg/cZm0SGofjICqVBUtrP5yJMmIC1U=
 github.com/golang/protobuf v1.2.0 h1:P3YflyNX/ehuJFLhxviNdFxQPkGK5cDcApsge1SqnvM=
 github.com/golang/protobuf v1.2.0/go.mod h1:6lQm79b+lXiMfvg/cZm0SGofjICqVBUtrP5yJMmIC1U=
@@ -115,16 +111,14 @@ github.com/kr/pretty v0.1.0/go.mod h1:dAy3ld7l9f0ibDNOQOHHMYYIIbhfbHSm3C4ZsoJORN
 github.com/kr/pty v1.1.1/go.mod h1:pFQYn66WHrOpPYNljwOMqo10TkYh1fy3cYio2l3bCsQ=
 github.com/kr/text v0.1.0 h1:45sCR5RtlFHMR4UwH9sdQ5TC8v0qDQCHnXt+kaKSTVE=
 github.com/kr/text v0.1.0/go.mod h1:4Jbv+DJW3UT/LiOwJeYQe1efqtUx/iVham/4vfdArNI=
-github.com/lib/pq v0.0.0-20180523175426-90697d60dd84 h1:it29sI2IM490luSc3RAhp5WuCYnc6RtbfLVAB7nmC5M=
 github.com/lib/pq v0.0.0-20180523175426-90697d60dd84/go.mod h1:5WUZQaWbwv1U+lTReE5YruASi9Al49XbQIvNi/34Woo=
-github.com/lib/pq v0.0.0-20180822103908-55f6f2718ccb h1:y4wxGMpTq5l97SEl+BPMZoDPyRHQjrKwb5ze4psanic=
-github.com/lib/pq v0.0.0-20180822103908-55f6f2718ccb/go.mod h1:5WUZQaWbwv1U+lTReE5YruASi9Al49XbQIvNi/34Woo=
+github.com/lib/pq v1.0.0 h1:X5PMW56eZitiTeO7tKzZxFCSpbFZJtkMMooicw2us9A=
+github.com/lib/pq v1.0.0/go.mod h1:5WUZQaWbwv1U+lTReE5YruASi9Al49XbQIvNi/34Woo=
 github.com/magiconair/properties v1.8.0 h1:LLgXmsheXeRoUOBOjtwPQCWIYqM/LU1ayDtDePerRcY=
 github.com/magiconair/properties v1.8.0/go.mod h1:PppfXfuXeibc/6YijjN8zIbojt8czPbwD3XqdrwzmxQ=
 github.com/markbates/deplist v1.0.2 h1:91fPoNtVdkSJa/F0Zv/5+CzcZ9OnCzbWYUmFpCKe3X8=
 github.com/markbates/deplist v1.0.2/go.mod h1:ZerU6FuDYMFbdh+BdCNmce+SexbmOZd/ftnrcxVyNXQ=
 github.com/markbates/going v1.0.0/go.mod h1:I6mnB4BPnEeqo85ynXIx1ZFLLbtiLHNXVgWeFO9OGOA=
-github.com/markbates/going v1.0.1 h1:IFDakPS7ROqx1rESYPSZmURUTwI4HWuM5waQIFCUZZQ=
 github.com/markbates/going v1.0.1/go.mod h1:I6mnB4BPnEeqo85ynXIx1ZFLLbtiLHNXVgWeFO9OGOA=
 github.com/markbates/going v1.0.2 h1:uNQHDDfMRNOUmuxDbPbvatyw4wr4UOSUZkGkdkcip1o=
 github.com/markbates/going v1.0.2/go.mod h1:UWCk3zm0UKefHZ7l8BNqi26UyiEMniznk8naLdTcy6c=
@@ -136,7 +130,6 @@ github.com/markbates/hmax v1.0.0 h1:yo2N0gBoCnUMKhV/VRLHomT6Y9wUm+oQQENuWJqCdlM=
 github.com/markbates/hmax v1.0.0/go.mod h1:cOkR9dktiESxIMu+65oc/r/bdY4bE8zZw3OLhLx0X2c=
 github.com/markbates/inflect v1.0.0 h1:gTffXSQCc+WaIvBcI/IItJQMOemietXr5EIKLXDYqI4=
 github.com/markbates/inflect v1.0.0/go.mod h1:oTeZL2KHA7CUX6X+fovmK9OvIOFuqu0TwdQrZjLTh88=
-github.com/markbates/refresh v1.4.1 h1:+kEJt7Bz6Bn/pjmnbFHhyAEnO+mW0POtyqsVyK62o3A=
 github.com/markbates/refresh v1.4.1/go.mod h1:og/05QDfszH/SCl3w8VI2Or990yna0wS2lqRcJoDqAg=
 github.com/markbates/refresh v1.4.2 h1:xQfceULuw5iEON8MB6hAs9XoMrOpYrd7feQgRWFDj+0=
 github.com/markbates/refresh v1.4.2/go.mod h1:C/Zey3IPrq0lXq1+SDhCQOuy7dKR3CabthJTTZP8AQg=
@@ -144,19 +137,15 @@ github.com/markbates/sigtx v1.0.0 h1:y/xtkBvNPRjD4KeEplf4w9rJVSc23/xl+jXYGowTwy0
 github.com/markbates/sigtx v1.0.0/go.mod h1:QF1Hv6Ic6Ca6W+T+DL0Y/ypborFKyvUY9HmuCD4VeTc=
 github.com/markbates/willie v1.0.6 h1:VguZshKlOyixOjcEdtlWxzCgr7AZE/3u+2bai9Ik1wY=
 github.com/markbates/willie v1.0.6/go.mod h1:XtK+fmQ7tgVMIVAS1ghwuqVPup3GtgrNY3UCvUlPdzM=
-github.com/markbates/willie v1.0.7 h1:0W+oMu9Ah+jvukKH9OmXFeKNDmbjqry8BcS9dQiRshU=
-github.com/markbates/willie v1.0.7/go.mod h1:42G0jXiZEVLXutUa33JFH8tQW2dsHAqwYWNlVHfPtvM=
 github.com/mattn/go-colorable v0.0.9 h1:UVL0vNpWh04HeJXV0KLcaT7r06gOH2l4OW6ddYRUIY4=
 github.com/mattn/go-colorable v0.0.9/go.mod h1:9vuHe8Xs5qXnSaW/c/ABM9alt+Vo+STaOChaDxuIBZU=
 github.com/mattn/go-isatty v0.0.3 h1:ns/ykhmWi7G9O+8a448SecJU3nSMBXJfqQkl0upE1jI=
 github.com/mattn/go-isatty v0.0.3/go.mod h1:M+lRXTBqGeGNdLjl/ufCoiOlB5xdOkqRJdNxMWT7Zi4=
 github.com/mattn/go-sqlite3 v1.9.0 h1:pDRiWfl+++eC2FEFRy6jXmQlvp4Yh3z1MJKg4UeYM/4=
 github.com/mattn/go-sqlite3 v1.9.0/go.mod h1:FPy6KqzDD04eiIsT53CuJW3U88zkxoIYsOqkbpncsNc=
-github.com/microcosm-cc/bluemonday v1.0.0 h1:dr58SIfmOwOVr+m4Ye1xLWv8Dk9OFwXAtYnbJSmJ65k=
 github.com/microcosm-cc/bluemonday v1.0.0/go.mod h1:hsXNsILzKxV+sX77C5b8FSuKF00vh2OMYv+xgHpAMF4=
 github.com/microcosm-cc/bluemonday v1.0.1 h1:SIYunPjnlXcW+gVfvm0IlSeR5U3WZUOLfVmqg85Go44=
 github.com/microcosm-cc/bluemonday v1.0.1/go.mod h1:hsXNsILzKxV+sX77C5b8FSuKF00vh2OMYv+xgHpAMF4=
-github.com/mitchellh/go-homedir v0.0.0-20180523094522-3864e76763d9 h1:Y94YB7jrsihrbGSqRNMwRWJ2/dCxr0hdC2oPRohkx0A=
 github.com/mitchellh/go-homedir v0.0.0-20180523094522-3864e76763d9/go.mod h1:SfyaCUpYCn1Vlf4IUYiD9fPX4A5wJrkLzIz1N1q0pr0=
 github.com/mitchellh/go-homedir v0.0.0-20180801233206-58046073cbff h1:jM4Eo4qMmmcqePS3u6X2lcEELtVuXWkWJIS/pRI3oSk=
 github.com/mitchellh/go-homedir v0.0.0-20180801233206-58046073cbff/go.mod h1:SfyaCUpYCn1Vlf4IUYiD9fPX4A5wJrkLzIz1N1q0pr0=
@@ -217,33 +206,27 @@ github.com/stretchr/testify v1.2.2 h1:bSDNvY7ZPG5RlJ8otE/7V6gMiyenm9RtJ7IUVIAoJ1
 github.com/stretchr/testify v1.2.2/go.mod h1:a8OnRcib4nhh0OaRAV+Yts87kKdq0PP7pXfy6kDkUVs=
 github.com/unrolled/secure v0.0.0-20180618144512-8287f3899c8e h1:tgJKQPcQriVRZoTd6NXN3jITyBs6vR1H+0JsulRuX6s=
 github.com/unrolled/secure v0.0.0-20180618144512-8287f3899c8e/go.mod h1:mnPT77IAdsi/kV7+Es7y+pXALeV3h7G6dQF6mNYjcLA=
-golang.org/x/crypto v0.0.0-20180808211826-de0752318171 h1:vYogbvSFj2YXcjQxFHu/rASSOt9sLytpCaSkiwQ135I=
 golang.org/x/crypto v0.0.0-20180808211826-de0752318171/go.mod h1:6SG95UA2DQfeDnfUPMdvaQW0Q7yPrPDi9nlGo2tz2b4=
-golang.org/x/crypto v0.0.0-20180816225734-aabede6cba87 h1:gCHhzI+1R9peHIMyiWVxoVaWlk1cYK7VThX5ptLtbXY=
-golang.org/x/crypto v0.0.0-20180816225734-aabede6cba87/go.mod h1:6SG95UA2DQfeDnfUPMdvaQW0Q7yPrPDi9nlGo2tz2b4=
 golang.org/x/crypto v0.0.0-20180820150726-614d502a4dac h1:7d7lG9fHOLdL6jZPtnV4LpI41SbohIJ1Atq7U991dMg=
 golang.org/x/crypto v0.0.0-20180820150726-614d502a4dac/go.mod h1:6SG95UA2DQfeDnfUPMdvaQW0Q7yPrPDi9nlGo2tz2b4=
 golang.org/x/net v0.0.0-20180801234040-f4c29de78a2a/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4=
 golang.org/x/net v0.0.0-20180808004115-f9ce57c11b24/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4=
-golang.org/x/net v0.0.0-20180811021610-c39426892332 h1:efGso+ep0DjyCBJPjvoz0HI6UldX4Md2F1rZFe1ir0E=
 golang.org/x/net v0.0.0-20180811021610-c39426892332/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4=
-golang.org/x/net v0.0.0-20180816102801-aaf60122140d h1:211XH5RPVP5tOBkz6xm3/b7KxtjqVf6PYG+evqJpE08=
 golang.org/x/net v0.0.0-20180816102801-aaf60122140d/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4=
 golang.org/x/net v0.0.0-20180821023952-922f4815f713 h1:rMJUcaDGbG+X967I4zGKCq5laYqcGKJmpB+3jhpOhPw=
 golang.org/x/net v0.0.0-20180821023952-922f4815f713/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4=
 golang.org/x/sync v0.0.0-20180314180146-1d60e4601c6f h1:wMNYb4v58l5UBM7MYRLPG6ZhfOqbKu7X5eyFl8ZhKvA=
 golang.org/x/sync v0.0.0-20180314180146-1d60e4601c6f/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
 golang.org/x/sys v0.0.0-20180616030259-6c888cc515d3/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
-golang.org/x/sys v0.0.0-20180814072032-4e1fef560951 h1:VfGaXvV9wRnTJreeGDE0FWEDiQP1WWUDmutCjCThDz8=
 golang.org/x/sys v0.0.0-20180814072032-4e1fef560951/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
-golang.org/x/sys v0.0.0-20180816055513-1c9583448a9c h1:uHnKXcvx6SNkuwC+nrzxkJ+TpPwZOtumbhWrrOYN5YA=
 golang.org/x/sys v0.0.0-20180816055513-1c9583448a9c/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
-golang.org/x/sys v0.0.0-20180821140842-3b58ed4ad339 h1:0w2EXzxbB03VAzqwe3csbadu4CPhMRtxCz/rjw9gkic=
 golang.org/x/sys v0.0.0-20180821140842-3b58ed4ad339/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
+golang.org/x/sys v0.0.0-20180823144017-11551d06cbcc h1:MeuS1UDyZyFH++6vVy44PuufTeFF0d0nfI6XB87YGSk=
+golang.org/x/sys v0.0.0-20180823144017-11551d06cbcc/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
 golang.org/x/text v0.3.0 h1:g61tztE5qeGQ89tm6NTjjM9VPIm088od1l6aSorWRWg=
 golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ=
-golang.org/x/tools v0.0.0-20180817170705-7d1dc997617f h1:PKEiTD+GsM0tTOVt125xcm3tN+JExjPbuypItbieWw0=
-golang.org/x/tools v0.0.0-20180817170705-7d1dc997617f/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ=
+golang.org/x/tools v0.0.0-20180822150542-447b503c8ba6/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ=
+golang.org/x/tools v0.0.0-20180823152632-ba93f9405e54/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ=
 google.golang.org/appengine v1.1.0 h1:igQkv0AAhEIvTEpD5LIpAfav2eeVO9HBTjvKHVJPRSs=
 google.golang.org/appengine v1.1.0/go.mod h1:EbEs0AVv82hx2wNQdGPgUI5lhzA/G0D9YwlJXL52JkM=
 gopkg.in/airbrake/gobrake.v2 v2.0.9 h1:7z2uVWwn7oVeeugY1DtlPAy5H+KYgB1KeKTnqjNatLo=
diff --git a/method_override_test.go b/method_override_test.go
index a80d2ef0d..36d7be01e 100644
--- a/method_override_test.go
+++ b/method_override_test.go
@@ -5,7 +5,7 @@ import (
 	"testing"
 
 	"github.com/gobuffalo/buffalo/render"
-	"github.com/markbates/willie"
+	"github.com/gobuffalo/httptest"
 	"github.com/stretchr/testify/require"
 )
 
@@ -17,8 +17,8 @@ func Test_MethodOverride(t *testing.T) {
 		return c.Render(200, render.String("you put me!"))
 	})
 
-	w := willie.New(a)
-	res := w.Request("/").Post(url.Values{"_method": []string{"PUT"}})
+	w := httptest.New(a)
+	res := w.HTML("/").Post(url.Values{"_method": []string{"PUT"}})
 	r.Equal(200, res.Code)
 	r.Equal("you put me!", res.Body.String())
 }
diff --git a/middleware/basicauth/basicauth_test.go b/middleware/basicauth/basicauth_test.go
index 2d5bd7eaf..2de6858bd 100644
--- a/middleware/basicauth/basicauth_test.go
+++ b/middleware/basicauth/basicauth_test.go
@@ -7,7 +7,7 @@ import (
 
 	"github.com/gobuffalo/buffalo"
 	"github.com/gobuffalo/buffalo/middleware/basicauth"
-	"github.com/markbates/willie"
+	"github.com/gobuffalo/httptest"
 	"github.com/stretchr/testify/require"
 )
 
@@ -27,25 +27,25 @@ func app() *buffalo.App {
 func TestBasicAuth(t *testing.T) {
 	r := require.New(t)
 
-	w := willie.New(app())
+	w := httptest.New(app())
 
 	authfail := "invalid basic auth"
 
 	// missing authorization
-	res := w.Request("/").Get()
+	res := w.HTML("/").Get()
 	r.Equal(401, res.Code)
 	r.Contains(res.Header().Get("WWW-Authenticate"), `Basic realm="Basic Authentication"`)
 	r.Contains(res.Body.String(), "Unauthorized")
 
 	// bad header value, not Basic
-	req := w.Request("/")
+	req := w.HTML("/")
 	req.Headers["Authorization"] = "badcreds"
 	res = req.Get()
 	r.Equal(401, res.Code)
 	r.Contains(res.Body.String(), "Unauthorized")
 
 	// bad cred values
-	req = w.Request("/")
+	req = w.HTML("/")
 	req.Headers["Authorization"] = "bad creds"
 	res = req.Get()
 	r.Equal(500, res.Code)
@@ -54,7 +54,7 @@ func TestBasicAuth(t *testing.T) {
 	creds := base64.StdEncoding.EncodeToString([]byte("badcredvalue"))
 
 	// invalid cred values in authorization
-	req = w.Request("/")
+	req = w.HTML("/")
 	req.Headers["Authorization"] = fmt.Sprintf("Basic %s", creds)
 	res = req.Get()
 	r.Equal(500, res.Code)
@@ -63,7 +63,7 @@ func TestBasicAuth(t *testing.T) {
 	creds = base64.StdEncoding.EncodeToString([]byte("tester:pass123"))
 
 	// valid cred values
-	req = w.Request("/")
+	req = w.HTML("/")
 	req.Headers["Authorization"] = fmt.Sprintf("Basic %s", creds)
 	res = req.Get()
 	r.Equal(200, res.Code)
diff --git a/middleware/content_type_test.go b/middleware/content_type_test.go
index 5dd2e9b36..c378899dd 100644
--- a/middleware/content_type_test.go
+++ b/middleware/content_type_test.go
@@ -6,8 +6,8 @@ import (
 	"github.com/gobuffalo/buffalo"
 	"github.com/gobuffalo/buffalo/middleware"
 	"github.com/gobuffalo/buffalo/render"
+	"github.com/gobuffalo/httptest"
 	"github.com/gobuffalo/x/httpx"
-	"github.com/markbates/willie"
 	"github.com/stretchr/testify/require"
 )
 
@@ -24,11 +24,11 @@ func ctApp() *buffalo.App {
 func Test_SetContentType(t *testing.T) {
 	r := require.New(t)
 
-	w := willie.New(ctApp())
-	res := w.Request("/set").Get()
+	w := httptest.New(ctApp())
+	res := w.HTML("/set").Get()
 	r.Equal("application/json", res.Body.String())
 
-	req := w.Request("/set")
+	req := w.HTML("/set")
 	req.Headers["Content-Type"] = "text/plain"
 
 	res = req.Get()
@@ -38,11 +38,11 @@ func Test_SetContentType(t *testing.T) {
 func Test_AddContentType(t *testing.T) {
 	r := require.New(t)
 
-	w := willie.New(ctApp())
-	res := w.Request("/add").Get()
+	w := httptest.New(ctApp())
+	res := w.HTML("/add").Get()
 	r.Equal("application/json", res.Body.String())
 
-	req := w.Request("/add")
+	req := w.HTML("/add")
 	req.Headers["Content-Type"] = "text/plain"
 
 	res = req.Get()
diff --git a/middleware/csrf/csrf_test.go b/middleware/csrf/csrf_test.go
index 5d57265a0..1a41194af 100644
--- a/middleware/csrf/csrf_test.go
+++ b/middleware/csrf/csrf_test.go
@@ -8,7 +8,7 @@ import (
 	"github.com/gobuffalo/buffalo/middleware/csrf"
 	"github.com/gobuffalo/buffalo/render"
 	"github.com/gobuffalo/envy"
-	"github.com/markbates/willie"
+	"github.com/gobuffalo/httptest"
 	"github.com/stretchr/testify/require"
 )
 
@@ -40,18 +40,18 @@ func ctCSRFApp() *buffalo.App {
 func Test_CSRFOnIdempotentAction(t *testing.T) {
 	r := require.New(t)
 
-	w := willie.New(ctCSRFApp())
-	res := w.Request("/csrf").Get()
+	w := httptest.New(ctCSRFApp())
+	res := w.HTML("/csrf").Get()
 	r.Equal(200, res.Code)
 }
 
 func Test_CSRFOnJSONRequest(t *testing.T) {
 	r := require.New(t)
 
-	w := willie.New(ctCSRFApp())
+	w := httptest.New(ctCSRFApp())
 
 	// Test missing token case
-	res := w.Request("/csrf").Post("")
+	res := w.HTML("/csrf").Post("")
 	r.Equal(500, res.Code)
 	r.Contains(res.Body.String(), "CSRF token not found in request")
 
@@ -62,36 +62,36 @@ func Test_CSRFOnJSONRequest(t *testing.T) {
 func Test_CSRFOnEditingAction(t *testing.T) {
 	r := require.New(t)
 
-	w := willie.New(ctCSRFApp())
+	w := httptest.New(ctCSRFApp())
 
 	// Test missing token case
-	res := w.Request("/csrf").Post("")
+	res := w.HTML("/csrf").Post("")
 	r.Equal(500, res.Code)
 	r.Contains(res.Body.String(), "CSRF token not found in request")
 
 	// Test provided bad token through Header case
-	req := w.Request("/csrf")
+	req := w.HTML("/csrf")
 	req.Headers["X-CSRF-Token"] = "test-token"
 	res = req.Post("")
 	r.Equal(500, res.Code)
 	r.Contains(res.Body.String(), "CSRF token not found in request")
 
 	// Test provided good token through Header case
-	res = w.Request("/csrf").Get()
+	res = w.HTML("/csrf").Get()
 	r.Equal(200, res.Code)
 	token := res.Body.String()
 
-	req = w.Request("/csrf")
+	req = w.HTML("/csrf")
 	req.Headers["X-CSRF-Token"] = token
 	res = req.Post("")
 	r.Equal(200, res.Code)
 
 	// Test provided good token through form case
-	res = w.Request("/csrf").Get()
+	res = w.HTML("/csrf").Get()
 	r.Equal(200, res.Code)
 	token = res.Body.String()
 
-	req = w.Request("/csrf")
+	req = w.HTML("/csrf")
 	res = req.Post(csrfForm{AuthenticityToken: token})
 	r.Equal(200, res.Code)
 }
diff --git a/middleware/i18n/i18n_test.go b/middleware/i18n/i18n_test.go
index cc4bc1a70..524d57406 100644
--- a/middleware/i18n/i18n_test.go
+++ b/middleware/i18n/i18n_test.go
@@ -9,8 +9,8 @@ import (
 	"github.com/gobuffalo/buffalo"
 	"github.com/gobuffalo/buffalo/middleware/i18n"
 	"github.com/gobuffalo/buffalo/render"
+	"github.com/gobuffalo/httptest"
 	"github.com/gobuffalo/packr"
-	"github.com/markbates/willie"
 	"github.com/stretchr/testify/require"
 )
 
@@ -84,16 +84,16 @@ func app() *buffalo.App {
 func Test_i18n(t *testing.T) {
 	r := require.New(t)
 
-	w := willie.New(app())
-	res := w.Request("/").Get()
+	w := httptest.New(app())
+	res := w.HTML("/").Get()
 	r.Equal("Hello, World!", strings.TrimSpace(res.Body.String()))
 }
 
 func Test_i18n_fr(t *testing.T) {
 	r := require.New(t)
 
-	w := willie.New(app())
-	req := w.Request("/")
+	w := httptest.New(app())
+	req := w.HTML("/")
 	// Set language as "french"
 	req.Headers["Accept-Language"] = "fr-fr"
 	res := req.Get()
@@ -103,16 +103,16 @@ func Test_i18n_fr(t *testing.T) {
 func Test_i18n_plural(t *testing.T) {
 	r := require.New(t)
 
-	w := willie.New(app())
-	res := w.Request("/plural").Get()
+	w := httptest.New(app())
+	res := w.HTML("/plural").Get()
 	r.Equal("Hello, alone!\nHello, 5 people!", strings.TrimSpace(res.Body.String()))
 }
 
 func Test_i18n_plural_fr(t *testing.T) {
 	r := require.New(t)
 
-	w := willie.New(app())
-	req := w.Request("/plural")
+	w := httptest.New(app())
+	req := w.HTML("/plural")
 	// Set language as "french"
 	req.Headers["Accept-Language"] = "fr-fr"
 	res := req.Get()
@@ -122,16 +122,16 @@ func Test_i18n_plural_fr(t *testing.T) {
 func Test_i18n_format(t *testing.T) {
 	r := require.New(t)
 
-	w := willie.New(app())
-	res := w.Request("/format").Get()
+	w := httptest.New(app())
+	res := w.HTML("/format").Get()
 	r.Equal("Hello Mark!\n\n\t* Mr. Mark Bates\n\n\t* Mr. Chuck Berry\n", res.Body.String())
 }
 
 func Test_i18n_format_fr(t *testing.T) {
 	r := require.New(t)
 
-	w := willie.New(app())
-	req := w.Request("/format")
+	w := httptest.New(app())
+	req := w.HTML("/format")
 	// Set language as "french"
 	req.Headers["Accept-Language"] = "fr-fr"
 	res := req.Get()
@@ -141,9 +141,9 @@ func Test_i18n_format_fr(t *testing.T) {
 func Test_i18n_Localized_View(t *testing.T) {
 	r := require.New(t)
 
-	w := willie.New(app())
+	w := httptest.New(app())
 	// Test with complex Accept-Language
-	req := w.Request("/localized")
+	req := w.HTML("/localized")
 	req.Headers["Accept-Language"] = "en-UK,en-US;q=0.5"
 	res := req.Get()
 	r.Equal("Hello!", strings.TrimSpace(res.Body.String()))
@@ -159,7 +159,7 @@ func Test_i18n_Localized_View(t *testing.T) {
 	r.Equal("Default", strings.TrimSpace(res.Body.String()))
 
 	// Test i18n disabled
-	req = w.Request("/localized-disabled")
+	req = w.HTML("/localized-disabled")
 	req.Headers["Accept-Language"] = "en-UK,en-US;q=0.5"
 	res = req.Get()
 	r.Equal("Default", strings.TrimSpace(res.Body.String()))
@@ -168,28 +168,28 @@ func Test_i18n_Localized_View(t *testing.T) {
 func Test_i18n_collision(t *testing.T) {
 	r := require.New(t)
 
-	w := willie.New(app())
-	res := w.Request("/collision").Get()
+	w := httptest.New(app())
+	res := w.HTML("/collision").Get()
 	r.Equal("Collision OK", strings.TrimSpace(res.Body.String()))
 }
 
 func Test_i18n_availableLanguages(t *testing.T) {
 	r := require.New(t)
 
-	w := willie.New(app())
-	res := w.Request("/languages-list").Get()
+	w := httptest.New(app())
+	res := w.HTML("/languages-list").Get()
 	r.Equal("[\"en-us\",\"fr-fr\"]", strings.TrimSpace(res.Body.String()))
 }
 
 func Test_i18n_URL_prefix(t *testing.T) {
 	r := require.New(t)
 
-	w := willie.New(app())
-	req := w.Request("/fr/index")
+	w := httptest.New(app())
+	req := w.HTML("/fr/index")
 	res := req.Get()
 	r.Equal("Bonjour à tous !", strings.TrimSpace(res.Body.String()))
 
-	req = w.Request("/en/index")
+	req = w.HTML("/en/index")
 	res = req.Get()
 	r.Equal("Hello, World!", strings.TrimSpace(res.Body.String()))
 }
@@ -197,8 +197,8 @@ func Test_i18n_URL_prefix(t *testing.T) {
 func Test_Refresh(t *testing.T) {
 	r := require.New(t)
 
-	w := willie.New(app())
-	req := w.Request("/refresh")
+	w := httptest.New(app())
+	req := w.HTML("/refresh")
 	res := req.Get()
 	r.Equal("success: Language changed!#success: Langue modifiée !#", strings.TrimSpace(res.Body.String()))
 }
diff --git a/middleware/param_logger_test.go b/middleware/param_logger_test.go
index 97e4d8865..ab42e5e0e 100644
--- a/middleware/param_logger_test.go
+++ b/middleware/param_logger_test.go
@@ -6,7 +6,7 @@ import (
 
 	"github.com/gobuffalo/buffalo"
 	"github.com/gobuffalo/buffalo/middleware"
-	"github.com/markbates/willie"
+	"github.com/gobuffalo/httptest"
 	"github.com/sirupsen/logrus"
 	"github.com/stretchr/testify/require"
 )
@@ -56,7 +56,7 @@ func Test_Logger(t *testing.T) {
 	app.GET("/", emptyHandler)
 	app.POST("/", emptyHandler)
 
-	wi := willie.New(app)
+	wi := httptest.New(app)
 	wi.HTML("/?param=value").Get()
 
 	r.Contains(lastEntry.Data["params"], "{\"param\":[\"value\"]}")
diff --git a/middleware/tokenauth/tokenauth_test.go b/middleware/tokenauth/tokenauth_test.go
index 8c14a8b02..927507765 100644
--- a/middleware/tokenauth/tokenauth_test.go
+++ b/middleware/tokenauth/tokenauth_test.go
@@ -11,10 +11,10 @@ import (
 	"github.com/dgrijalva/jwt-go"
 	"github.com/gobuffalo/buffalo/middleware/tokenauth"
 	"github.com/gobuffalo/envy"
+	"github.com/gobuffalo/httptest"
 	"github.com/pkg/errors"
 
 	"github.com/gobuffalo/buffalo"
-	"github.com/markbates/willie"
 	"github.com/stretchr/testify/require"
 )
 
@@ -75,14 +75,14 @@ func appECDSA() *buffalo.App {
 // Test HMAC
 func TestTokenHMAC(t *testing.T) {
 	r := require.New(t)
-	w := willie.New(appHMAC())
+	w := httptest.New(appHMAC())
 
 	// Missing Authorization
-	res := w.Request("/").Get()
+	res := w.HTML("/").Get()
 	r.Equal(http.StatusUnauthorized, res.Code)
 
 	// invalid token
-	req := w.Request("/")
+	req := w.HTML("/")
 	req.Headers["Authorization"] = "badcreds"
 	res = req.Get()
 	r.Equal(http.StatusUnauthorized, res.Code)
@@ -113,14 +113,14 @@ func TestTokenHMAC(t *testing.T) {
 // Test RSA
 func TestTokenRSA(t *testing.T) {
 	r := require.New(t)
-	w := willie.New(appRSA())
+	w := httptest.New(appRSA())
 
 	// Missing Authorization
-	res := w.Request("/").Get()
+	res := w.HTML("/").Get()
 	r.Equal(http.StatusUnauthorized, res.Code)
 
 	// invalid token
-	req := w.Request("/")
+	req := w.HTML("/")
 	req.Headers["Authorization"] = "badcreds"
 	res = req.Get()
 	r.Equal(http.StatusUnauthorized, res.Code)
@@ -162,14 +162,14 @@ func TestTokenRSA(t *testing.T) {
 // Test ECDSA
 func TestTokenECDSA(t *testing.T) {
 	r := require.New(t)
-	w := willie.New(appECDSA())
+	w := httptest.New(appECDSA())
 
 	// Missing Authorization
-	res := w.Request("/").Get()
+	res := w.HTML("/").Get()
 	r.Equal(http.StatusUnauthorized, res.Code)
 
 	// invalid token
-	req := w.Request("/")
+	req := w.HTML("/")
 	req.Headers["Authorization"] = "badcreds"
 	res = req.Get()
 	r.Equal(http.StatusUnauthorized, res.Code)
@@ -210,14 +210,14 @@ func TestTokenECDSA(t *testing.T) {
 // Test RSAPSS
 func TestTokenRSAPSS(t *testing.T) {
 	r := require.New(t)
-	w := willie.New(appRSAPSS())
+	w := httptest.New(appRSAPSS())
 
 	// Missing Authorization
-	res := w.Request("/").Get()
+	res := w.HTML("/").Get()
 	r.Equal(http.StatusUnauthorized, res.Code)
 
 	// invalid token
-	req := w.Request("/")
+	req := w.HTML("/")
 	req.Headers["Authorization"] = "badcreds"
 	res = req.Get()
 	r.Equal(http.StatusUnauthorized, res.Code)
diff --git a/middleware_test.go b/middleware_test.go
index 42553195e..5decc706b 100644
--- a/middleware_test.go
+++ b/middleware_test.go
@@ -4,7 +4,7 @@ import (
 	"testing"
 
 	"github.com/gobuffalo/buffalo/render"
-	"github.com/markbates/willie"
+	"github.com/gobuffalo/httptest"
 	"github.com/stretchr/testify/require"
 )
 
@@ -28,8 +28,8 @@ func Test_App_Use(t *testing.T) {
 		return nil
 	})
 
-	w := willie.New(a)
-	w.Request("/").Get()
+	w := httptest.New(a)
+	w.HTML("/").Get()
 	r.Len(log, 3)
 	r.Equal([]string{"start", "handler", "end"}, log)
 }
@@ -64,8 +64,8 @@ func Test_Middleware_Replace(t *testing.T) {
 		return nil
 	})
 
-	w := willie.New(a)
-	w.Request("/").Get()
+	w := httptest.New(a)
+	w.HTML("/").Get()
 	r.Len(log, 3)
 	r.Equal([]string{"m2 start", "handler", "m2 end"}, log)
 }
@@ -109,14 +109,14 @@ func Test_Middleware_Skip(t *testing.T) {
 
 	a.Middleware.Skip(mw2, h2)
 
-	w := willie.New(a)
+	w := httptest.New(a)
 
-	w.Request("/h2").Get()
+	w.HTML("/h2").Get()
 	r.Len(log, 3)
 	r.Equal([]string{"mw1 start", "h2", "mw1 end"}, log)
 
 	log = []string{}
-	w.Request("/h1").Get()
+	w.HTML("/h1").Get()
 	r.Len(log, 5)
 	r.Equal([]string{"mw1 start", "mw2 start", "h1", "mw2 end", "mw1 end"}, log)
 }
@@ -159,24 +159,24 @@ func Test_Middleware_Skip_Resource(t *testing.T) {
 	// fmt.Println("set up skip")
 	g.Middleware.Skip(mw1, ur.Show)
 
-	w := willie.New(a)
+	w := httptest.New(a)
 
 	// fmt.Println("make autos call")
 	log = []string{}
-	res := w.Request("/autos/1").Get()
+	res := w.HTML("/autos/1").Get()
 	r.Len(log, 2)
 	r.Equal("show", res.Body.String())
 
 	// fmt.Println("make list call")
 	log = []string{}
-	res = w.Request("/cars").Get()
+	res = w.HTML("/cars").Get()
 	r.Len(log, 2)
 	r.Equal([]string{"mw1 start", "mw1 end"}, log)
 	r.Equal("list", res.Body.String())
 
 	// fmt.Println("make show call")
 	log = []string{}
-	res = w.Request("/cars/1").Get()
+	res = w.HTML("/cars/1").Get()
 	r.Len(log, 0)
 	r.Equal("show", res.Body.String())
 
diff --git a/not_found_test.go b/not_found_test.go
index 2561e16d7..28d985464 100644
--- a/not_found_test.go
+++ b/not_found_test.go
@@ -4,7 +4,7 @@ import (
 	"encoding/json"
 	"testing"
 
-	"github.com/markbates/willie"
+	"github.com/gobuffalo/httptest"
 	"github.com/stretchr/testify/require"
 )
 
@@ -15,8 +15,8 @@ func Test_App_Dev_NotFound(t *testing.T) {
 	a.Env = "development"
 	a.GET("/foo", func(c Context) error { return nil })
 
-	w := willie.New(a)
-	res := w.Request("/bad").Get()
+	w := httptest.New(a)
+	res := w.HTML("/bad").Get()
 
 	body := res.Body.String()
 	r.Contains(body, "404 - ERROR!")
@@ -31,7 +31,7 @@ func Test_App_Dev_NotFound_JSON(t *testing.T) {
 	a.Env = "development"
 	a.GET("/foo", func(c Context) error { return nil })
 
-	w := willie.New(a)
+	w := httptest.New(a)
 	res := w.JSON("/bad").Get()
 	r.Equal(404, res.Code)
 
@@ -52,8 +52,8 @@ func Test_App_Override_NotFound(t *testing.T) {
 	}
 	a.GET("/foo", func(c Context) error { return nil })
 
-	w := willie.New(a)
-	res := w.Request("/bad").Get()
+	w := httptest.New(a)
+	res := w.HTML("/bad").Get()
 	r.Equal(404, res.Code)
 
 	body := res.Body.String()
diff --git a/render/auto_test.go b/render/auto_test.go
index 3dd944db7..e7a1b92c7 100644
--- a/render/auto_test.go
+++ b/render/auto_test.go
@@ -1,7 +1,6 @@
 package render_test
 
 import (
-	"net/http/httptest"
 	"os"
 	"path/filepath"
 	"strings"
@@ -9,8 +8,8 @@ import (
 
 	"github.com/gobuffalo/buffalo"
 	"github.com/gobuffalo/buffalo/render"
+	"github.com/gobuffalo/httptest"
 	"github.com/gobuffalo/packr"
-	"github.com/markbates/willie"
 	"github.com/stretchr/testify/require"
 )
 
@@ -47,7 +46,7 @@ func Test_Auto_JSON(t *testing.T) {
 		return c.Render(200, render.Auto(c, []string{"Honda", "Toyota", "Ford", "Chevy"}))
 	})
 
-	w := willie.New(app)
+	w := httptest.New(app)
 
 	res := w.JSON("/cars").Get()
 	r.Equal(`["Honda","Toyota","Ford","Chevy"]`, strings.TrimSpace(res.Body.String()))
@@ -61,7 +60,7 @@ func Test_Auto_XML(t *testing.T) {
 		return c.Render(200, render.Auto(c, []string{"Honda", "Toyota", "Ford", "Chevy"}))
 	})
 
-	w := willie.New(app)
+	w := httptest.New(app)
 
 	res := w.XML("/cars").Get()
 	r.Equal("<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<string>Honda</string>\n<string>Toyota</string>\n<string>Ford</string>\n<string>Chevy</string>", strings.TrimSpace(res.Body.String()))
@@ -79,7 +78,7 @@ func Test_Auto_HTML_List(t *testing.T) {
 			}))
 		})
 
-		w := willie.New(app)
+		w := httptest.New(app)
 		res := w.HTML("/cars").Get()
 
 		r.Contains(res.Body.String(), "INDEX: 2")
@@ -105,7 +104,7 @@ func Test_Auto_HTML_List_Plural(t *testing.T) {
 			}))
 		})
 
-		w := willie.New(app)
+		w := httptest.New(app)
 		res := w.HTML("/people").Get()
 
 		r.Contains(res.Body.String(), "INDEX: 2")
@@ -131,7 +130,7 @@ func Test_Auto_HTML_List_Plural_MultiWord(t *testing.T) {
 			}))
 		})
 
-		w := willie.New(app)
+		w := httptest.New(app)
 		res := w.HTML("/room_providers").Get()
 
 		r.Contains(res.Body.String(), "INDEX: 2")
@@ -148,7 +147,7 @@ func Test_Auto_HTML_Show(t *testing.T) {
 			return c.Render(200, e.Auto(c, Car{Name: "Honda"}))
 		})
 
-		w := willie.New(app)
+		w := httptest.New(app)
 		res := w.HTML("/cars/1").Get()
 		r.Contains(res.Body.String(), "Show: Honda")
 	})
@@ -164,7 +163,7 @@ func Test_Auto_HTML_New(t *testing.T) {
 			return c.Render(200, e.Auto(c, Car{Name: "Honda"}))
 		})
 
-		w := willie.New(app)
+		w := httptest.New(app)
 		res := w.HTML("/cars/new").Get()
 		r.Contains(res.Body.String(), "New: Honda")
 	})
@@ -180,7 +179,7 @@ func Test_Auto_HTML_Create(t *testing.T) {
 			return c.Render(201, e.Auto(c, Car{Name: "Honda"}))
 		})
 
-		w := willie.New(app)
+		w := httptest.New(app)
 		res := w.HTML("/cars").Post(nil)
 		r.Contains(res.Body.String(), "New: Honda")
 	})
@@ -198,7 +197,7 @@ func Test_Auto_HTML_Create_Redirect(t *testing.T) {
 		}))
 	})
 
-	w := willie.New(app)
+	w := httptest.New(app)
 	res := w.HTML("/cars").Post(nil)
 	r.Equal("/cars/1", res.Location())
 	r.Equal(302, res.Code)
@@ -216,7 +215,7 @@ func Test_Auto_HTML_Create_Redirect_Error(t *testing.T) {
 			return c.Render(422, e.Auto(c, b))
 		})
 
-		w := willie.New(app)
+		w := httptest.New(app)
 		res := w.HTML("/cars").Post(nil)
 		r.Equal(422, res.Code)
 		r.Contains(res.Body.String(), "Create: Honda")
@@ -233,7 +232,7 @@ func Test_Auto_HTML_Edit(t *testing.T) {
 			return c.Render(200, e.Auto(c, Car{Name: "Honda"}))
 		})
 
-		w := willie.New(app)
+		w := httptest.New(app)
 		res := w.HTML("/cars/1/edit").Get()
 		r.Contains(res.Body.String(), "Edit: Honda")
 	})
@@ -249,7 +248,7 @@ func Test_Auto_HTML_Update(t *testing.T) {
 			return c.Render(200, e.Auto(c, Car{Name: "Honda"}))
 		})
 
-		w := willie.New(app)
+		w := httptest.New(app)
 		res := w.HTML("/cars/1").Put(nil)
 
 		r.Contains(res.Body.String(), "Update: Honda")
@@ -269,7 +268,7 @@ func Test_Auto_HTML_Update_Redirect(t *testing.T) {
 		return c.Render(200, render.Auto(c, b))
 	})
 
-	w := willie.New(app)
+	w := httptest.New(app)
 	res := w.HTML("/cars/1").Put(nil)
 	r.Equal("/cars/1", res.Location())
 	r.Equal(302, res.Code)
@@ -288,7 +287,7 @@ func Test_Auto_HTML_Update_Redirect_Error(t *testing.T) {
 			return c.Render(422, e.Auto(c, b))
 		})
 
-		w := willie.New(app)
+		w := httptest.New(app)
 		res := w.HTML("/cars/1").Put(nil)
 		r.Equal(422, res.Code)
 		r.Contains(res.Body.String(), "Update: Honda")
@@ -308,7 +307,7 @@ func Test_Auto_HTML_Destroy_Redirect(t *testing.T) {
 		return c.Render(200, render.Auto(c, b))
 	})
 
-	w := willie.New(app)
+	w := httptest.New(app)
 	res := w.HTML("/cars/1").Delete()
 	r.Equal("/cars", res.Location())
 	r.Equal(302, res.Code)
diff --git a/route_info_test.go b/route_info_test.go
index 26f0a05b1..1ea695a25 100644
--- a/route_info_test.go
+++ b/route_info_test.go
@@ -5,7 +5,7 @@ import (
 	"testing"
 
 	"github.com/gobuffalo/buffalo/render"
-	"github.com/markbates/willie"
+	"github.com/gobuffalo/httptest"
 	"github.com/stretchr/testify/require"
 )
 
@@ -21,7 +21,7 @@ func Test_RouteInfo_ServeHTTP_SQL_Error(t *testing.T) {
 		return sql.ErrNoRows
 	})
 
-	w := willie.New(app)
+	w := httptest.New(app)
 
 	res := w.HTML("/good").Get()
 	r.Equal(200, res.Code)
diff --git a/router_test.go b/router_test.go
index 158536f78..f4b0d9484 100644
--- a/router_test.go
+++ b/router_test.go
@@ -4,16 +4,15 @@ import (
 	"fmt"
 	"io/ioutil"
 	"net/http"
-	"net/http/httptest"
 	"path"
 	"path/filepath"
 	"strings"
 	"testing"
 
 	"github.com/gobuffalo/buffalo/render"
+	"github.com/gobuffalo/httptest"
 	"github.com/gobuffalo/packr"
 	"github.com/gorilla/mux"
-	"github.com/markbates/willie"
 	"github.com/stretchr/testify/require"
 )
 
@@ -62,7 +61,7 @@ func otherTestApp() *App {
 
 func Test_MethodNotFoundError(t *testing.T) {
 	r := require.New(t)
-	w := willie.New(testApp())
+	w := httptest.New(testApp())
 	res := w.HTML("/bar").Post(nil)
 	r.Equal(405, res.Code)
 	r.Contains(res.Body.String(), "my custom 405")
@@ -272,8 +271,8 @@ func Test_Router_Group(t *testing.T) {
 		return c.Render(201, nil)
 	})
 
-	w := willie.New(a)
-	res := w.Request("/api/v1/users").Get()
+	w := httptest.New(a)
+	res := w.HTML("/api/v1/users").Get()
 	r.Equal(201, res.Code)
 }
 
@@ -290,8 +289,8 @@ func Test_Router_Group_on_Group(t *testing.T) {
 		return c.Render(420, nil)
 	})
 
-	w := willie.New(a)
-	res := w.Request("/api/v1/foo/bar").Get()
+	w := httptest.New(a)
+	res := w.HTML("/api/v1/foo/bar").Get()
 	r.Equal(420, res.Code)
 }
 
@@ -313,8 +312,8 @@ func Test_Router_Group_Middleware(t *testing.T) {
 
 func Test_Router_Redirect(t *testing.T) {
 	r := require.New(t)
-	w := willie.New(testApp())
-	res := w.Request("/foo").Get()
+	w := httptest.New(testApp())
+	res := w.HTML("/foo").Get()
 	r.Equal(301, res.Code)
 	r.Equal("/bar", res.Location())
 }
@@ -332,8 +331,8 @@ func Test_Router_ServeFiles(t *testing.T) {
 	a := New(Options{})
 	a.ServeFiles("/assets", http.Dir(filepath.Dir(tmpFile.Name())))
 
-	w := willie.New(a)
-	res := w.Request("/assets/%s", filepath.Base(tmpFile.Name())).Get()
+	w := httptest.New(a)
+	res := w.HTML("/assets/%s", filepath.Base(tmpFile.Name())).Get()
 
 	r.Equal(200, res.Code)
 	r.Equal(af, res.Body.Bytes())
@@ -387,8 +386,8 @@ func Test_App_NamedRoutes(t *testing.T) {
 	a.Resource("/car", carsResource)
 	a.Resource("/resources", resourcesResource)
 
-	w := willie.New(a)
-	res := w.Request("/").Get()
+	w := httptest.New(a)
+	res := w.HTML("/").Get()
 
 	r.Equal(200, res.Code)
 	r.Contains(res.Body.String(), "1. /")
@@ -423,8 +422,8 @@ func Test_App_NamedRoutes_MissingParameter(t *testing.T) {
 	}
 
 	a.GET("/users/{user_id}", sampleHandler)
-	w := willie.New(a)
-	res := w.Request("/users/1").Get()
+	w := httptest.New(a)
+	res := w.HTML("/users/1").Get()
 
 	r.Equal(500, res.Code)
 	r.Contains(res.Body.String(), "missing parameters for /users/{user_id}")
@@ -662,8 +661,8 @@ func Test_CatchAll_Route(t *testing.T) {
 		return c.Render(200, rr.String(name))
 	})
 
-	w := willie.New(a)
-	res := w.Request("/john").Get()
+	w := httptest.New(a)
+	res := w.HTML("/john").Get()
 
 	r.Contains(res.Body.String(), "john")
 }
@@ -703,8 +702,8 @@ func Test_Router_Matches_Trailing_Slash(t *testing.T) {
 				return c.Render(200, render.String(c.Request().URL.Path))
 			})
 
-			w := willie.New(app)
-			res := w.Request(tt.browser).Get()
+			w := httptest.New(app)
+			res := w.HTML(tt.browser).Get()
 
 			r.Equal(200, res.Code)
 			r.Equal(tt.expected, res.Body.String())
diff --git a/wrappers_test.go b/wrappers_test.go
index 8179b3b58..b0522f103 100644
--- a/wrappers_test.go
+++ b/wrappers_test.go
@@ -2,11 +2,10 @@ package buffalo
 
 import (
 	"net/http"
-	"net/http/httptest"
 	"testing"
 
 	"github.com/gobuffalo/buffalo/render"
-	"github.com/markbates/willie"
+	"github.com/gobuffalo/httptest"
 	"github.com/stretchr/testify/require"
 )
 
@@ -18,8 +17,8 @@ func Test_WrapHandlerFunc(t *testing.T) {
 		res.Write([]byte("hello"))
 	}))
 
-	w := willie.New(a)
-	res := w.Request("/foo").Get()
+	w := httptest.New(a)
+	res := w.HTML("/foo").Get()
 
 	r.Equal("hello", res.Body.String())
 }
@@ -32,8 +31,8 @@ func Test_WrapHandler(t *testing.T) {
 		res.Write([]byte("hello"))
 	})))
 
-	w := willie.New(a)
-	res := w.Request("/foo").Get()
+	w := httptest.New(a)
+	res := w.HTML("/foo").Get()
 
 	r.Equal("hello", res.Body.String())
 }