From afff3f88851b5ea2fe1676871b0aebdc09367ba7 Mon Sep 17 00:00:00 2001 From: Harshavardhana Date: Mon, 31 Aug 2015 17:15:49 -0700 Subject: [PATCH] Revert "Enable controller to have CORS" This reverts commit f39ac24e9929d17b74200aecbbb0ff79e091e781. --- pkg/controller/router.go | 3 +- vendor.json | 7 - vendor/github.com/rs/cors/LICENSE | 19 -- vendor/github.com/rs/cors/README.md | 99 ------ vendor/github.com/rs/cors/bench_test.go | 88 ------ vendor/github.com/rs/cors/cors.go | 385 ------------------------ vendor/github.com/rs/cors/cors_test.go | 371 ----------------------- vendor/github.com/rs/cors/utils.go | 70 ----- vendor/github.com/rs/cors/utils_test.go | 70 ----- 9 files changed, 1 insertion(+), 1111 deletions(-) delete mode 100644 vendor/github.com/rs/cors/LICENSE delete mode 100644 vendor/github.com/rs/cors/README.md delete mode 100644 vendor/github.com/rs/cors/bench_test.go delete mode 100644 vendor/github.com/rs/cors/cors.go delete mode 100644 vendor/github.com/rs/cors/cors_test.go delete mode 100644 vendor/github.com/rs/cors/utils.go delete mode 100644 vendor/github.com/rs/cors/utils_test.go diff --git a/pkg/controller/router.go b/pkg/controller/router.go index 5a15f9074..db38bf241 100644 --- a/pkg/controller/router.go +++ b/pkg/controller/router.go @@ -21,7 +21,6 @@ import ( router "github.com/gorilla/mux" "github.com/minio/minio/pkg/rpc" - "github.com/rs/cors" ) // getRPCHandler rpc handler @@ -40,5 +39,5 @@ func getRPCHandler() http.Handler { // registerRPC - register rpc handlers func registerRPC(mux *router.Router, s *rpc.Server) http.Handler { mux.Handle("/rpc", s) - return cors.Default().Handler(mux) + return mux } diff --git a/vendor.json b/vendor.json index 01e81e1bb..d38687627 100755 --- a/vendor.json +++ b/vendor.json @@ -72,13 +72,6 @@ "revision": "ee386baecc113eef2b8945df429120a5aec319ef", "revisionTime": "2015-08-19T11:23:55-07:00" }, - { - "canonical": "github.com/rs/cors", - "comment": "", - "local": "vendor/github.com/rs/cors", - "revision": "eb527c8097e0f19a3ff7b253a3fe70545070f420", - "revisionTime": "2015-08-29T22:34:20-07:00" - }, { "canonical": "gopkg.in/check.v1", "comment": "", diff --git a/vendor/github.com/rs/cors/LICENSE b/vendor/github.com/rs/cors/LICENSE deleted file mode 100644 index d8e2df5a4..000000000 --- a/vendor/github.com/rs/cors/LICENSE +++ /dev/null @@ -1,19 +0,0 @@ -Copyright (c) 2014 Olivier Poitrey - -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/vendor/github.com/rs/cors/README.md b/vendor/github.com/rs/cors/README.md deleted file mode 100644 index 521d903d1..000000000 --- a/vendor/github.com/rs/cors/README.md +++ /dev/null @@ -1,99 +0,0 @@ -# Go CORS handler [![godoc](http://img.shields.io/badge/godoc-reference-blue.svg?style=flat)](https://godoc.org/github.com/rs/cors) [![license](http://img.shields.io/badge/license-MIT-red.svg?style=flat)](https://raw.githubusercontent.com/rs/cors/master/LICENSE) [![build](https://img.shields.io/travis/rs/cors.svg?style=flat)](https://travis-ci.org/rs/cors) - -CORS is a `net/http` handler implementing [Cross Origin Resource Sharing W3 specification](http://www.w3.org/TR/cors/) in Golang. - -## Getting Started - -After installing Go and setting up your [GOPATH](http://golang.org/doc/code.html#GOPATH), create your first `.go` file. We'll call it `server.go`. - -```go -package main - -import ( - "net/http" - - "github.com/rs/cors" -) - -func main() { - mux := http.NewServeMux() - mux.HandleFunc("/", func(w http.ResponseWriter, r *http.Request) { - w.Header().Set("Content-Type", "application/json") - w.Write([]byte("{\"hello\": \"world\"}")) - }) - - // cors.Default() setup the middleware with default options being - // all origins accepted with simple methods (GET, POST). See - // documentation below for more options. - handler := cors.Default().Handler(mux) - http.ListenAndServe(":8080", handler) -} -``` - -Install `cors`: - - go get github.com/rs/cors - -Then run your server: - - go run server.go - -The server now runs on `localhost:8080`: - - $ curl -D - -H 'Origin: http://foo.com' http://localhost:8080/ - HTTP/1.1 200 OK - Access-Control-Allow-Origin: foo.com - Content-Type: application/json - Date: Sat, 25 Oct 2014 03:43:57 GMT - Content-Length: 18 - - {"hello": "world"} - -### More Examples - -* `net/http`: [examples/nethttp/server.go](https://github.com/rs/cors/blob/master/examples/nethttp/server.go) -* [Goji](https://goji.io): [examples/goji/server.go](https://github.com/rs/cors/blob/master/examples/goji/server.go) -* [Martini](http://martini.codegangsta.io): [examples/martini/server.go](https://github.com/rs/cors/blob/master/examples/martini/server.go) -* [Negroni](https://github.com/codegangsta/negroni): [examples/negroni/server.go](https://github.com/rs/cors/blob/master/examples/negroni/server.go) -* [Alice](https://github.com/justinas/alice): [examples/alice/server.go](https://github.com/rs/cors/blob/master/examples/alice/server.go) - -## Parameters - -Parameters are passed to the middleware thru the `cors.New` method as follow: - -```go -c := cors.New(cors.Options{ - AllowedOrigins: []string{"http://foo.com"}, - AllowCredentials: true, -}) - -// Insert the middleware -handler = c.Handler(handler) -``` - -* **AllowedOrigins** `[]string`: A list of origins a cross-domain request can be executed from. If the special `*` value is present in the list, all origins will be allowed. An origin may contain a wildcard (`*`) to replace 0 or more characters (i.e.: `http://*.domain.com`). Usage of wildcards implies a small performance penality. Only one wildcard can be used per origin. The default value is `*`. -* **AllowOriginFunc** `func (origin string) bool`: A custom function to validate the origin. It take the origin as argument and returns true if allowed or false otherwise. If this option is set, the content of `AllowedOrigins` is ignored -* **AllowedMethods** `[]string`: A list of methods the client is allowed to use with cross-domain requests. Default value is simple methods (`GET` and `POST`). -* **AllowedHeaders** `[]string`: A list of non simple headers the client is allowed to use with cross-domain requests. -* **ExposedHeaders** `[]string`: Indicates which headers are safe to expose to the API of a CORS API specification -* **AllowCredentials** `bool`: Indicates whether the request can include user credentials like cookies, HTTP authentication or client side SSL certificates. The default is `false`. -* **MaxAge** `int`: Indicates how long (in seconds) the results of a preflight request can be cached. The default is `0` which stands for no max age. -* **OptionsPassthrough** `bool`: Instructs preflight to let other potential next handlers to process the `OPTIONS` method. Turn this on if your application handles `OPTIONS`. -* **Debug** `bool`: Debugging flag adds additional output to debug server side CORS issues. - -See [API documentation](http://godoc.org/github.com/rs/cors) for more info. - -## Benchmarks - - BenchmarkWithout 20000000 64.6 ns/op 8 B/op 1 allocs/op - BenchmarkDefault 3000000 469 ns/op 114 B/op 2 allocs/op - BenchmarkAllowedOrigin 3000000 608 ns/op 114 B/op 2 allocs/op - BenchmarkPreflight 20000000 73.2 ns/op 0 B/op 0 allocs/op - BenchmarkPreflightHeader 20000000 73.6 ns/op 0 B/op 0 allocs/op - BenchmarkParseHeaderList 2000000 847 ns/op 184 B/op 6 allocs/op - BenchmarkParse…Single 5000000 290 ns/op 32 B/op 3 allocs/op - BenchmarkParse…Normalized 2000000 776 ns/op 160 B/op 6 allocs/op - -## Licenses - -All source code is licensed under the [MIT License](https://raw.github.com/rs/cors/master/LICENSE). diff --git a/vendor/github.com/rs/cors/bench_test.go b/vendor/github.com/rs/cors/bench_test.go deleted file mode 100644 index b6e3721de..000000000 --- a/vendor/github.com/rs/cors/bench_test.go +++ /dev/null @@ -1,88 +0,0 @@ -package cors - -import ( - "net/http" - "testing" -) - -type FakeResponse struct { - header http.Header -} - -func (r FakeResponse) Header() http.Header { - return r.header -} - -func (r FakeResponse) WriteHeader(n int) { -} - -func (r FakeResponse) Write(b []byte) (n int, err error) { - return len(b), nil -} - -func BenchmarkWithout(b *testing.B) { - res := FakeResponse{http.Header{}} - req, _ := http.NewRequest("GET", "http://example.com/foo", nil) - - b.ReportAllocs() - b.ResetTimer() - for i := 0; i < b.N; i++ { - testHandler.ServeHTTP(res, req) - } -} - -func BenchmarkDefault(b *testing.B) { - res := FakeResponse{http.Header{}} - req, _ := http.NewRequest("GET", "http://example.com/foo", nil) - req.Header.Add("Origin", "somedomain.com") - handler := Default().Handler(testHandler) - - b.ReportAllocs() - b.ResetTimer() - for i := 0; i < b.N; i++ { - handler.ServeHTTP(res, req) - } -} - -func BenchmarkAllowedOrigin(b *testing.B) { - res := FakeResponse{http.Header{}} - req, _ := http.NewRequest("GET", "http://example.com/foo", nil) - req.Header.Add("Origin", "somedomain.com") - c := New(Options{ - AllowedOrigins: []string{"somedomain.com"}, - }) - handler := c.Handler(testHandler) - - b.ReportAllocs() - b.ResetTimer() - for i := 0; i < b.N; i++ { - handler.ServeHTTP(res, req) - } -} - -func BenchmarkPreflight(b *testing.B) { - res := FakeResponse{http.Header{}} - req, _ := http.NewRequest("OPTIONS", "http://example.com/foo", nil) - req.Header.Add("Access-Control-Request-Method", "GET") - handler := Default().Handler(testHandler) - - b.ReportAllocs() - b.ResetTimer() - for i := 0; i < b.N; i++ { - handler.ServeHTTP(res, req) - } -} - -func BenchmarkPreflightHeader(b *testing.B) { - res := FakeResponse{http.Header{}} - req, _ := http.NewRequest("OPTIONS", "http://example.com/foo", nil) - req.Header.Add("Access-Control-Request-Method", "GET") - req.Header.Add("Access-Control-Request-Headers", "Accept") - handler := Default().Handler(testHandler) - - b.ReportAllocs() - b.ResetTimer() - for i := 0; i < b.N; i++ { - handler.ServeHTTP(res, req) - } -} diff --git a/vendor/github.com/rs/cors/cors.go b/vendor/github.com/rs/cors/cors.go deleted file mode 100644 index dffa73fa0..000000000 --- a/vendor/github.com/rs/cors/cors.go +++ /dev/null @@ -1,385 +0,0 @@ -/* -Package cors is net/http handler to handle CORS related requests -as defined by http://www.w3.org/TR/cors/ - -You can configure it by passing an option struct to cors.New: - - c := cors.New(cors.Options{ - AllowedOrigins: []string{"foo.com"}, - AllowedMethods: []string{"GET", "POST", "DELETE"}, - AllowCredentials: true, - }) - -Then insert the handler in the chain: - - handler = c.Handler(handler) - -See Options documentation for more options. - -The resulting handler is a standard net/http handler. -*/ -package cors - -import ( - "log" - "net/http" - "os" - "strconv" - "strings" -) - -// Options is a configuration container to setup the CORS middleware. -type Options struct { - // AllowedOrigins is a list of origins a cross-domain request can be executed from. - // If the special "*" value is present in the list, all origins will be allowed. - // An origin may contain a wildcard (*) to replace 0 or more characters - // (i.e.: http://*.domain.com). Usage of wildcards implies a small performance penality. - // Only one wildcard can be used per origin. - // Default value is ["*"] - AllowedOrigins []string - // AllowOriginFunc is a custom function to validate the origin. It take the origin - // as argument and returns true if allowed or false otherwise. If this option is - // set, the content of AllowedOrigins is ignored. - AllowOriginFunc func(origin string) bool - // AllowedMethods is a list of methods the client is allowed to use with - // cross-domain requests. Default value is simple methods (GET and POST) - AllowedMethods []string - // AllowedHeaders is list of non simple headers the client is allowed to use with - // cross-domain requests. - // If the special "*" value is present in the list, all headers will be allowed. - // Default value is [] but "Origin" is always appended to the list. - AllowedHeaders []string - // ExposedHeaders indicates which headers are safe to expose to the API of a CORS - // API specification - ExposedHeaders []string - // AllowCredentials indicates whether the request can include user credentials like - // cookies, HTTP authentication or client side SSL certificates. - AllowCredentials bool - // MaxAge indicates how long (in seconds) the results of a preflight request - // can be cached - MaxAge int - // OptionsPassthrough instructs preflight to let other potential next handlers to - // process the OPTIONS method. Turn this on if your application handles OPTIONS. - OptionsPassthrough bool - // Debugging flag adds additional output to debug server side CORS issues - Debug bool -} - -// Cors http handler -type Cors struct { - // Debug logger - log *log.Logger - // Set to true when allowed origins contains a "*" - allowedOriginsAll bool - // Normalized list of plain allowed origins - allowedOrigins []string - // List of allowed origins containing wildcards - allowedWOrigins []wildcard - // Optional origin validator function - allowOriginFunc func(origin string) bool - // Set to true when allowed headers contains a "*" - allowedHeadersAll bool - // Normalized list of allowed headers - allowedHeaders []string - // Normalized list of allowed methods - allowedMethods []string - // Normalized list of exposed headers - exposedHeaders []string - allowCredentials bool - maxAge int - optionPassthrough bool -} - -// New creates a new Cors handler with the provided options. -func New(options Options) *Cors { - c := &Cors{ - exposedHeaders: convert(options.ExposedHeaders, http.CanonicalHeaderKey), - allowOriginFunc: options.AllowOriginFunc, - allowCredentials: options.AllowCredentials, - maxAge: options.MaxAge, - optionPassthrough: options.OptionsPassthrough, - } - if options.Debug { - c.log = log.New(os.Stdout, "[cors] ", log.LstdFlags) - } - - // Normalize options - // Note: for origins and methods matching, the spec requires a case-sensitive matching. - // As it may error prone, we chose to ignore the spec here. - - // Allowed Origins - if len(options.AllowedOrigins) == 0 { - // Default is all origins - c.allowedOriginsAll = true - } else { - c.allowedOrigins = []string{} - c.allowedWOrigins = []wildcard{} - for _, origin := range options.AllowedOrigins { - // Normalize - origin = strings.ToLower(origin) - if origin == "*" { - // If "*" is present in the list, turn the whole list into a match all - c.allowedOriginsAll = true - c.allowedOrigins = nil - c.allowedWOrigins = nil - break - } else if i := strings.IndexByte(origin, '*'); i >= 0 { - // Split the origin in two: start and end string without the * - w := wildcard{origin[0:i], origin[i+1 : len(origin)]} - c.allowedWOrigins = append(c.allowedWOrigins, w) - } else { - c.allowedOrigins = append(c.allowedOrigins, origin) - } - } - } - - // Allowed Headers - if len(options.AllowedHeaders) == 0 { - // Use sensible defaults - c.allowedHeaders = []string{"Origin", "Accept", "Content-Type"} - } else { - // Origin is always appended as some browsers will always request for this header at preflight - c.allowedHeaders = convert(append(options.AllowedHeaders, "Origin"), http.CanonicalHeaderKey) - for _, h := range options.AllowedHeaders { - if h == "*" { - c.allowedHeadersAll = true - c.allowedHeaders = nil - break - } - } - } - - // Allowed Methods - if len(options.AllowedMethods) == 0 { - // Default is spec's "simple" methods - c.allowedMethods = []string{"GET", "POST"} - } else { - c.allowedMethods = convert(options.AllowedMethods, strings.ToUpper) - } - - return c -} - -// Default creates a new Cors handler with default options -func Default() *Cors { - return New(Options{}) -} - -// Handler apply the CORS specification on the request, and add relevant CORS headers -// as necessary. -func (c *Cors) Handler(h http.Handler) http.Handler { - return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) { - if r.Method == "OPTIONS" { - c.logf("Handler: Preflight request") - c.handlePreflight(w, r) - // Preflight requests are standalone and should stop the chain as some other - // middleware may not handle OPTIONS requests correctly. One typical example - // is authentication middleware ; OPTIONS requests won't carry authentication - // headers (see #1) - if c.optionPassthrough { - h.ServeHTTP(w, r) - } - } else { - c.logf("Handler: Actual request") - c.handleActualRequest(w, r) - h.ServeHTTP(w, r) - } - }) -} - -// HandlerFunc provides Martini compatible handler -func (c *Cors) HandlerFunc(w http.ResponseWriter, r *http.Request) { - if r.Method == "OPTIONS" { - c.logf("HandlerFunc: Preflight request") - c.handlePreflight(w, r) - } else { - c.logf("HandlerFunc: Actual request") - c.handleActualRequest(w, r) - } -} - -// Negroni compatible interface -func (c *Cors) ServeHTTP(w http.ResponseWriter, r *http.Request, next http.HandlerFunc) { - if r.Method == "OPTIONS" { - c.logf("ServeHTTP: Preflight request") - c.handlePreflight(w, r) - // Preflight requests are standalone and should stop the chain as some other - // middleware may not handle OPTIONS requests correctly. One typical example - // is authentication middleware ; OPTIONS requests won't carry authentication - // headers (see #1) - if c.optionPassthrough { - next(w, r) - } - } else { - c.logf("ServeHTTP: Actual request") - c.handleActualRequest(w, r) - next(w, r) - } -} - -// handlePreflight handles pre-flight CORS requests -func (c *Cors) handlePreflight(w http.ResponseWriter, r *http.Request) { - headers := w.Header() - origin := r.Header.Get("Origin") - - if r.Method != "OPTIONS" { - c.logf(" Preflight aborted: %s!=OPTIONS", r.Method) - return - } - // Always set Vary headers - // see https://github.com/rs/cors/issues/10, - // https://github.com/rs/cors/commit/dbdca4d95feaa7511a46e6f1efb3b3aa505bc43f#commitcomment-12352001 - headers.Add("Vary", "Origin") - headers.Add("Vary", "Access-Control-Request-Method") - headers.Add("Vary", "Access-Control-Request-Headers") - - if origin == "" { - c.logf(" Preflight aborted: empty origin") - return - } - if !c.isOriginAllowed(origin) { - c.logf(" Preflight aborted: origin '%s' not allowed", origin) - return - } - - reqMethod := r.Header.Get("Access-Control-Request-Method") - if !c.isMethodAllowed(reqMethod) { - c.logf(" Preflight aborted: method '%s' not allowed", reqMethod) - return - } - reqHeaders := parseHeaderList(r.Header.Get("Access-Control-Request-Headers")) - if !c.areHeadersAllowed(reqHeaders) { - c.logf(" Preflight aborted: headers '%v' not allowed", reqHeaders) - return - } - headers.Set("Access-Control-Allow-Origin", origin) - // Spec says: Since the list of methods can be unbounded, simply returning the method indicated - // by Access-Control-Request-Method (if supported) can be enough - headers.Set("Access-Control-Allow-Methods", strings.ToUpper(reqMethod)) - if len(reqHeaders) > 0 { - - // Spec says: Since the list of headers can be unbounded, simply returning supported headers - // from Access-Control-Request-Headers can be enough - headers.Set("Access-Control-Allow-Headers", strings.Join(reqHeaders, ", ")) - } - if c.allowCredentials { - headers.Set("Access-Control-Allow-Credentials", "true") - } - if c.maxAge > 0 { - headers.Set("Access-Control-Max-Age", strconv.Itoa(c.maxAge)) - } - c.logf(" Preflight response headers: %v", headers) -} - -// handleActualRequest handles simple cross-origin requests, actual request or redirects -func (c *Cors) handleActualRequest(w http.ResponseWriter, r *http.Request) { - headers := w.Header() - origin := r.Header.Get("Origin") - - if r.Method == "OPTIONS" { - c.logf(" Actual request no headers added: method == %s", r.Method) - return - } - // Always set Vary, see https://github.com/rs/cors/issues/10 - headers.Add("Vary", "Origin") - if origin == "" { - c.logf(" Actual request no headers added: missing origin") - return - } - if !c.isOriginAllowed(origin) { - c.logf(" Actual request no headers added: origin '%s' not allowed", origin) - return - } - - // Note that spec does define a way to specifically disallow a simple method like GET or - // POST. Access-Control-Allow-Methods is only used for pre-flight requests and the - // spec doesn't instruct to check the allowed methods for simple cross-origin requests. - // We think it's a nice feature to be able to have control on those methods though. - if !c.isMethodAllowed(r.Method) { - if c.log != nil { - c.logf(" Actual request no headers added: method '%s' not allowed", - r.Method) - } - - return - } - headers.Set("Access-Control-Allow-Origin", origin) - if len(c.exposedHeaders) > 0 { - headers.Set("Access-Control-Expose-Headers", strings.Join(c.exposedHeaders, ", ")) - } - if c.allowCredentials { - headers.Set("Access-Control-Allow-Credentials", "true") - } - c.logf(" Actual response added headers: %v", headers) -} - -// convenience method. checks if debugging is turned on before printing -func (c *Cors) logf(format string, a ...interface{}) { - if c.log != nil { - c.log.Printf(format, a...) - } -} - -// isOriginAllowed checks if a given origin is allowed to perform cross-domain requests -// on the endpoint -func (c *Cors) isOriginAllowed(origin string) bool { - if c.allowOriginFunc != nil { - return c.allowOriginFunc(origin) - } - if c.allowedOriginsAll { - return true - } - origin = strings.ToLower(origin) - for _, o := range c.allowedOrigins { - if o == origin { - return true - } - } - for _, w := range c.allowedWOrigins { - if w.match(origin) { - return true - } - } - return false -} - -// isMethodAllowed checks if a given method can be used as part of a cross-domain request -// on the endpoing -func (c *Cors) isMethodAllowed(method string) bool { - if len(c.allowedMethods) == 0 { - // If no method allowed, always return false, even for preflight request - return false - } - method = strings.ToUpper(method) - if method == "OPTIONS" { - // Always allow preflight requests - return true - } - for _, m := range c.allowedMethods { - if m == method { - return true - } - } - return false -} - -// areHeadersAllowed checks if a given list of headers are allowed to used within -// a cross-domain request. -func (c *Cors) areHeadersAllowed(requestedHeaders []string) bool { - if c.allowedHeadersAll || len(requestedHeaders) == 0 { - return true - } - for _, header := range requestedHeaders { - header = http.CanonicalHeaderKey(header) - found := false - for _, h := range c.allowedHeaders { - if h == header { - found = true - } - } - if !found { - return false - } - } - return true -} diff --git a/vendor/github.com/rs/cors/cors_test.go b/vendor/github.com/rs/cors/cors_test.go deleted file mode 100644 index 28672a001..000000000 --- a/vendor/github.com/rs/cors/cors_test.go +++ /dev/null @@ -1,371 +0,0 @@ -package cors - -import ( - "net/http" - "net/http/httptest" - "regexp" - "strings" - "testing" -) - -var testHandler = http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) { - w.Write([]byte("bar")) -}) - -func assertHeaders(t *testing.T, resHeaders http.Header, reqHeaders map[string]string) { - for name, value := range reqHeaders { - if actual := strings.Join(resHeaders[name], ", "); actual != value { - t.Errorf("Invalid header `%s', wanted `%s', got `%s'", name, value, actual) - } - } -} - -func TestNoConfig(t *testing.T) { - s := New(Options{ - // Intentionally left blank. - }) - - res := httptest.NewRecorder() - req, _ := http.NewRequest("GET", "http://example.com/foo", nil) - - s.Handler(testHandler).ServeHTTP(res, req) - - assertHeaders(t, res.Header(), map[string]string{ - "Vary": "Origin", - "Access-Control-Allow-Origin": "", - "Access-Control-Allow-Methods": "", - "Access-Control-Allow-Headers": "", - "Access-Control-Allow-Credentials": "", - "Access-Control-Max-Age": "", - "Access-Control-Expose-Headers": "", - }) -} - -func TestMatchAllOrigin(t *testing.T) { - s := New(Options{ - AllowedOrigins: []string{"*"}, - }) - - res := httptest.NewRecorder() - req, _ := http.NewRequest("GET", "http://example.com/foo", nil) - req.Header.Add("Origin", "http://foobar.com") - - s.Handler(testHandler).ServeHTTP(res, req) - - assertHeaders(t, res.Header(), map[string]string{ - "Vary": "Origin", - "Access-Control-Allow-Origin": "http://foobar.com", - "Access-Control-Allow-Methods": "", - "Access-Control-Allow-Headers": "", - "Access-Control-Allow-Credentials": "", - "Access-Control-Max-Age": "", - "Access-Control-Expose-Headers": "", - }) -} - -func TestAllowedOrigin(t *testing.T) { - s := New(Options{ - AllowedOrigins: []string{"http://foobar.com"}, - }) - - res := httptest.NewRecorder() - req, _ := http.NewRequest("GET", "http://example.com/foo", nil) - req.Header.Add("Origin", "http://foobar.com") - - s.Handler(testHandler).ServeHTTP(res, req) - - assertHeaders(t, res.Header(), map[string]string{ - "Vary": "Origin", - "Access-Control-Allow-Origin": "http://foobar.com", - "Access-Control-Allow-Methods": "", - "Access-Control-Allow-Headers": "", - "Access-Control-Allow-Credentials": "", - "Access-Control-Max-Age": "", - "Access-Control-Expose-Headers": "", - }) -} - -func TestWildcardOrigin(t *testing.T) { - s := New(Options{ - AllowedOrigins: []string{"http://*.bar.com"}, - }) - - res := httptest.NewRecorder() - req, _ := http.NewRequest("GET", "http://example.com/foo", nil) - req.Header.Add("Origin", "http://foo.bar.com") - - s.Handler(testHandler).ServeHTTP(res, req) - - assertHeaders(t, res.Header(), map[string]string{ - "Vary": "Origin", - "Access-Control-Allow-Origin": "http://foo.bar.com", - "Access-Control-Allow-Methods": "", - "Access-Control-Allow-Headers": "", - "Access-Control-Allow-Credentials": "", - "Access-Control-Max-Age": "", - "Access-Control-Expose-Headers": "", - }) -} - -func TestDisallowedOrigin(t *testing.T) { - s := New(Options{ - AllowedOrigins: []string{"http://foobar.com"}, - }) - - res := httptest.NewRecorder() - req, _ := http.NewRequest("GET", "http://example.com/foo", nil) - req.Header.Add("Origin", "http://barbaz.com") - - s.Handler(testHandler).ServeHTTP(res, req) - - assertHeaders(t, res.Header(), map[string]string{ - "Vary": "Origin", - "Access-Control-Allow-Origin": "", - "Access-Control-Allow-Methods": "", - "Access-Control-Allow-Headers": "", - "Access-Control-Allow-Credentials": "", - "Access-Control-Max-Age": "", - "Access-Control-Expose-Headers": "", - }) -} - -func TestDisallowedWildcardOrigin(t *testing.T) { - s := New(Options{ - AllowedOrigins: []string{"http://*.bar.com"}, - }) - - res := httptest.NewRecorder() - req, _ := http.NewRequest("GET", "http://example.com/foo", nil) - req.Header.Add("Origin", "http://foo.baz.com") - - s.Handler(testHandler).ServeHTTP(res, req) - - assertHeaders(t, res.Header(), map[string]string{ - "Vary": "Origin", - "Access-Control-Allow-Origin": "", - "Access-Control-Allow-Methods": "", - "Access-Control-Allow-Headers": "", - "Access-Control-Allow-Credentials": "", - "Access-Control-Max-Age": "", - "Access-Control-Expose-Headers": "", - }) -} - -func TestAllowedOriginFunc(t *testing.T) { - r, _ := regexp.Compile("^http://foo") - s := New(Options{ - AllowOriginFunc: func(o string) bool { - return r.MatchString(o) - }, - }) - - req, _ := http.NewRequest("GET", "http://example.com/foo", nil) - - res := httptest.NewRecorder() - req.Header.Set("Origin", "http://foobar.com") - s.Handler(testHandler).ServeHTTP(res, req) - assertHeaders(t, res.Header(), map[string]string{ - "Access-Control-Allow-Origin": "http://foobar.com", - }) - - res = httptest.NewRecorder() - req.Header.Set("Origin", "http://barfoo.com") - s.Handler(testHandler).ServeHTTP(res, req) - assertHeaders(t, res.Header(), map[string]string{ - "Access-Control-Allow-Origin": "", - }) -} - -func TestAllowedMethod(t *testing.T) { - s := New(Options{ - AllowedOrigins: []string{"http://foobar.com"}, - AllowedMethods: []string{"PUT", "DELETE"}, - }) - - res := httptest.NewRecorder() - req, _ := http.NewRequest("OPTIONS", "http://example.com/foo", nil) - req.Header.Add("Origin", "http://foobar.com") - req.Header.Add("Access-Control-Request-Method", "PUT") - - s.Handler(testHandler).ServeHTTP(res, req) - - assertHeaders(t, res.Header(), map[string]string{ - "Vary": "Origin, Access-Control-Request-Method, Access-Control-Request-Headers", - "Access-Control-Allow-Origin": "http://foobar.com", - "Access-Control-Allow-Methods": "PUT", - "Access-Control-Allow-Headers": "", - "Access-Control-Allow-Credentials": "", - "Access-Control-Max-Age": "", - "Access-Control-Expose-Headers": "", - }) -} - -func TestDisallowedMethod(t *testing.T) { - s := New(Options{ - AllowedOrigins: []string{"http://foobar.com"}, - AllowedMethods: []string{"PUT", "DELETE"}, - }) - - res := httptest.NewRecorder() - req, _ := http.NewRequest("OPTIONS", "http://example.com/foo", nil) - req.Header.Add("Origin", "http://foobar.com") - req.Header.Add("Access-Control-Request-Method", "PATCH") - - s.Handler(testHandler).ServeHTTP(res, req) - - assertHeaders(t, res.Header(), map[string]string{ - "Vary": "Origin, Access-Control-Request-Method, Access-Control-Request-Headers", - "Access-Control-Allow-Origin": "", - "Access-Control-Allow-Methods": "", - "Access-Control-Allow-Headers": "", - "Access-Control-Allow-Credentials": "", - "Access-Control-Max-Age": "", - "Access-Control-Expose-Headers": "", - }) -} - -func TestAllowedHeader(t *testing.T) { - s := New(Options{ - AllowedOrigins: []string{"http://foobar.com"}, - AllowedHeaders: []string{"X-Header-1", "x-header-2"}, - }) - - res := httptest.NewRecorder() - req, _ := http.NewRequest("OPTIONS", "http://example.com/foo", nil) - req.Header.Add("Origin", "http://foobar.com") - req.Header.Add("Access-Control-Request-Method", "GET") - req.Header.Add("Access-Control-Request-Headers", "X-Header-2, X-HEADER-1") - - s.Handler(testHandler).ServeHTTP(res, req) - - assertHeaders(t, res.Header(), map[string]string{ - "Vary": "Origin, Access-Control-Request-Method, Access-Control-Request-Headers", - "Access-Control-Allow-Origin": "http://foobar.com", - "Access-Control-Allow-Methods": "GET", - "Access-Control-Allow-Headers": "X-Header-2, X-Header-1", - "Access-Control-Allow-Credentials": "", - "Access-Control-Max-Age": "", - "Access-Control-Expose-Headers": "", - }) -} - -func TestAllowedWildcardHeader(t *testing.T) { - s := New(Options{ - AllowedOrigins: []string{"http://foobar.com"}, - AllowedHeaders: []string{"*"}, - }) - - res := httptest.NewRecorder() - req, _ := http.NewRequest("OPTIONS", "http://example.com/foo", nil) - req.Header.Add("Origin", "http://foobar.com") - req.Header.Add("Access-Control-Request-Method", "GET") - req.Header.Add("Access-Control-Request-Headers", "X-Header-2, X-HEADER-1") - - s.Handler(testHandler).ServeHTTP(res, req) - - assertHeaders(t, res.Header(), map[string]string{ - "Vary": "Origin, Access-Control-Request-Method, Access-Control-Request-Headers", - "Access-Control-Allow-Origin": "http://foobar.com", - "Access-Control-Allow-Methods": "GET", - "Access-Control-Allow-Headers": "X-Header-2, X-Header-1", - "Access-Control-Allow-Credentials": "", - "Access-Control-Max-Age": "", - "Access-Control-Expose-Headers": "", - }) -} - -func TestDisallowedHeader(t *testing.T) { - s := New(Options{ - AllowedOrigins: []string{"http://foobar.com"}, - AllowedHeaders: []string{"X-Header-1", "x-header-2"}, - }) - - res := httptest.NewRecorder() - req, _ := http.NewRequest("OPTIONS", "http://example.com/foo", nil) - req.Header.Add("Origin", "http://foobar.com") - req.Header.Add("Access-Control-Request-Method", "GET") - req.Header.Add("Access-Control-Request-Headers", "X-Header-3, X-Header-1") - - s.Handler(testHandler).ServeHTTP(res, req) - - assertHeaders(t, res.Header(), map[string]string{ - "Vary": "Origin, Access-Control-Request-Method, Access-Control-Request-Headers", - "Access-Control-Allow-Origin": "", - "Access-Control-Allow-Methods": "", - "Access-Control-Allow-Headers": "", - "Access-Control-Allow-Credentials": "", - "Access-Control-Max-Age": "", - "Access-Control-Expose-Headers": "", - }) -} - -func TestOriginHeader(t *testing.T) { - s := New(Options{ - AllowedOrigins: []string{"http://foobar.com"}, - }) - - res := httptest.NewRecorder() - req, _ := http.NewRequest("OPTIONS", "http://example.com/foo", nil) - req.Header.Add("Origin", "http://foobar.com") - req.Header.Add("Access-Control-Request-Method", "GET") - req.Header.Add("Access-Control-Request-Headers", "origin") - - s.Handler(testHandler).ServeHTTP(res, req) - - assertHeaders(t, res.Header(), map[string]string{ - "Vary": "Origin, Access-Control-Request-Method, Access-Control-Request-Headers", - "Access-Control-Allow-Origin": "http://foobar.com", - "Access-Control-Allow-Methods": "GET", - "Access-Control-Allow-Headers": "Origin", - "Access-Control-Allow-Credentials": "", - "Access-Control-Max-Age": "", - "Access-Control-Expose-Headers": "", - }) -} - -func TestExposedHeader(t *testing.T) { - s := New(Options{ - AllowedOrigins: []string{"http://foobar.com"}, - ExposedHeaders: []string{"X-Header-1", "x-header-2"}, - }) - - res := httptest.NewRecorder() - req, _ := http.NewRequest("GET", "http://example.com/foo", nil) - req.Header.Add("Origin", "http://foobar.com") - - s.Handler(testHandler).ServeHTTP(res, req) - - assertHeaders(t, res.Header(), map[string]string{ - "Vary": "Origin", - "Access-Control-Allow-Origin": "http://foobar.com", - "Access-Control-Allow-Methods": "", - "Access-Control-Allow-Headers": "", - "Access-Control-Allow-Credentials": "", - "Access-Control-Max-Age": "", - "Access-Control-Expose-Headers": "X-Header-1, X-Header-2", - }) -} - -func TestAllowedCredentials(t *testing.T) { - s := New(Options{ - AllowedOrigins: []string{"http://foobar.com"}, - AllowCredentials: true, - }) - - res := httptest.NewRecorder() - req, _ := http.NewRequest("OPTIONS", "http://example.com/foo", nil) - req.Header.Add("Origin", "http://foobar.com") - req.Header.Add("Access-Control-Request-Method", "GET") - - s.Handler(testHandler).ServeHTTP(res, req) - - assertHeaders(t, res.Header(), map[string]string{ - "Vary": "Origin, Access-Control-Request-Method, Access-Control-Request-Headers", - "Access-Control-Allow-Origin": "http://foobar.com", - "Access-Control-Allow-Methods": "GET", - "Access-Control-Allow-Headers": "", - "Access-Control-Allow-Credentials": "true", - "Access-Control-Max-Age": "", - "Access-Control-Expose-Headers": "", - }) -} diff --git a/vendor/github.com/rs/cors/utils.go b/vendor/github.com/rs/cors/utils.go deleted file mode 100644 index cd24831fc..000000000 --- a/vendor/github.com/rs/cors/utils.go +++ /dev/null @@ -1,70 +0,0 @@ -package cors - -import "strings" - -const toLower = 'a' - 'A' - -type converter func(string) string - -type wildcard struct { - prefix string - suffix string -} - -func (w wildcard) match(s string) bool { - return len(s) >= len(w.prefix+w.suffix) && strings.HasPrefix(s, w.prefix) && strings.HasSuffix(s, w.suffix) -} - -// convert converts a list of string using the passed converter function -func convert(s []string, c converter) []string { - out := []string{} - for _, i := range s { - out = append(out, c(i)) - } - return out -} - -// parseHeaderList tokenize + normalize a string containing a list of headers -func parseHeaderList(headerList string) []string { - l := len(headerList) - h := make([]byte, 0, l) - upper := true - // Estimate the number headers in order to allocate the right splice size - t := 0 - for i := 0; i < l; i++ { - if headerList[i] == ',' { - t++ - } - } - headers := make([]string, 0, t) - for i := 0; i < l; i++ { - b := headerList[i] - if b >= 'a' && b <= 'z' { - if upper { - h = append(h, b-toLower) - } else { - h = append(h, b) - } - } else if b >= 'A' && b <= 'Z' { - if !upper { - h = append(h, b+toLower) - } else { - h = append(h, b) - } - } else if b == '-' || (b >= '0' && b <= '9') { - h = append(h, b) - } - - if b == ' ' || b == ',' || i == l-1 { - if len(h) > 0 { - // Flush the found header - headers = append(headers, string(h)) - h = h[:0] - upper = true - } - } else { - upper = b == '-' - } - } - return headers -} diff --git a/vendor/github.com/rs/cors/utils_test.go b/vendor/github.com/rs/cors/utils_test.go deleted file mode 100644 index 83053b3fc..000000000 --- a/vendor/github.com/rs/cors/utils_test.go +++ /dev/null @@ -1,70 +0,0 @@ -package cors - -import ( - "strings" - "testing" -) - -func TestWildcard(t *testing.T) { - w := wildcard{"foo", "bar"} - if !w.match("foobar") { - t.Error("foo*bar should match foobar") - } - if !w.match("foobazbar") { - t.Error("foo*bar should match foobazbar") - } - if w.match("foobaz") { - t.Error("foo*bar should not match foobaz") - } - - w = wildcard{"foo", "oof"} - if w.match("foof") { - t.Error("foo*oof should not match foof") - } -} - -func TestConvert(t *testing.T) { - s := convert([]string{"A", "b", "C"}, strings.ToLower) - e := []string{"a", "b", "c"} - if s[0] != e[0] || s[1] != e[1] || s[2] != e[2] { - t.Errorf("%v != %v", s, e) - } -} - -func TestParseHeaderList(t *testing.T) { - h := parseHeaderList("header, second-header, THIRD-HEADER, Numb3r3d-H34d3r") - e := []string{"Header", "Second-Header", "Third-Header", "Numb3r3d-H34d3r"} - if h[0] != e[0] || h[1] != e[1] || h[2] != e[2] { - t.Errorf("%v != %v", h, e) - } -} - -func TestParseHeaderListEmpty(t *testing.T) { - if len(parseHeaderList("")) != 0 { - t.Error("should be empty sclice") - } - if len(parseHeaderList(" , ")) != 0 { - t.Error("should be empty sclice") - } -} - -func BenchmarkParseHeaderList(b *testing.B) { - b.ReportAllocs() - for i := 0; i < b.N; i++ { - parseHeaderList("header, second-header, THIRD-HEADER") - } -} - -func BenchmarkParseHeaderListSingle(b *testing.B) { - b.ReportAllocs() - for i := 0; i < b.N; i++ { - parseHeaderList("header") - } -} - -func BenchmarkParseHeaderListNormalized(b *testing.B) { - b.ReportAllocs() - for i := 0; i < b.N; i++ { - parseHeaderList("Header1, Header2, Third-Header") - } -}