diff --git a/docs/sources/http_api/folder_dashboard_search.md b/docs/sources/http_api/folder_dashboard_search.md index 0a736a277b78..cee7d335cc32 100644 --- a/docs/sources/http_api/folder_dashboard_search.md +++ b/docs/sources/http_api/folder_dashboard_search.md @@ -24,7 +24,7 @@ Query parameters: - **folderIds** – List of folder id's to search in for dashboards - **starred** – Flag indicating if only starred Dashboards should be returned - **limit** – Limit the number of returned results (max 5000) -- **page** – Use this parameter to access hits beyond limit. Numbering starts at 1. limit param acts as page size. +- **page** – Use this parameter to access hits beyond limit. Numbering starts at 1. limit param acts as page size. Only available in Grafana v6.2+. **Example request for retrieving folders and dashboards of the general folder**: diff --git a/pkg/api/pluginproxy/ds_proxy.go b/pkg/api/pluginproxy/ds_proxy.go index b86d1834844f..fe79fa565950 100644 --- a/pkg/api/pluginproxy/ds_proxy.go +++ b/pkg/api/pluginproxy/ds_proxy.go @@ -101,8 +101,14 @@ func (proxy *DataSourceProxy) HandleRequest() { opentracing.HTTPHeaders, opentracing.HTTPHeadersCarrier(proxy.ctx.Req.Request.Header)) + originalSetCookie := proxy.ctx.Resp.Header().Get("Set-Cookie") + reverseProxy.ServeHTTP(proxy.ctx.Resp, proxy.ctx.Req.Request) proxy.ctx.Resp.Header().Del("Set-Cookie") + + if originalSetCookie != "" { + proxy.ctx.Resp.Header().Set("Set-Cookie", originalSetCookie) + } } func (proxy *DataSourceProxy) addTraceFromHeaderValue(span opentracing.Span, headerName string, tagName string) { diff --git a/pkg/api/pluginproxy/ds_proxy_test.go b/pkg/api/pluginproxy/ds_proxy_test.go index e9e526fb7c39..c3eccb4a57c9 100644 --- a/pkg/api/pluginproxy/ds_proxy_test.go +++ b/pkg/api/pluginproxy/ds_proxy_test.go @@ -3,13 +3,15 @@ package pluginproxy import ( "bytes" "fmt" - "github.com/grafana/grafana/pkg/components/securejsondata" "io/ioutil" "net/http" + "net/http/httptest" "net/url" "testing" "time" + "github.com/grafana/grafana/pkg/components/securejsondata" + "golang.org/x/oauth2" macaron "gopkg.in/macaron.v1" @@ -496,9 +498,73 @@ func TestDSRouteRule(t *testing.T) { runDatasourceAuthTest(test) } }) + + Convey("HandleRequest()", func() { + backend := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) { + http.SetCookie(w, &http.Cookie{Name: "flavor", Value: "chocolateChip"}) + w.WriteHeader(200) + w.Write([]byte("I am the backend")) + })) + defer backend.Close() + + plugin := &plugins.DataSourcePlugin{} + ds := &m.DataSource{Url: backend.URL, Type: m.DS_GRAPHITE} + + responseRecorder := &CloseNotifierResponseRecorder{ + ResponseRecorder: httptest.NewRecorder(), + } + defer responseRecorder.Close() + + setupCtx := func(fn func(http.ResponseWriter)) *m.ReqContext { + responseWriter := macaron.NewResponseWriter("GET", responseRecorder) + if fn != nil { + fn(responseWriter) + } + + return &m.ReqContext{ + SignedInUser: &m.SignedInUser{}, + Context: &macaron.Context{ + Req: macaron.Request{ + Request: httptest.NewRequest("GET", "/render", nil), + }, + Resp: responseWriter, + }, + } + } + + Convey("When response header Set-Cookie is not set should remove proxied Set-Cookie header", func() { + ctx := setupCtx(nil) + proxy := NewDataSourceProxy(ds, plugin, ctx, "/render", &setting.Cfg{}) + proxy.HandleRequest() + So(proxy.ctx.Resp.Header().Get("Set-Cookie"), ShouldBeEmpty) + }) + + Convey("When response header Set-Cookie is set should remove proxied Set-Cookie header and restore the original Set-Cookie header", func() { + ctx := setupCtx(func(w http.ResponseWriter) { + w.Header().Set("Set-Cookie", "important_cookie=important_value") + }) + proxy := NewDataSourceProxy(ds, plugin, ctx, "/render", &setting.Cfg{}) + proxy.HandleRequest() + So(proxy.ctx.Resp.Header().Get("Set-Cookie"), ShouldEqual, "important_cookie=important_value") + }) + }) }) } +type CloseNotifierResponseRecorder struct { + *httptest.ResponseRecorder + closeChan chan bool +} + +func (r *CloseNotifierResponseRecorder) CloseNotify() <-chan bool { + r.closeChan = make(chan bool) + return r.closeChan +} + +func (r *CloseNotifierResponseRecorder) Close() { + close(r.closeChan) +} + // getDatasourceProxiedRequest is a helper for easier setup of tests based on global config and ReqContext. func getDatasourceProxiedRequest(ctx *m.ReqContext, cfg *setting.Cfg) *http.Request { plugin := &plugins.DataSourcePlugin{} diff --git a/pkg/cmd/grafana-cli/commands/install_command.go b/pkg/cmd/grafana-cli/commands/install_command.go index bec1d51bff46..99cef15e50e3 100644 --- a/pkg/cmd/grafana-cli/commands/install_command.go +++ b/pkg/cmd/grafana-cli/commands/install_command.go @@ -144,7 +144,7 @@ func downloadFile(pluginName, filePath, url string) (err error) { } }() - resp, err := http.Get(url) + resp, err := http.Get(url) // #nosec if err != nil { return err } @@ -167,7 +167,7 @@ func extractFiles(body []byte, pluginName string, filePath string) error { newFile := path.Join(filePath, RemoveGitBuildFromName(pluginName, zf.Name)) if zf.FileInfo().IsDir() { - err := os.Mkdir(newFile, 0777) + err := os.Mkdir(newFile, 0755) if permissionsError(err) { return fmt.Errorf(permissionsDeniedMessage, newFile) } diff --git a/pkg/services/notifications/codes.go b/pkg/services/notifications/codes.go index 4dbe76c1cad5..6382b609036b 100644 --- a/pkg/services/notifications/codes.go +++ b/pkg/services/notifications/codes.go @@ -7,6 +7,7 @@ import ( "time" "github.com/Unknwon/com" + m "github.com/grafana/grafana/pkg/models" "github.com/grafana/grafana/pkg/setting" ) diff --git a/scripts/backend-lint.sh b/scripts/backend-lint.sh index 304f91550e0c..064b8626fb2c 100755 --- a/scripts/backend-lint.sh +++ b/scripts/backend-lint.sh @@ -39,4 +39,7 @@ exit_if_fail go vet ./pkg/... exit_if_fail revive -formatter stylish -config ./scripts/revive.toml # TODO recheck the rules and leave only necessary exclusions -#exit_if_fail gosec -quiet -exclude=G104,G107,G201,G202,G204,G301,G302,G304,G402,G501,G505,G401 ./pkg/... +# exit_if_fail gosec -quiet \ +# -exclude=G104,G107,G201,G202,G204,G301,G304,G401,G402,G501 \ +# -conf=./scripts/gosec.json \ +# ./pkg/... diff --git a/scripts/gosec.json b/scripts/gosec.json new file mode 100644 index 000000000000..19c4500d53a9 --- /dev/null +++ b/scripts/gosec.json @@ -0,0 +1,4 @@ +{ + "G302": "0660", + "G301": "0755" +}