aboutsummaryrefslogtreecommitdiff
path: root/src/dict2rest/vendor/github.com/justinas/alice
diff options
context:
space:
mode:
Diffstat (limited to 'src/dict2rest/vendor/github.com/justinas/alice')
-rw-r--r--src/dict2rest/vendor/github.com/justinas/alice/.travis.yml11
-rw-r--r--src/dict2rest/vendor/github.com/justinas/alice/LICENSE20
-rw-r--r--src/dict2rest/vendor/github.com/justinas/alice/README.md92
-rw-r--r--src/dict2rest/vendor/github.com/justinas/alice/chain.go119
-rw-r--r--src/dict2rest/vendor/github.com/justinas/alice/chain_test.go144
5 files changed, 386 insertions, 0 deletions
diff --git a/src/dict2rest/vendor/github.com/justinas/alice/.travis.yml b/src/dict2rest/vendor/github.com/justinas/alice/.travis.yml
new file mode 100644
index 0000000..9398694
--- /dev/null
+++ b/src/dict2rest/vendor/github.com/justinas/alice/.travis.yml
@@ -0,0 +1,11 @@
+language: go
+
+install:
+ - go get github.com/stretchr/testify/assert
+
+go:
+ - 1.1
+ - 1.2
+ - 1.3
+ - 1.4
+ - tip
diff --git a/src/dict2rest/vendor/github.com/justinas/alice/LICENSE b/src/dict2rest/vendor/github.com/justinas/alice/LICENSE
new file mode 100644
index 0000000..0d0d352
--- /dev/null
+++ b/src/dict2rest/vendor/github.com/justinas/alice/LICENSE
@@ -0,0 +1,20 @@
+The MIT License (MIT)
+
+Copyright (c) 2014 Justinas Stankevicius
+
+Permission is hereby granted, free of charge, to any person obtaining a copy of
+this software and associated documentation files (the "Software"), to deal in
+the Software without restriction, including without limitation the rights to
+use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
+the Software, and to permit persons to whom the Software is furnished to do so,
+subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in all
+copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
+FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
+COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
+IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
diff --git a/src/dict2rest/vendor/github.com/justinas/alice/README.md b/src/dict2rest/vendor/github.com/justinas/alice/README.md
new file mode 100644
index 0000000..88d2134
--- /dev/null
+++ b/src/dict2rest/vendor/github.com/justinas/alice/README.md
@@ -0,0 +1,92 @@
+# Alice
+
+[![Build Status](https://travis-ci.org/justinas/alice.svg?branch=master)](https://travis-ci.org/justinas/alice)
+
+Alice provides a convenient way to chain
+your HTTP middleware functions and the app handler.
+
+In short, it transforms
+
+ Middleware1(Middleware2(Middleware3(App)))
+
+to
+
+ alice.New(Middleware1, Middleware2, Middleware3).Then(App).
+
+### Why?
+
+None of the other middleware chaining solutions
+behaves exactly like Alice.
+Alice is as minimal as it gets:
+in essence, it's just a for loop that does the wrapping for you.
+
+Check out [this blog post](http://justinas.org/alice-painless-middleware-chaining-for-go/)
+for explanation how Alice is different from other chaining solutions.
+
+### Usage
+
+Your middleware constructors should have the form of
+
+ func (http.Handler) http.Handler
+
+Some middleware provide this out of the box.
+For ones that don't, it's trivial to write one yourself.
+
+```go
+func myStripPrefix(h http.Handler) http.Handler {
+ return http.StripPrefix("/old", h)
+}
+```
+
+This complete example shows the full power of Alice.
+
+```go
+package main
+
+import (
+ "net/http"
+ "time"
+
+ "github.com/PuerkitoBio/throttled"
+ "github.com/justinas/alice"
+ "github.com/justinas/nosurf"
+)
+
+func timeoutHandler(h http.Handler) http.Handler {
+ return http.TimeoutHandler(h, 1*time.Second, "timed out")
+}
+
+func myApp(w http.ResponseWriter, r *http.Request) {
+ w.Write([]byte("Hello world!"))
+}
+
+func main() {
+ th := throttled.Interval(throttled.PerSec(10), 1, &throttled.VaryBy{Path: true}, 50)
+ myHandler := http.HandlerFunc(myApp)
+
+ chain := alice.New(th.Throttle, timeoutHandler, nosurf.NewPure).Then(myHandler)
+ http.ListenAndServe(":8000", chain)
+}
+```
+
+Here, the request will pass [throttled](https://github.com/PuerkitoBio/throttled) first,
+then an http.TimeoutHandler we've set up,
+then [nosurf](https://github.com/justinas/nosurf)
+and will finally reach our handler.
+
+Note that Alice makes **no guarantees** for
+how one or another piece of middleware will behave.
+It executes all middleware sequentially so that if a
+piece of middleware were to stop the chain,
+the request will not reach the inner handlers.
+This is intentional behavior.
+
+Alice works with Go 1.0 and higher,
+but running tests requires at least Go 1.1.
+
+### Contributing
+
+0. Find an issue that bugs you / open a new one.
+1. Discuss.
+2. Branch off, commit, test.
+3. Make a pull request / attach the commits to the issue.
diff --git a/src/dict2rest/vendor/github.com/justinas/alice/chain.go b/src/dict2rest/vendor/github.com/justinas/alice/chain.go
new file mode 100644
index 0000000..d281ad3
--- /dev/null
+++ b/src/dict2rest/vendor/github.com/justinas/alice/chain.go
@@ -0,0 +1,119 @@
+// Package alice provides a convenient way to chain http handlers.
+package alice
+
+import "net/http"
+
+// A constructor for a piece of middleware.
+// Some middleware use this constructor out of the box,
+// so in most cases you can just pass somepackage.New
+type Constructor func(http.Handler) http.Handler
+
+// Chain acts as a list of http.Handler constructors.
+// Chain is effectively immutable:
+// once created, it will always hold
+// the same set of constructors in the same order.
+type Chain struct {
+ constructors []Constructor
+}
+
+// New creates a new chain,
+// memorizing the given list of middleware constructors.
+// New serves no other function,
+// constructors are only called upon a call to Then().
+func New(constructors ...Constructor) Chain {
+ c := Chain{}
+ c.constructors = append(c.constructors, constructors...)
+
+ return c
+}
+
+// Then chains the middleware and returns the final http.Handler.
+// New(m1, m2, m3).Then(h)
+// is equivalent to:
+// m1(m2(m3(h)))
+// When the request comes in, it will be passed to m1, then m2, then m3
+// and finally, the given handler
+// (assuming every middleware calls the following one).
+//
+// A chain can be safely reused by calling Then() several times.
+// stdStack := alice.New(ratelimitHandler, csrfHandler)
+// indexPipe = stdStack.Then(indexHandler)
+// authPipe = stdStack.Then(authHandler)
+// Note that constructors are called on every call to Then()
+// and thus several instances of the same middleware will be created
+// when a chain is reused in this way.
+// For proper middleware, this should cause no problems.
+//
+// Then() treats nil as http.DefaultServeMux.
+func (c Chain) Then(h http.Handler) http.Handler {
+ var final http.Handler
+ if h != nil {
+ final = h
+ } else {
+ final = http.DefaultServeMux
+ }
+
+ for i := len(c.constructors) - 1; i >= 0; i-- {
+ final = c.constructors[i](final)
+ }
+
+ return final
+}
+
+// ThenFunc works identically to Then, but takes
+// a HandlerFunc instead of a Handler.
+//
+// The following two statements are equivalent:
+// c.Then(http.HandlerFunc(fn))
+// c.ThenFunc(fn)
+//
+// ThenFunc provides all the guarantees of Then.
+func (c Chain) ThenFunc(fn http.HandlerFunc) http.Handler {
+ if fn == nil {
+ return c.Then(nil)
+ }
+ return c.Then(http.HandlerFunc(fn))
+}
+
+// Append extends a chain, adding the specified constructors
+// as the last ones in the request flow.
+//
+// Append returns a new chain, leaving the original one untouched.
+//
+// stdChain := alice.New(m1, m2)
+// extChain := stdChain.Append(m3, m4)
+// // requests in stdChain go m1 -> m2
+// // requests in extChain go m1 -> m2 -> m3 -> m4
+func (c Chain) Append(constructors ...Constructor) Chain {
+ newCons := make([]Constructor, len(c.constructors)+len(constructors))
+ copy(newCons, c.constructors)
+ copy(newCons[len(c.constructors):], constructors)
+
+ newChain := New(newCons...)
+ return newChain
+}
+
+// Extend extends a chain by adding the specified chain
+// as the last one in the request flow.
+//
+// Extend returns a new chain, leaving the original one untouched.
+//
+// stdChain := alice.New(m1, m2)
+// ext1Chain := alice.New(m3, m4)
+// ext2Chain := stdChain.Extend(ext1Chain)
+// // requests in stdChain go m1 -> m2
+// // requests in ext1Chain go m3 -> m4
+// // requests in ext2Chain go m1 -> m2 -> m3 -> m4
+//
+// Another example:
+// aHtmlAfterNosurf := alice.New(m2)
+// aHtml := alice.New(m1, func(h http.Handler) http.Handler {
+// csrf := nosurf.New(h)
+// csrf.SetFailureHandler(aHtmlAfterNosurf.ThenFunc(csrfFail))
+// return csrf
+// }).Extend(aHtmlAfterNosurf)
+// // requests to aHtml hitting nosurfs success handler go m1 -> nosurf -> m2 -> target-handler
+// // requests to aHtml hitting nosurfs failure handler go m1 -> nosurf -> m2 -> csrfFail
+func (c Chain) Extend(chain Chain) Chain {
+ return c.Append(chain.constructors...)
+}
diff --git a/src/dict2rest/vendor/github.com/justinas/alice/chain_test.go b/src/dict2rest/vendor/github.com/justinas/alice/chain_test.go
new file mode 100644
index 0000000..49c0470
--- /dev/null
+++ b/src/dict2rest/vendor/github.com/justinas/alice/chain_test.go
@@ -0,0 +1,144 @@
+// Package alice implements a middleware chaining solution.
+package alice
+
+import (
+ "net/http"
+ "net/http/httptest"
+ "reflect"
+ "testing"
+
+ "github.com/stretchr/testify/assert"
+)
+
+// A constructor for middleware
+// that writes its own "tag" into the RW and does nothing else.
+// Useful in checking if a chain is behaving in the right order.
+func tagMiddleware(tag string) Constructor {
+ return func(h http.Handler) http.Handler {
+ return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
+ w.Write([]byte(tag))
+ h.ServeHTTP(w, r)
+ })
+ }
+}
+
+// Not recommended (https://golang.org/pkg/reflect/#Value.Pointer),
+// but the best we can do.
+func funcsEqual(f1, f2 interface{}) bool {
+ val1 := reflect.ValueOf(f1)
+ val2 := reflect.ValueOf(f2)
+ return val1.Pointer() == val2.Pointer()
+}
+
+var testApp = http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
+ w.Write([]byte("app\n"))
+})
+
+// Tests creating a new chain
+func TestNew(t *testing.T) {
+ c1 := func(h http.Handler) http.Handler {
+ return nil
+ }
+ c2 := func(h http.Handler) http.Handler {
+ return http.StripPrefix("potato", nil)
+ }
+
+ slice := []Constructor{c1, c2}
+
+ chain := New(slice...)
+ assert.True(t, funcsEqual(chain.constructors[0], slice[0]))
+ assert.True(t, funcsEqual(chain.constructors[1], slice[1]))
+}
+
+func TestThenWorksWithNoMiddleware(t *testing.T) {
+ assert.NotPanics(t, func() {
+ chain := New()
+ final := chain.Then(testApp)
+
+ assert.True(t, funcsEqual(final, testApp))
+ })
+}
+
+func TestThenTreatsNilAsDefaultServeMux(t *testing.T) {
+ chained := New().Then(nil)
+ assert.Equal(t, chained, http.DefaultServeMux)
+}
+
+func TestThenFuncTreatsNilAsDefaultServeMux(t *testing.T) {
+ chained := New().ThenFunc(nil)
+ assert.Equal(t, chained, http.DefaultServeMux)
+}
+
+func TestThenOrdersHandlersRight(t *testing.T) {
+ t1 := tagMiddleware("t1\n")
+ t2 := tagMiddleware("t2\n")
+ t3 := tagMiddleware("t3\n")
+
+ chained := New(t1, t2, t3).Then(testApp)
+
+ w := httptest.NewRecorder()
+ r, err := http.NewRequest("GET", "/", nil)
+ if err != nil {
+ t.Fatal(err)
+ }
+
+ chained.ServeHTTP(w, r)
+
+ assert.Equal(t, w.Body.String(), "t1\nt2\nt3\napp\n")
+}
+
+func TestAppendAddsHandlersCorrectly(t *testing.T) {
+ chain := New(tagMiddleware("t1\n"), tagMiddleware("t2\n"))
+ newChain := chain.Append(tagMiddleware("t3\n"), tagMiddleware("t4\n"))
+
+ assert.Equal(t, len(chain.constructors), 2)
+ assert.Equal(t, len(newChain.constructors), 4)
+
+ chained := newChain.Then(testApp)
+
+ w := httptest.NewRecorder()
+ r, err := http.NewRequest("GET", "/", nil)
+ if err != nil {
+ t.Fatal(err)
+ }
+
+ chained.ServeHTTP(w, r)
+
+ assert.Equal(t, w.Body.String(), "t1\nt2\nt3\nt4\napp\n")
+}
+
+func TestAppendRespectsImmutability(t *testing.T) {
+ chain := New(tagMiddleware(""))
+ newChain := chain.Append(tagMiddleware(""))
+
+ assert.NotEqual(t, &chain.constructors[0], &newChain.constructors[0])
+}
+
+func TestExtendAddsHandlersCorrectly(t *testing.T) {
+ chain1 := New(tagMiddleware("t1\n"), tagMiddleware("t2\n"))
+ chain2 := New(tagMiddleware("t3\n"), tagMiddleware("t4\n"))
+ newChain := chain1.Extend(chain2)
+
+ assert.Equal(t, len(chain1.constructors), 2)
+ assert.Equal(t, len(chain2.constructors), 2)
+ assert.Equal(t, len(newChain.constructors), 4)
+
+ chained := newChain.Then(testApp)
+
+ w := httptest.NewRecorder()
+ r, err := http.NewRequest("GET", "/", nil)
+ if err != nil {
+ t.Fatal(err)
+ }
+
+ chained.ServeHTTP(w, r)
+
+ assert.Equal(t, w.Body.String(), "t1\nt2\nt3\nt4\napp\n")
+}
+
+func TestExtendRespectsImmutability(t *testing.T) {
+ chain := New(tagMiddleware(""))
+ newChain := chain.Extend(New(tagMiddleware("")))
+
+ assert.NotEqual(t, &chain.constructors[0], &newChain.constructors[0])
+}