diff --git a/CHANGELOG.md b/CHANGELOG.md index 2215d0ff660..72211224636 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -12,6 +12,7 @@ * **dashboard**: fix for collapse row by clicking on row title, fixes [#3065](https://github.com/grafana/grafana/issues/3065) * **influxdb**: fix for relative time ranges `last x months` and `last x years`, fixes [#3067](https://github.com/grafana/grafana/issues/3067) * **graph**: layout fix for color picker when right side legend was enabled, fixes [#3093](https://github.com/grafana/grafana/issues/3093) +* **elasticsearch**: disabling elastic query (via eye) caused error, fixes [#3300](https://github.com/grafana/grafana/issues/3300) # 2.5 (2015-10-28) diff --git a/docs/sources/reference/http_api.md b/docs/sources/reference/http_api.md index eb1e235b1f7..5c917a7096f 100644 --- a/docs/sources/reference/http_api.md +++ b/docs/sources/reference/http_api.md @@ -36,9 +36,9 @@ You use the token in all requests in the `Authorization` header, like this: **Example**: - GET http://your.grafana.com/api/dashboards/db/mydash HTTP/1.1 - Accept: application/json - Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk + GET http://your.grafana.com/api/dashboards/db/mydash HTTP/1.1 + Accept: application/json + Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk The `Authorization` header value should be `Bearer `. @@ -52,26 +52,26 @@ Creates a new dashboard or updates an existing dashboard. **Example Request for new dashboard**: - POST /api/dashboards/db HTTP/1.1 - Accept: application/json - Content-Type: application/json - Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk + POST /api/dashboards/db HTTP/1.1 + Accept: application/json + Content-Type: application/json + Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk - { - "dashboard": { - "id": null, - "title": "Production Overview", - "tags": [ "templated" ], - "timezone": "browser", - "rows": [ - { - } - ], - "schemaVersion": 6, - "version": 0 - }, - "overwrite": false - } + { + "dashboard": { + "id": null, + "title": "Production Overview", + "tags": [ "templated" ], + "timezone": "browser", + "rows": [ + { + } + ], + "schemaVersion": 6, + "version": 0 + }, + "overwrite": false + } JSON Body schema: @@ -119,34 +119,34 @@ Will return the dashboard given the dashboard slug. Slug is the url friendly ver **Example Request**: - GET /api/dashboards/db/production-overview HTTP/1.1 - Accept: application/json - Content-Type: application/json - Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk + GET /api/dashboards/db/production-overview HTTP/1.1 + Accept: application/json + Content-Type: application/json + Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk **Example Response**: - HTTP/1.1 200 - Content-Type: application/json + HTTP/1.1 200 + Content-Type: application/json - { - "meta": { - "isStarred": false, - "slug": "production-overview" - }, - "model": { - "id": null, - "title": "Production Overview", - "tags": [ "templated" ], - "timezone": "browser", - "rows": [ - { - } - ] - "schemaVersion": 6, - "version": 0 - }, - } + { + "meta": { + "isStarred": false, + "slug": "production-overview" + }, + "model": { + "id": null, + "title": "Production Overview", + "tags": [ "templated" ], + "timezone": "browser", + "rows": [ + { + } + ] + "schemaVersion": 6, + "version": 0 + }, + } ### Delete dashboard @@ -156,17 +156,17 @@ The above will delete the dashboard with the specified slug. The slug is the url **Example Request**: - DELETE /api/dashboards/db/test HTTP/1.1 - Accept: application/json - Content-Type: application/json - Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk + DELETE /api/dashboards/db/test HTTP/1.1 + Accept: application/json + Content-Type: application/json + Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk **Example Response**: - HTTP/1.1 200 - Content-Type: application/json + HTTP/1.1 200 + Content-Type: application/json - {"title": "Test"} + {"title": "Test"} ### Gets the home dashboard @@ -176,53 +176,53 @@ Will return the home dashboard. **Example Request**: - GET /api/dashboards/home HTTP/1.1 - Accept: application/json - Content-Type: application/json - Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk + GET /api/dashboards/home HTTP/1.1 + Accept: application/json + Content-Type: application/json + Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk **Example Response**: - HTTP/1.1 200 - Content-Type: application/json + HTTP/1.1 200 + Content-Type: application/json - { - "meta": { - "isHome":true, - "canSave":false, - "canEdit":false, - "canStar":false, - "slug":"", - "expires":"0001-01-01T00:00:00Z", - "created":"0001-01-01T00:00:00Z" - }, - "dashboard": { - "editable":false, - "hideControls":true, - "nav":[ - { - "enable":false, - "type":"timepicker" - } - ], - "rows": [ - { - - } - ], - "style":"dark", - "tags":[], - "templating":{ - "list":[ - ] - }, - "time":{ - }, - "timezone":"browser", - "title":"Home", - "version":5 - } + { + "meta": { + "isHome":true, + "canSave":false, + "canEdit":false, + "canStar":false, + "slug":"", + "expires":"0001-01-01T00:00:00Z", + "created":"0001-01-01T00:00:00Z" + }, + "dashboard": { + "editable":false, + "hideControls":true, + "nav":[ + { + "enable":false, + "type":"timepicker" } + ], + "rows": [ + { + + } + ], + "style":"dark", + "tags":[], + "templating":{ + "list":[ + ] + }, + "time":{ + }, + "timezone":"browser", + "title":"Home", + "version":5 + } + } ### Tags for Dashboard @@ -233,27 +233,27 @@ Get all tabs of dashboards **Example Request**: - GET /api/dashboards/home HTTP/1.1 - Accept: application/json - Content-Type: application/json - Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk + GET /api/dashboards/home HTTP/1.1 + Accept: application/json + Content-Type: application/json + Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk **Example Response**: - HTTP/1.1 200 - Content-Type: application/json + HTTP/1.1 200 + Content-Type: application/json + + [ + { + "term":"tag1", + "count":1 + }, + { + "term":"tag2", + "count":4 + } + ] - [ - { - "term":"tag1", - "count":1 - }, - { - "term":"tag2", - "count":4 - } - ] - ### Dashboard from JSON file `GET /file/:file` @@ -271,27 +271,27 @@ Status Codes: **Example Request**: - GET /api/search?query=MyDashboard&starred=true&tag=prod HTTP/1.1 - Accept: application/json - Content-Type: application/json - Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk + GET /api/search?query=MyDashboard&starred=true&tag=prod HTTP/1.1 + Accept: application/json + Content-Type: application/json + Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk **Example Response**: - HTTP/1.1 200 - Content-Type: application/json - - [ - { - "id":1, - "title":"Production Overview", - "uri":"db/production-overview", - "type":"dash-db", - "tags":[], - "isStarred":false - } - ] - + HTTP/1.1 200 + Content-Type: application/json + + [ + { + "id":1, + "title":"Production Overview", + "uri":"db/production-overview", + "type":"dash-db", + "tags":[], + "isStarred":false + } + ] + ## Data sources ### Get all datasources @@ -300,34 +300,34 @@ Status Codes: **Example Request**: - GET /api/datasources HTTP/1.1 - Accept: application/json - Content-Type: application/json - Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk + GET /api/datasources HTTP/1.1 + Accept: application/json + Content-Type: application/json + Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk **Example Response**: - HTTP/1.1 200 - Content-Type: application/json + HTTP/1.1 200 + Content-Type: application/json - [ - { - "id":1, - "orgId":1, - "name":"datasource_elastic", - "type":"elasticsearch", - "access":"proxy", - "url":"http://mydatasource.com", - "password":"", - "user":"", - "database":"grafana-dash", - "basicAuth":false, - "basicAuthUser":"", - "basicAuthPassword":"", - "isDefault":false, - "jsonData":null - } - ] + [ + { + "id":1, + "orgId":1, + "name":"datasource_elastic", + "type":"elasticsearch", + "access":"proxy", + "url":"http://mydatasource.com", + "password":"", + "user":"", + "database":"grafana-dash", + "basicAuth":false, + "basicAuthUser":"", + "basicAuthPassword":"", + "isDefault":false, + "jsonData":null + } + ] ### Get a single data sources by Id @@ -335,32 +335,32 @@ Status Codes: **Example Request**: - GET /api/datasources/1 HTTP/1.1 - Accept: application/json - Content-Type: application/json - Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk + GET /api/datasources/1 HTTP/1.1 + Accept: application/json + Content-Type: application/json + Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk **Example Response**: - HTTP/1.1 200 - Content-Type: application/json + HTTP/1.1 200 + Content-Type: application/json - { - "id":1, - "orgId":1, - "name":"test_datasource", - "type":"graphite", - "access":"proxy", - "url":"http://mydatasource.com", - "password":"", - "user":"", - "database":"", - "basicAuth":false, - "basicAuthUser":"", - "basicAuthPassword":"", - "isDefault":false, - "jsonData":null - } + { + "id":1, + "orgId":1, + "name":"test_datasource", + "type":"graphite", + "access":"proxy", + "url":"http://mydatasource.com", + "password":"", + "user":"", + "database":"", + "basicAuth":false, + "basicAuthUser":"", + "basicAuthPassword":"", + "isDefault":false, + "jsonData":null + } ### Create data source @@ -368,26 +368,26 @@ Status Codes: **Example Request**: - POST /api/datasources HTTP/1.1 - Accept: application/json - Content-Type: application/json - Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk + POST /api/datasources HTTP/1.1 + Accept: application/json + Content-Type: application/json + Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk - { - "name":"test_datasource", - "type":"graphite", - "url":"http://mydatasource.com", - "access":"proxy", - "basicAuth":false - } + { + "name":"test_datasource", + "type":"graphite", + "url":"http://mydatasource.com", + "access":"proxy", + "basicAuth":false + } **Example Response**: - HTTP/1.1 200 - Content-Type: application/json + HTTP/1.1 200 + Content-Type: application/json - {"id":1,"message":"Datasource added"} + {"id":1,"message":"Datasource added"} ### Update an existing data source @@ -395,34 +395,34 @@ Status Codes: **Example Request**: - PUT /api/datasources/1 HTTP/1.1 - Accept: application/json - Content-Type: application/json - Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk - - { - "id":1, - "orgId":1, - "name":"test_datasource", - "type":"graphite", - "access":"proxy", - "url":"http://mydatasource.com", - "password":"", - "user":"", - "database":"", - "basicAuth":true, - "basicAuthUser":"basicuser", - "basicAuthPassword":"basicuser", - "isDefault":false, - "jsonData":null - } + PUT /api/datasources/1 HTTP/1.1 + Accept: application/json + Content-Type: application/json + Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk + + { + "id":1, + "orgId":1, + "name":"test_datasource", + "type":"graphite", + "access":"proxy", + "url":"http://mydatasource.com", + "password":"", + "user":"", + "database":"", + "basicAuth":true, + "basicAuthUser":"basicuser", + "basicAuthPassword":"basicuser", + "isDefault":false, + "jsonData":null + } **Example Response**: - HTTP/1.1 200 - Content-Type: application/json + HTTP/1.1 200 + Content-Type: application/json - {"message":"Datasource updated"} + {"message":"Datasource updated"} ### Delete an existing data source @@ -430,17 +430,17 @@ Status Codes: **Example Request**: - DELETE /api/datasources/1 HTTP/1.1 - Accept: application/json - Content-Type: application/json - Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk + DELETE /api/datasources/1 HTTP/1.1 + Accept: application/json + Content-Type: application/json + Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk **Example Response**: - HTTP/1.1 200 - Content-Type: application/json + HTTP/1.1 200 + Content-Type: application/json - {"message":"Data source deleted"} + {"message":"Data source deleted"} ### Available data source types @@ -448,29 +448,29 @@ Status Codes: **Example Request**: - GET /api/datasources/plugins HTTP/1.1 - Accept: application/json - Content-Type: application/json - Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk - + GET /api/datasources/plugins HTTP/1.1 + Accept: application/json + Content-Type: application/json + Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk + **Example Response**: - HTTP/1.1 200 - Content-Type: application/json + HTTP/1.1 200 + Content-Type: application/json + + { + "grafana":{ + "metrics":true,"module":"plugins/datasource/grafana/datasource", + "name":"Grafana (for testing)", + "partials":{ + "query":"app/plugins/datasource/grafana/partials/query.editor.html" + }, + "pluginType":"datasource", + "serviceName":"GrafanaDatasource", + "type":"grafana" + } + } - { - "grafana":{ - "metrics":true,"module":"plugins/datasource/grafana/datasource", - "name":"Grafana (for testing)", - "partials":{ - "query":"app/plugins/datasource/grafana/partials/query.editor.html" - }, - "pluginType":"datasource", - "serviceName":"GrafanaDatasource", - "type":"grafana" - } - } - ## Data source proxy calls `GET /api/datasources/proxy/:datasourceId/*` @@ -485,20 +485,20 @@ Proxies all calls to the actual datasource. **Example Request**: - GET /api/org HTTP/1.1 - Accept: application/json - Content-Type: application/json - Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk + GET /api/org HTTP/1.1 + Accept: application/json + Content-Type: application/json + Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk **Example Response**: - HTTP/1.1 200 - Content-Type: application/json + HTTP/1.1 200 + Content-Type: application/json - { - "id":1, - "name":"Main Org." - } + { + "id":1, + "name":"Main Org." + } ### Update current Organisation @@ -506,49 +506,49 @@ Proxies all calls to the actual datasource. **Example Request**: - PUT /api/org HTTP/1.1 - Accept: application/json - Content-Type: application/json - Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk + PUT /api/org HTTP/1.1 + Accept: application/json + Content-Type: application/json + Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk + + { + "name":"Main Org." + } + - { - "name":"Main Org." - } - - **Example Response**: - HTTP/1.1 200 - Content-Type: application/json + HTTP/1.1 200 + Content-Type: application/json + + {"message":"Organization updated"} + - {"message":"Organization updated"} - - ### Get all users within the actual organisation `GET /api/org/users` **Example Request**: - GET /api/org/users HTTP/1.1 - Accept: application/json - Content-Type: application/json - Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk + GET /api/org/users HTTP/1.1 + Accept: application/json + Content-Type: application/json + Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk **Example Response**: - HTTP/1.1 200 - Content-Type: application/json + HTTP/1.1 200 + Content-Type: application/json - [ - { - "orgId":1, - "userId":1, - "email":"admin@mygraf.com", - "login":"admin", - "role":"Admin" - } - ] + [ + { + "orgId":1, + "userId":1, + "email":"admin@mygraf.com", + "login":"admin", + "role":"Admin" + } + ] ### Add a new user to the actual organisation @@ -558,65 +558,65 @@ Adds a global user to the actual organisation. **Example Request**: - POST /api/org/users HTTP/1.1 - Accept: application/json - Content-Type: application/json - Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk + POST /api/org/users HTTP/1.1 + Accept: application/json + Content-Type: application/json + Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk + + { + "role": "Admin", + "loginOrEmail": "admin" + } + - { - "role": "Admin", - "loginOrEmail": "admin" - } - - **Example Response**: - HTTP/1.1 200 - Content-Type: application/json - - {"message":"User added to organization"} - + HTTP/1.1 200 + Content-Type: application/json + + {"message":"User added to organization"} + ### Updates the given user `PATCH /api/org/users/:userId` **Example Request**: - PATCH /api/org/users/1 HTTP/1.1 - Accept: application/json - Content-Type: application/json - Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk + PATCH /api/org/users/1 HTTP/1.1 + Accept: application/json + Content-Type: application/json + Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk + + { + "role": "Viewer", + } + - { - "role": "Viewer", - } - - **Example Response**: - HTTP/1.1 200 - Content-Type: application/json - - {"message":"Organization user updated"} + HTTP/1.1 200 + Content-Type: application/json + + {"message":"Organization user updated"} + - ### Delete user in actual organisation `DELETE /api/org/users/:userId` **Example Request**: - DELETE /api/org/users/1 HTTP/1.1 - Accept: application/json - Content-Type: application/json - Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk + DELETE /api/org/users/1 HTTP/1.1 + Accept: application/json + Content-Type: application/json + Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk **Example Response**: - HTTP/1.1 200 - Content-Type: application/json - - {"message":"User removed from organization"} + HTTP/1.1 200 + Content-Type: application/json + + {"message":"User removed from organization"} ## Organisations @@ -627,22 +627,22 @@ Adds a global user to the actual organisation. **Example Request**: - GET /api/orgs HTTP/1.1 - Accept: application/json - Content-Type: application/json - Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk + GET /api/orgs HTTP/1.1 + Accept: application/json + Content-Type: application/json + Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk **Example Response**: - HTTP/1.1 200 - Content-Type: application/json - - [ - { - "id":1, - "name":"Main Org." - } - ] + HTTP/1.1 200 + Content-Type: application/json + + [ + { + "id":1, + "name":"Main Org." + } + ] ### Update Organisation @@ -652,22 +652,22 @@ Update Organisation, fields *Adress 1*, *Adress 2*, *City* are not implemented y **Example Request**: - PUT /api/orgs/1 HTTP/1.1 - Accept: application/json - Content-Type: application/json - Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk + PUT /api/orgs/1 HTTP/1.1 + Accept: application/json + Content-Type: application/json + Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk + + { + "name":"Main Org 2." + } + - { - "name":"Main Org 2." - } - - **Example Response**: - HTTP/1.1 200 - Content-Type: application/json - - {"message":"Organization updated"} + HTTP/1.1 200 + Content-Type: application/json + + {"message":"Organization updated"} ### Get Users in Organisation @@ -675,24 +675,24 @@ Update Organisation, fields *Adress 1*, *Adress 2*, *City* are not implemented y **Example Request**: - GET /api/orgs/1/users HTTP/1.1 - Accept: application/json - Content-Type: application/json - Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk + GET /api/orgs/1/users HTTP/1.1 + Accept: application/json + Content-Type: application/json + Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk **Example Response**: - HTTP/1.1 200 - Content-Type: application/json - [ - { - "orgId":1, - "userId":1, - "email":"admin@mygraf.com", - "login":"admin", - "role":"Admin" - } - ] + HTTP/1.1 200 + Content-Type: application/json + [ + { + "orgId":1, + "userId":1, + "email":"admin@mygraf.com", + "login":"admin", + "role":"Admin" + } + ] ### Add User in Organisation @@ -700,22 +700,22 @@ Update Organisation, fields *Adress 1*, *Adress 2*, *City* are not implemented y **Example Request**: - POST /api/orgs/1/users HTTP/1.1 - Accept: application/json - Content-Type: application/json - Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk + POST /api/orgs/1/users HTTP/1.1 + Accept: application/json + Content-Type: application/json + Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk + + { + "loginOrEmail":"user", + "role":"Viewer" + } - { - "loginOrEmail":"user", - "role":"Viewer" - } - **Example Response**: - HTTP/1.1 200 - Content-Type: application/json - - {"message":"User added to organization"} + HTTP/1.1 200 + Content-Type: application/json + + {"message":"User added to organization"} ### Update Users in Organisation @@ -723,21 +723,21 @@ Update Organisation, fields *Adress 1*, *Adress 2*, *City* are not implemented y **Example Request**: - PATCH /api/orgs/1/users/2 HTTP/1.1 - Accept: application/json - Content-Type: application/json - Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk + PATCH /api/orgs/1/users/2 HTTP/1.1 + Accept: application/json + Content-Type: application/json + Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk + + { + "role":"Admin" + } - { - "role":"Admin" - } - **Example Response**: - HTTP/1.1 200 - Content-Type: application/json - - {"message":"Organization user updated"} + HTTP/1.1 200 + Content-Type: application/json + + {"message":"Organization user updated"} ### Delete User in Organisation @@ -745,17 +745,17 @@ Update Organisation, fields *Adress 1*, *Adress 2*, *City* are not implemented y **Example Request**: - DELETE /api/orgs/1/users/2 HTTP/1.1 - Accept: application/json - Content-Type: application/json - Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk - + DELETE /api/orgs/1/users/2 HTTP/1.1 + Accept: application/json + Content-Type: application/json + Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk + **Example Response**: - HTTP/1.1 200 - Content-Type: application/json - - {"message":"User removed from organization"} + HTTP/1.1 200 + Content-Type: application/json + + {"message":"User removed from organization"} ## Users @@ -765,31 +765,32 @@ Update Organisation, fields *Adress 1*, *Adress 2*, *City* are not implemented y **Example Request**: - GET /api/users HTTP/1.1 - Accept: application/json - Content-Type: application/json - Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk + GET /api/users HTTP/1.1 + Accept: application/json + Content-Type: application/json + Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk **Example Response**: - HTTP/1.1 200 - Content-Type: application/json - [ - { - "id": 1, - "name": "Admin", - "login": "admin", - "email": "admin@mygraf.com", - "isAdmin": true - }, - { - "id": 2, - "name": "User", - "login": "user", - "email": "user@mygraf.com" - "isAdmin": false - } - ] + HTTP/1.1 200 + Content-Type: application/json + + [ + { + "id": 1, + "name": "Admin", + "login": "admin", + "email": "admin@mygraf.com", + "isAdmin": true + }, + { + "id": 2, + "name": "User", + "login": "user", + "email": "user@mygraf.com" + "isAdmin": false + } + ] ### Get single user by Id @@ -797,24 +798,24 @@ Update Organisation, fields *Adress 1*, *Adress 2*, *City* are not implemented y **Example Request**: - GET /api/users/1 HTTP/1.1 - Accept: application/json - Content-Type: application/json - Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk + GET /api/users/1 HTTP/1.1 + Accept: application/json + Content-Type: application/json + Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk **Example Response**: - HTTP/1.1 200 - Content-Type: application/json - - { - "email": "user@mygraf.com" - "name": "admin", - "login": "admin", - "theme": "light", - "orgId": 1, - "isGrafanaAdmin": true - } + HTTP/1.1 200 + Content-Type: application/json + + { + "email": "user@mygraf.com" + "name": "admin", + "login": "admin", + "theme": "light", + "orgId": 1, + "isGrafanaAdmin": true + } ### User Update @@ -822,23 +823,24 @@ Update Organisation, fields *Adress 1*, *Adress 2*, *City* are not implemented y **Example Request**: - PUT /api/users/2 HTTP/1.1 - Accept: application/json - Content-Type: application/json - Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk - - { - "email":"user@mygraf.com", - "name":"User2", - "login":"user", - "theme":"light" - } + PUT /api/users/2 HTTP/1.1 + Accept: application/json + Content-Type: application/json + Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk + + { + "email":"user@mygraf.com", + "name":"User2", + "login":"user", + "theme":"light" + } + **Example Response**: - - HTTP/1.1 200 - Content-Type: application/json - - {"message":"User updated"} + + HTTP/1.1 200 + Content-Type: application/json + + {"message":"User updated"} ### Get Organisations for user @@ -847,23 +849,23 @@ Update Organisation, fields *Adress 1*, *Adress 2*, *City* are not implemented y **Example Request**: - GET /api/users/1/orgs HTTP/1.1 - Accept: application/json - Content-Type: application/json - Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk + GET /api/users/1/orgs HTTP/1.1 + Accept: application/json + Content-Type: application/json + Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk **Example Response**: - HTTP/1.1 200 - Content-Type: application/json + HTTP/1.1 200 + Content-Type: application/json - [ - { - "orgId":1, - "name":"Main Org.", - "role":"Admin" - } - ] + [ + { + "orgId":1, + "name":"Main Org.", + "role":"Admin" + } + ] ## User @@ -873,24 +875,24 @@ Update Organisation, fields *Adress 1*, *Adress 2*, *City* are not implemented y **Example Request**: - GET /api/user HTTP/1.1 - Accept: application/json - Content-Type: application/json - Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk - + GET /api/user HTTP/1.1 + Accept: application/json + Content-Type: application/json + Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk + **Example Response**: - HTTP/1.1 200 - Content-Type: application/json - - { - "email":"admin@mygraf.com", - "name":"Admin", - "login":"admin", - "theme":"light", - "orgId":1, - "isGrafanaAdmin":true - } + HTTP/1.1 200 + Content-Type: application/json + + { + "email":"admin@mygraf.com", + "name":"Admin", + "login":"admin", + "theme":"light", + "orgId":1, + "isGrafanaAdmin":true + } ### Change Password @@ -900,22 +902,23 @@ Changes the password for the user **Example Request**: - PUT /api/user/password HTTP/1.1 - Accept: application/json - Content-Type: application/json - Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk + PUT /api/user/password HTTP/1.1 + Accept: application/json + Content-Type: application/json + Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk + + { + "oldPassword": "old_password", + "newPassword": "new_password", + "confirmNew": "confirm_new_password" + } - { - "password": ""new_password" - } - - **Example Response**: - HTTP/1.1 200 - Content-Type: application/json - - {"message":"User password updated"} + HTTP/1.1 200 + Content-Type: application/json + + {"message":"User password changed"} ### Switch user context @@ -925,17 +928,17 @@ Switch user context to the given organisation. **Example Request**: - POST /api/user/using/2 HTTP/1.1 - Accept: application/json - Content-Type: application/json - Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk - + POST /api/user/using/2 HTTP/1.1 + Accept: application/json + Content-Type: application/json + Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk + **Example Response**: - HTTP/1.1 200 - Content-Type: application/json - - {"message":"Active organization changed"} + HTTP/1.1 200 + Content-Type: application/json + + {"message":"Active organization changed"} ### Organisations of the actual User @@ -945,23 +948,23 @@ Return a list of all organisations of the current user. **Example Request**: - GET /api/user/orgs HTTP/1.1 - Accept: application/json - Content-Type: application/json - Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk - + GET /api/user/orgs HTTP/1.1 + Accept: application/json + Content-Type: application/json + Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk + **Example Response**: - HTTP/1.1 200 - Content-Type: application/json - - [ - { - "orgId":1, - "name":"Main Org.", - "role":"Admin" - } - ] + HTTP/1.1 200 + Content-Type: application/json + + [ + { + "orgId":1, + "name":"Main Org.", + "role":"Admin" + } + ] ### Star a dashboard @@ -971,17 +974,17 @@ Stars the given Dashboard for the actual user. **Example Request**: - POST /api/user/stars/dashboard/1 HTTP/1.1 - Accept: application/json - Content-Type: application/json - Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk - + POST /api/user/stars/dashboard/1 HTTP/1.1 + Accept: application/json + Content-Type: application/json + Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk + **Example Response**: - HTTP/1.1 200 - Content-Type: application/json - - {"message":"Dashboard starred!"} + HTTP/1.1 200 + Content-Type: application/json + + {"message":"Dashboard starred!"} ### Unstar a dashboard @@ -991,17 +994,17 @@ Deletes the starring of the given Dashboard for the actual user. **Example Request**: - DELETE /api/user/stars/dashboard/1 HTTP/1.1 - Accept: application/json - Content-Type: application/json - Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk - + DELETE /api/user/stars/dashboard/1 HTTP/1.1 + Accept: application/json + Content-Type: application/json + Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk + **Example Response**: - HTTP/1.1 200 - Content-Type: application/json - - {"message":"Dashboard unstarred"} + HTTP/1.1 200 + Content-Type: application/json + + {"message":"Dashboard unstarred"} ## Snapshots @@ -1012,112 +1015,112 @@ Deletes the starring of the given Dashboard for the actual user. **Example Request**: - POST /api/snapshots HTTP/1.1 - Accept: application/json - Content-Type: application/json - Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk - - { - "dashboard": { - "editable":false, - "hideControls":true, - "nav":[ - { - "enable":false, - "type":"timepicker" - } - ], - "rows": [ - { - - } - ], - "style":"dark", - "tags":[], - "templating":{ - "list":[ - ] - }, - "time":{ - }, - "timezone":"browser", - "title":"Home", - "version":5 - } - "expires": 3600 - } - + POST /api/snapshots HTTP/1.1 + Accept: application/json + Content-Type: application/json + Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk + + { + "dashboard": { + "editable":false, + "hideControls":true, + "nav":[ + { + "enable":false, + "type":"timepicker" + } + ], + "rows": [ + { + + } + ], + "style":"dark", + "tags":[], + "templating":{ + "list":[ + ] + }, + "time":{ + }, + "timezone":"browser", + "title":"Home", + "version":5 + } + "expires": 3600 + } + **Example Response**: - HTTP/1.1 200 - Content-Type: application/json - { - "deleteKey":"XXXXXXX", - "deleteUrl":"myurl/dashboard/snapshot/XXXXXXX", - "key":"YYYYYYY", - "url":"myurl/dashboard/snapshot/YYYYYYY" - } + HTTP/1.1 200 + Content-Type: application/json + { + "deleteKey":"XXXXXXX", + "deleteUrl":"myurl/dashboard/snapshot/XXXXXXX", + "key":"YYYYYYY", + "url":"myurl/dashboard/snapshot/YYYYYYY" + } Keys: - **deleteKey** – Key generated to delete the snapshot - **key** – Key generated to share the dashboard - + ### Get Snapshot by Id - + `GET /api/snapshots/:key` **Example Request**: - GET /api/snapshots/YYYYYYY HTTP/1.1 - Accept: application/json - Content-Type: application/json - Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk - + GET /api/snapshots/YYYYYYY HTTP/1.1 + Accept: application/json + Content-Type: application/json + Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk + **Example Response**: - HTTP/1.1 200 - Content-Type: application/json - - { - "meta":{ - "isSnapshot":true, - "type":"snapshot", - "canSave":false, - "canEdit":false, - "canStar":false, - "slug":"", - "expires":"2200-13-32T25:23:23+02:00", - "created":"2200-13-32T28:24:23+02:00"}, - - { - "dashboard": { - "editable":false, - "hideControls":true, - "nav":[ - { - "enable":false, - "type":"timepicker" - } - ], - "rows": [ - { - - } - ], - "style":"dark", - "tags":[], - "templating":{ - "list":[ - ] - }, - "time":{ - }, - "timezone":"browser", - "title":"Home", - "version":5 - } - } + HTTP/1.1 200 + Content-Type: application/json + + { + "meta":{ + "isSnapshot":true, + "type":"snapshot", + "canSave":false, + "canEdit":false, + "canStar":false, + "slug":"", + "expires":"2200-13-32T25:23:23+02:00", + "created":"2200-13-32T28:24:23+02:00"}, + + { + "dashboard": { + "editable":false, + "hideControls":true, + "nav":[ + { + "enable":false, + "type":"timepicker" + } + ], + "rows": [ + { + + } + ], + "style":"dark", + "tags":[], + "templating":{ + "list":[ + ] + }, + "time":{ + }, + "timezone":"browser", + "title":"Home", + "version":5 + } + } ### Delete Snapshot by Id @@ -1125,18 +1128,18 @@ Keys: **Example Request**: - GET /api/snapshots/YYYYYYY HTTP/1.1 - Accept: application/json - Content-Type: application/json - Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk + GET /api/snapshots/YYYYYYY HTTP/1.1 + Accept: application/json + Content-Type: application/json + Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk **Example Response**: - HTTP/1.1 200 - Content-Type: application/json - - {"message":"Snapshot deleted. It might take an hour before it's cleared from a CDN cache."} - + HTTP/1.1 200 + Content-Type: application/json + + {"message":"Snapshot deleted. It might take an hour before it's cleared from a CDN cache."} + ## Frontend Settings @@ -1146,45 +1149,45 @@ Keys: **Example Request**: - GET /api/frontend/settings HTTP/1.1 - Accept: application/json - Content-Type: application/json - Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk + GET /api/frontend/settings HTTP/1.1 + Accept: application/json + Content-Type: application/json + Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk **Example Response**: - HTTP/1.1 200 - Content-Type: application/json - - { - "allowOrgCreate":true, - "appSubUrl":"", - "buildInfo":{ - "buildstamp":xxxxxx, - "commit":"vyyyy", - "version":"zzzzz" - }, - "datasources":{ - "datasourcename":{ - "index":"grafana-dash", - "meta":{ - "annotations":true, - "module":"plugins/datasource/grafana/datasource", - "name":"Grafana", - "partials":{ - "annotations":"app/plugins/datasource/grafana/partials/annotations.editor.html", - "config":"app/plugins/datasource/grafana/partials/config.html" - }, - "pluginType":"datasource", - "serviceName":"Grafana", - "type":"grafanasearch" - } - } - } - - defaultDatasource: "Grafana" - } - + HTTP/1.1 200 + Content-Type: application/json + + { + "allowOrgCreate":true, + "appSubUrl":"", + "buildInfo":{ + "buildstamp":xxxxxx, + "commit":"vyyyy", + "version":"zzzzz" + }, + "datasources":{ + "datasourcename":{ + "index":"grafana-dash", + "meta":{ + "annotations":true, + "module":"plugins/datasource/grafana/datasource", + "name":"Grafana", + "partials":{ + "annotations":"app/plugins/datasource/grafana/partials/annotations.editor.html", + "config":"app/plugins/datasource/grafana/partials/config.html" + }, + "pluginType":"datasource", + "serviceName":"Grafana", + "type":"grafanasearch" + } + } + } + + defaultDatasource: "Grafana" + } + ## Login ### Renew session based on remember cookie @@ -1193,18 +1196,18 @@ Keys: **Example Request**: - GET /api/login/ping HTTP/1.1 - Accept: application/json - Content-Type: application/json - Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk + GET /api/login/ping HTTP/1.1 + Accept: application/json + Content-Type: application/json + Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk **Example Response**: - HTTP/1.1 200 - Content-Type: application/json - - {"message": "Logged in"} - + HTTP/1.1 200 + Content-Type: application/json + + {"message": "Logged in"} + ## Admin ### Settings @@ -1213,155 +1216,155 @@ Keys: **Example Request**: - GET /api/admin/settings - Accept: application/json - Content-Type: application/json - Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk + GET /api/admin/settings + Accept: application/json + Content-Type: application/json + Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk **Example Response**: - HTTP/1.1 200 - Content-Type: application/json - - { - "DEFAULT": - { - "app_mode":"production"}, - "analytics": - { - "google_analytics_ua_id":"", - "reporting_enabled":"false" - }, - "auth.anonymous":{ - "enabled":"true", - "org_name":"Main Org.", - "org_role":"Viewer" - }, - "auth.basic":{ - "enabled":"false" - }, - "auth.github":{ - "allow_sign_up":"false", - "allowed_domains":"", - "allowed_organizations":"", - "api_url":"https://api.github.com/user", - "auth_url":"https://github.com/login/oauth/authorize", - "client_id":"some_id", - "client_secret":"************", - "enabled":"false", - "scopes":"user:email", - "team_ids":"", - "token_url":"https://github.com/login/oauth/access_token" - }, - "auth.google":{ - "allow_sign_up":"false","allowed_domains":"", - "api_url":"https://www.googleapis.com/oauth2/v1/userinfo", - "auth_url":"https://accounts.google.com/o/oauth2/auth", - "client_id":"some_client_id", - "client_secret":"************", - "enabled":"false", - "scopes":"https://www.googleapis.com/auth/userinfo.profile https://www.googleapis.com/auth/userinfo.email", - "token_url":"https://accounts.google.com/o/oauth2/token" - }, - "auth.ldap":{ - "config_file":"/etc/grafana/ldap.toml", - "enabled":"false" - }, - "auth.proxy":{ - "auto_sign_up":"true", - "enabled":"false", - "header_name":"X-WEBAUTH-USER", - "header_property":"username" - }, - "dashboards.json":{ - "enabled":"false", - "path":"/var/lib/grafana/dashboards" - }, - "database":{ - "host":"127.0.0.1:0000", - "name":"grafana", - "password":"************", - "path":"grafana.db", - "ssl_mode":"disable", - "type":"sqlite3", - "user":"root" - }, - "emails":{ - "templates_pattern":"emails/*.html", - "welcome_email_on_sign_up":"false" - }, - "event_publisher":{ - "enabled":"false", - "exchange":"grafana_events", - "rabbitmq_url":"amqp://localhost/" - }, - "log":{ - "buffer_len":"10000", - "level":"Info", - "mode":"file" - }, - "log.console":{ - "level":"" - }, - "log.file":{ - "daily_rotate":"true", - "file_name":"", - "level":"", - "log_rotate":"true", - "max_days":"7", - "max_lines":"1000000", - "max_lines_shift":"28", - "max_size_shift":"" - }, - "paths":{ - "data":"/tsdb/grafana", - "logs":"/logs/apps/grafana"}, - "security":{ - "admin_password":"************", - "admin_user":"admin", - "cookie_remember_name":"grafana_remember", - "cookie_username":"grafana_user", - "disable_gravatar":"false", - "login_remember_days":"7", - "secret_key":"************" - }, - "server":{ - "cert_file":"", - "cert_key":"", - "domain":"mygraf.com", - "enable_gzip":"false", - "enforce_domain":"false", - "http_addr":"127.0.0.1", - "http_port":"0000", - "protocol":"http", - "root_url":"%(protocol)s://%(domain)s:%(http_port)s/", - "router_logging":"true", - "static_root_path":"public" - }, - "session":{ - "cookie_name":"grafana_sess", - "cookie_secure":"false", - "gc_interval_time":"", - "provider":"file", - "provider_config":"sessions", - "session_life_time":"86400" - }, - "smtp":{ - "cert_file":"", - "enabled":"false", - "from_address":"admin@grafana.localhost", - "host":"localhost:25", - "key_file":"", - "password":"************", - "skip_verify":"false", - "user":""}, - "users":{ - "allow_org_create":"true", - "allow_sign_up":"false", - "auto_assign_org":"true", - "auto_assign_org_role":"Viewer" - } - } + HTTP/1.1 200 + Content-Type: application/json + + { + "DEFAULT": + { + "app_mode":"production"}, + "analytics": + { + "google_analytics_ua_id":"", + "reporting_enabled":"false" + }, + "auth.anonymous":{ + "enabled":"true", + "org_name":"Main Org.", + "org_role":"Viewer" + }, + "auth.basic":{ + "enabled":"false" + }, + "auth.github":{ + "allow_sign_up":"false", + "allowed_domains":"", + "allowed_organizations":"", + "api_url":"https://api.github.com/user", + "auth_url":"https://github.com/login/oauth/authorize", + "client_id":"some_id", + "client_secret":"************", + "enabled":"false", + "scopes":"user:email", + "team_ids":"", + "token_url":"https://github.com/login/oauth/access_token" + }, + "auth.google":{ + "allow_sign_up":"false","allowed_domains":"", + "api_url":"https://www.googleapis.com/oauth2/v1/userinfo", + "auth_url":"https://accounts.google.com/o/oauth2/auth", + "client_id":"some_client_id", + "client_secret":"************", + "enabled":"false", + "scopes":"https://www.googleapis.com/auth/userinfo.profile https://www.googleapis.com/auth/userinfo.email", + "token_url":"https://accounts.google.com/o/oauth2/token" + }, + "auth.ldap":{ + "config_file":"/etc/grafana/ldap.toml", + "enabled":"false" + }, + "auth.proxy":{ + "auto_sign_up":"true", + "enabled":"false", + "header_name":"X-WEBAUTH-USER", + "header_property":"username" + }, + "dashboards.json":{ + "enabled":"false", + "path":"/var/lib/grafana/dashboards" + }, + "database":{ + "host":"127.0.0.1:0000", + "name":"grafana", + "password":"************", + "path":"grafana.db", + "ssl_mode":"disable", + "type":"sqlite3", + "user":"root" + }, + "emails":{ + "templates_pattern":"emails/*.html", + "welcome_email_on_sign_up":"false" + }, + "event_publisher":{ + "enabled":"false", + "exchange":"grafana_events", + "rabbitmq_url":"amqp://localhost/" + }, + "log":{ + "buffer_len":"10000", + "level":"Info", + "mode":"file" + }, + "log.console":{ + "level":"" + }, + "log.file":{ + "daily_rotate":"true", + "file_name":"", + "level":"", + "log_rotate":"true", + "max_days":"7", + "max_lines":"1000000", + "max_lines_shift":"28", + "max_size_shift":"" + }, + "paths":{ + "data":"/tsdb/grafana", + "logs":"/logs/apps/grafana"}, + "security":{ + "admin_password":"************", + "admin_user":"admin", + "cookie_remember_name":"grafana_remember", + "cookie_username":"grafana_user", + "disable_gravatar":"false", + "login_remember_days":"7", + "secret_key":"************" + }, + "server":{ + "cert_file":"", + "cert_key":"", + "domain":"mygraf.com", + "enable_gzip":"false", + "enforce_domain":"false", + "http_addr":"127.0.0.1", + "http_port":"0000", + "protocol":"http", + "root_url":"%(protocol)s://%(domain)s:%(http_port)s/", + "router_logging":"true", + "static_root_path":"public" + }, + "session":{ + "cookie_name":"grafana_sess", + "cookie_secure":"false", + "gc_interval_time":"", + "provider":"file", + "provider_config":"sessions", + "session_life_time":"86400" + }, + "smtp":{ + "cert_file":"", + "enabled":"false", + "from_address":"admin@grafana.localhost", + "host":"localhost:25", + "key_file":"", + "password":"************", + "skip_verify":"false", + "user":""}, + "users":{ + "allow_org_create":"true", + "allow_sign_up":"false", + "auto_assign_org":"true", + "auto_assign_org_role":"Viewer" + } + } ### Global Users @@ -1371,24 +1374,24 @@ Create new user **Example Request**: - POST /api/admin/users HTTP/1.1 - Accept: application/json - Content-Type: application/json - Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk - - { - "name":"User", - "email":"user@graf.com", - "login":"user", - "password":"userpassword" - } + POST /api/admin/users HTTP/1.1 + Accept: application/json + Content-Type: application/json + Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk + + { + "name":"User", + "email":"user@graf.com", + "login":"user", + "password":"userpassword" + } **Example Response**: - HTTP/1.1 200 - Content-Type: application/json - - {"id":5,"message":"User created"} + HTTP/1.1 200 + Content-Type: application/json + + {"id":5,"message":"User created"} ### Password for User @@ -1398,17 +1401,17 @@ Change password for specific user **Example Request**: - PUT /api/admin/users/2/password HTTP/1.1 - Accept: application/json - Content-Type: application/json - Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk - + PUT /api/admin/users/2/password HTTP/1.1 + Accept: application/json + Content-Type: application/json + Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk + **Example Response**: - HTTP/1.1 200 - Content-Type: application/json - - {"password":"userpassword"} + HTTP/1.1 200 + Content-Type: application/json + + {"password":"userpassword"} ### Permissions @@ -1416,17 +1419,17 @@ Change password for specific user **Example Request**: - PUT /api/admin/users/2/permissions HTTP/1.1 - Accept: application/json - Content-Type: application/json - Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk - + PUT /api/admin/users/2/permissions HTTP/1.1 + Accept: application/json + Content-Type: application/json + Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk + **Example Response**: - HTTP/1.1 200 - Content-Type: application/json - - {message: "User permissions updated"} + HTTP/1.1 200 + Content-Type: application/json + + {message: "User permissions updated"} ### Delete global User @@ -1434,14 +1437,14 @@ Change password for specific user **Example Request**: - DELETE /api/admin/users/2 HTTP/1.1 - Accept: application/json - Content-Type: application/json - Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk + DELETE /api/admin/users/2 HTTP/1.1 + Accept: application/json + Content-Type: application/json + Authorization: Bearer eyJrIjoiT0tTcG1pUlY2RnVKZTFVaDFsNFZXdE9ZWmNrMkZYbk **Example Response**: - HTTP/1.1 200 - Content-Type: application/json - - {message: "User deleted"} + HTTP/1.1 200 + Content-Type: application/json + + {message: "User deleted"} diff --git a/public/app/panels/table/controller.ts b/public/app/panels/table/controller.ts index e2166f82577..4547a9d7896 100644 --- a/public/app/panels/table/controller.ts +++ b/public/app/panels/table/controller.ts @@ -27,7 +27,7 @@ export class TablePanelCtrl { var panelDefaults = { targets: [{}], transform: 'timeseries_to_rows', - pageSize: 50, + pageSize: null, showHeader: true, styles: [ { diff --git a/public/app/panels/table/editor.html b/public/app/panels/table/editor.html index a862a2b7776..27bf9002d56 100644 --- a/public/app/panels/table/editor.html +++ b/public/app/panels/table/editor.html @@ -44,7 +44,7 @@ Pagination (Page size)
  • -
  • diff --git a/public/app/panels/table/editor.ts b/public/app/panels/table/editor.ts index 228b41ccd57..2908023d330 100644 --- a/public/app/panels/table/editor.ts +++ b/public/app/panels/table/editor.ts @@ -38,7 +38,7 @@ export function tablePanelEditor() { scope.updateColumnsMenu = function(data) { scope.columnsMenu = transformers[scope.panel.transform].getColumns(data); - scope.showColumnOptions = scope.columnsMenu.length > 0; + scope.showColumnOptions = true; }; scope.$on('render', function(event, table, rawData) { @@ -51,6 +51,7 @@ export function tablePanelEditor() { }; scope.transformChanged = function() { + scope.panel.columns = []; scope.updateColumnsMenu(); scope.render(); }; diff --git a/public/app/panels/table/module.ts b/public/app/panels/table/module.ts index f09a7389a59..dbdc4d0ba25 100644 --- a/public/app/panels/table/module.ts +++ b/public/app/panels/table/module.ts @@ -45,7 +45,8 @@ export function tablePanel() { function appendPaginationControls(footerElem) { footerElem.empty(); - var pageCount = Math.ceil(data.rows.length / panel.pageSize); + var pageSize = panel.pageSize || 100; + var pageCount = Math.ceil(data.rows.length / pageSize); if (pageCount === 1) { return; } @@ -55,18 +56,12 @@ export function tablePanel() { var paginationList = $(''); - // var prevLink = $('
  • «
  • '); - // paginationList.append(prevLink); - for (var i = startPage; i < endPage; i++) { var activeClass = i === scope.pageIndex ? 'active' : ''; var pageLinkElem = $('
  • ' + (i+1) + '
  • '); paginationList.append(pageLinkElem); } - // var nextLink = $('
  • »
  • '); - // paginationList.append(nextLink); - footerElem.append(paginationList); } diff --git a/public/app/panels/table/renderer.ts b/public/app/panels/table/renderer.ts index 3ecb6d68643..a55a8bf2fac 100644 --- a/public/app/panels/table/renderer.ts +++ b/public/app/panels/table/renderer.ts @@ -119,8 +119,9 @@ export class TableRenderer { } render(page) { - let startPos = page * this.panel.pageSize; - let endPos = Math.min(startPos + this.panel.pageSize, this.table.rows.length); + let pageSize = this.panel.pageSize || 100; + let startPos = page * pageSize; + let endPos = Math.min(startPos + pageSize, this.table.rows.length); var html = ""; for (var y = startPos; y < endPos; y++) { diff --git a/public/app/panels/table/transformers.ts b/public/app/panels/table/transformers.ts index 48559f943bd..1a5482693e7 100644 --- a/public/app/panels/table/transformers.ts +++ b/public/app/panels/table/transformers.ts @@ -145,7 +145,7 @@ transformers['json'] = { var names: any = {}; for (var i = 0; i < data.length; i++) { var series = data[i]; - if (series.type === 'docs') { + if (series.type !== 'docs') { continue; } diff --git a/public/app/plugins/datasource/elasticsearch/datasource.js b/public/app/plugins/datasource/elasticsearch/datasource.js index ce370c639d2..9c749b9459e 100644 --- a/public/app/plugins/datasource/elasticsearch/datasource.js +++ b/public/app/plugins/datasource/elasticsearch/datasource.js @@ -163,11 +163,10 @@ function (angular, _, moment, kbn, ElasticQueryBuilder, IndexPattern, ElasticRes var payload = ""; var target; var sentTargets = []; - var headerAdded = false; for (var i = 0; i < options.targets.length; i++) { target = options.targets[i]; - if (target.hide) {return;} + if (target.hide) {continue;} var queryObj = this.queryBuilder.build(target); var esQuery = angular.toJson(queryObj); @@ -176,12 +175,9 @@ function (angular, _, moment, kbn, ElasticQueryBuilder, IndexPattern, ElasticRes luceneQuery = luceneQuery.substr(1, luceneQuery.length - 2); esQuery = esQuery.replace("$lucene_query", luceneQuery); - if (!headerAdded) { - var searchType = queryObj.size === 0 ? 'count' : 'query_then_fetch'; - var header = this.getQueryHeader(searchType, options.range.from, options.range.to); - payload += header + '\n'; - headerAdded = true; - } + var searchType = queryObj.size === 0 ? 'count' : 'query_then_fetch'; + var header = this.getQueryHeader(searchType, options.range.from, options.range.to); + payload += header + '\n'; payload += esQuery + '\n'; sentTargets.push(target); diff --git a/public/app/plugins/datasource/elasticsearch/elastic_response.js b/public/app/plugins/datasource/elasticsearch/elastic_response.js index 7eb4378831d..73050ce7f2b 100644 --- a/public/app/plugins/datasource/elasticsearch/elastic_response.js +++ b/public/app/plugins/datasource/elasticsearch/elastic_response.js @@ -86,20 +86,71 @@ function (_, queryDef) { } }; + ElasticResponse.prototype.processAggregationDocs = function(esAgg, aggDef, target, docs, props) { + var metric, y, i, bucket, metricName, doc; + + for (i = 0; i < esAgg.buckets.length; i++) { + bucket = esAgg.buckets[i]; + doc = _.defaults({}, props); + doc[aggDef.field] = bucket.key; + + for (y = 0; y < target.metrics.length; y++) { + metric = target.metrics[y]; + + switch(metric.type) { + case "count": { + metricName = this._getMetricName(metric.type); + doc[metricName] = bucket.doc_count; + break; + } + case 'extended_stats': { + for (var statName in metric.meta) { + if (!metric.meta[statName]) { + continue; + } + + var stats = bucket[metric.id]; + // add stats that are in nested obj to top level obj + stats.std_deviation_bounds_upper = stats.std_deviation_bounds.upper; + stats.std_deviation_bounds_lower = stats.std_deviation_bounds.lower; + + metricName = this._getMetricName(statName); + doc[metricName] = stats[statName]; + } + break; + } + default: { + metricName = this._getMetricName(metric.type); + doc[metricName] =bucket[metric.id].value; + break; + } + } + } + + docs.push(doc); + } + }; + // This is quite complex // neeed to recurise down the nested buckets to build series - ElasticResponse.prototype.processBuckets = function(aggs, target, seriesList, props) { + ElasticResponse.prototype.processBuckets = function(aggs, target, seriesList, docs, props, depth) { var bucket, aggDef, esAgg, aggId; + var maxDepth = target.bucketAggs.length-1; for (aggId in aggs) { aggDef = _.findWhere(target.bucketAggs, {id: aggId}); esAgg = aggs[aggId]; + if (!aggDef) { continue; } - if (aggDef.type === 'date_histogram') { - this.processMetrics(esAgg, target, seriesList, props); + if (depth === maxDepth) { + if (aggDef.type === 'date_histogram') { + this.processMetrics(esAgg, target, seriesList, props); + } else { + this.processAggregationDocs(esAgg, aggDef, target, docs, props); + } } else { for (var nameIndex in esAgg.buckets) { bucket = esAgg.buckets[nameIndex]; @@ -109,7 +160,7 @@ function (_, queryDef) { } else { props["filter"] = nameIndex; } - this.processBuckets(bucket, target, seriesList, props); + this.processBuckets(bucket, target, seriesList, docs, props, depth+1); } } } @@ -217,13 +268,18 @@ function (_, queryDef) { var aggregations = response.aggregations; var target = this.targets[i]; var tmpSeriesList = []; + var docs = []; - this.processBuckets(aggregations, target, tmpSeriesList, {}); + this.processBuckets(aggregations, target, tmpSeriesList, docs, {}, 0); this.nameSeries(tmpSeriesList, target); for (var y = 0; y < tmpSeriesList.length; y++) { seriesList.push(tmpSeriesList[y]); } + + if (seriesList.length === 0 && docs.length > 0) { + seriesList.push({target: 'docs', type: 'docs', datapoints: docs}); + } } } diff --git a/public/app/plugins/datasource/elasticsearch/query_builder.js b/public/app/plugins/datasource/elasticsearch/query_builder.js index 34156397ed0..129c52d3f02 100644 --- a/public/app/plugins/datasource/elasticsearch/query_builder.js +++ b/public/app/plugins/datasource/elasticsearch/query_builder.js @@ -10,7 +10,7 @@ function (angular) { ElasticQueryBuilder.prototype.getRangeFilter = function() { var filter = {}; - filter[this.timeField] = {"gte": "$timeFrom", "lte": "$timeTo", "format": "epoch_millis"}; + filter[this.timeField] = {"gte": "$timeFrom", "lte": "$timeTo"}; return filter; }; @@ -127,7 +127,6 @@ function (angular) { "interval": this.getInterval(aggDef), "field": this.timeField, "min_doc_count": 0, - "format": "epoch_millis", "extended_bounds": { "min": "$timeFrom", "max": "$timeTo" } }; break; diff --git a/public/app/plugins/datasource/elasticsearch/specs/elastic_response_specs.ts b/public/app/plugins/datasource/elasticsearch/specs/elastic_response_specs.ts index 5ae67f92d78..4e80833c55b 100644 --- a/public/app/plugins/datasource/elasticsearch/specs/elastic_response_specs.ts +++ b/public/app/plugins/datasource/elasticsearch/specs/elastic_response_specs.ts @@ -411,6 +411,51 @@ describe('ElasticResponse', function() { }); }); + describe('No group by time', function() { + beforeEach(function() { + targets = [{ + refId: 'A', + metrics: [{type: 'avg', id: '1'}, {type: 'count' }], + bucketAggs: [{id: '2', type: 'terms', field: 'host'}], + }]; + + response = { + responses: [{ + aggregations: { + "2": { + buckets: [ + { + "1": { value: 1000}, + key: "server-1", + doc_count: 369, + }, + { + "1": { value: 2000}, + key: "server-2", + doc_count: 200, + }, + ] + } + } + }] + }; + + result = new ElasticResponse(targets, response).getTimeSeries(); + }); + + it.only('should return table', function() { + expect(result.data.length).to.be(1); + expect(result.data[0].type).to.be('docs'); + expect(result.data[0].datapoints.length).to.be(2); + expect(result.data[0].datapoints[0].host).to.be("server-1"); + expect(result.data[0].datapoints[0].Average).to.be(1000); + expect(result.data[0].datapoints[0].Count).to.be(369); + + expect(result.data[0].datapoints[1].host).to.be("server-2"); + expect(result.data[0].datapoints[1].Average).to.be(2000); + }); + }); + describe('Raw documents query', function() { beforeEach(function() { targets = [{ refId: 'A', metrics: [{type: 'raw_document', id: '1'}], bucketAggs: [] }];