@@ -27,6 +27,7 @@ func Register(r *macaron.Macaron) {
|
||||
r.Get("/profile/", reqSignedIn, Index)
|
||||
r.Get("/org/", reqSignedIn, Index)
|
||||
r.Get("/datasources/", reqSignedIn, Index)
|
||||
r.Get("/datasources/edit/*", reqSignedIn, Index)
|
||||
r.Get("/org/users/", reqSignedIn, Index)
|
||||
r.Get("/org/apikeys/", reqSignedIn, Index)
|
||||
r.Get("/dashboard/import/", reqSignedIn, Index)
|
||||
@@ -75,6 +76,7 @@ func Register(r *macaron.Macaron) {
|
||||
r.Combo("/").Get(GetDataSources).Put(AddDataSource).Post(UpdateDataSource)
|
||||
r.Delete("/:id", DeleteDataSource)
|
||||
r.Get("/:id", GetDataSourceById)
|
||||
r.Get("/plugins", GetDataSourcePlugins)
|
||||
}, reqAccountAdmin)
|
||||
|
||||
r.Get("/frontend/settings/", GetFrontendSettings)
|
||||
|
||||
@@ -21,12 +21,12 @@ func NewReverseProxy(ds *m.DataSource, proxyPath string) *httputil.ReverseProxy
|
||||
|
||||
reqQueryVals := req.URL.Query()
|
||||
|
||||
if ds.Type == m.DS_INFLUXDB {
|
||||
if ds.Type == m.DS_INFLUXDB_08 {
|
||||
req.URL.Path = util.JoinUrlFragments(target.Path, "db/"+ds.Database+"/"+proxyPath)
|
||||
reqQueryVals.Add("u", ds.User)
|
||||
reqQueryVals.Add("p", ds.Password)
|
||||
req.URL.RawQuery = reqQueryVals.Encode()
|
||||
} else if ds.Type == m.DS_INFLUXDB_08 {
|
||||
} else if ds.Type == m.DS_INFLUXDB {
|
||||
req.URL.Path = util.JoinUrlFragments(target.Path, proxyPath)
|
||||
reqQueryVals.Add("db", ds.Database)
|
||||
reqQueryVals.Add("u", ds.User)
|
||||
|
||||
@@ -5,6 +5,7 @@ import (
|
||||
"github.com/grafana/grafana/pkg/bus"
|
||||
"github.com/grafana/grafana/pkg/middleware"
|
||||
m "github.com/grafana/grafana/pkg/models"
|
||||
"github.com/grafana/grafana/pkg/plugins"
|
||||
)
|
||||
|
||||
func GetDataSources(c *middleware.Context) {
|
||||
@@ -118,3 +119,7 @@ func UpdateDataSource(c *middleware.Context) {
|
||||
|
||||
c.JsonOK("Datasource updated")
|
||||
}
|
||||
|
||||
func GetDataSourcePlugins(c *middleware.Context) {
|
||||
c.JSON(200, plugins.DataSources)
|
||||
}
|
||||
|
||||
+1
-1
@@ -15,7 +15,7 @@ define([
|
||||
'extend-jquery',
|
||||
'bindonce',
|
||||
],
|
||||
function (angular, $, _, appLevelRequire, config) {
|
||||
function (angular, $, _, appLevelRequire) {
|
||||
|
||||
"use strict";
|
||||
|
||||
|
||||
@@ -6,8 +6,9 @@ function (angular) {
|
||||
'use strict';
|
||||
|
||||
var module = angular.module('grafana.controllers');
|
||||
var datasourceTypes = [];
|
||||
|
||||
module.controller('DataSourceEditCtrl', function($scope, $http, backendSrv, $routeParams, $location, datasourceSrv) {
|
||||
module.controller('DataSourceEditCtrl', function($scope, $q, backendSrv, $routeParams, $location, datasourceSrv) {
|
||||
|
||||
var defaults = {
|
||||
name: '',
|
||||
@@ -16,32 +17,44 @@ function (angular) {
|
||||
access: 'proxy'
|
||||
};
|
||||
|
||||
$scope.types = [
|
||||
{ name: 'Graphite', type: 'graphite' },
|
||||
{ name: 'InfluxDB 0.9.x (Experimental support)', type: 'influxdb' },
|
||||
{ name: 'InfluxDB 0.8.x', type: 'influxdb_08' },
|
||||
{ name: 'Elasticsearch', type: 'elasticsearch' },
|
||||
{ name: 'OpenTSDB', type: 'opentsdb' },
|
||||
];
|
||||
|
||||
$scope.init = function() {
|
||||
$scope.isNew = true;
|
||||
$scope.datasources = [];
|
||||
|
||||
if ($routeParams.id) {
|
||||
$scope.isNew = false;
|
||||
$scope.getDatasourceById($routeParams.id);
|
||||
} else {
|
||||
$scope.current = angular.copy(defaults);
|
||||
$scope.loadDatasourceTypes().then(function() {
|
||||
if ($routeParams.id) {
|
||||
$scope.isNew = false;
|
||||
$scope.getDatasourceById($routeParams.id);
|
||||
} else {
|
||||
$scope.current = angular.copy(defaults);
|
||||
$scope.typeChanged();
|
||||
}
|
||||
});
|
||||
};
|
||||
|
||||
$scope.loadDatasourceTypes = function() {
|
||||
if (datasourceTypes.length > 0) {
|
||||
$scope.types = datasourceTypes;
|
||||
return $q.when(null);
|
||||
}
|
||||
|
||||
return backendSrv.get('/api/datasources/plugins').then(function(plugins) {
|
||||
datasourceTypes = plugins;
|
||||
$scope.types = plugins;
|
||||
});
|
||||
};
|
||||
|
||||
$scope.getDatasourceById = function(id) {
|
||||
backendSrv.get('/api/datasources/' + id).then(function(ds) {
|
||||
$scope.current = ds;
|
||||
$scope.typeChanged();
|
||||
});
|
||||
};
|
||||
|
||||
$scope.typeChanged = function() {
|
||||
$scope.datasourceMeta = $scope.types[$scope.current.type];
|
||||
};
|
||||
|
||||
$scope.updateFrontendSettings = function() {
|
||||
backendSrv.get('/api/frontend/settings').then(function(settings) {
|
||||
datasourceSrv.init(settings.datasources);
|
||||
|
||||
@@ -19,7 +19,7 @@
|
||||
</div>
|
||||
<div class="editor-option">
|
||||
<label class="small">Type</label>
|
||||
<select class="input-large" ng-model="current.type" ng-options="f.type as f.name for f in types" ng-change="typeChanged()"></select>
|
||||
<select class="input-large" ng-model="current.type" ng-options="k as v.name for (k, v) in types" ng-change="typeChanged()"></select>
|
||||
</div>
|
||||
<editor-opt-bool text="Mark as default" model="current.isDefault" change="render()"></editor-opt-bool>
|
||||
</div>
|
||||
@@ -27,7 +27,7 @@
|
||||
<div class="editor-row">
|
||||
<div class="editor-option">
|
||||
<label class="small">Url</label>
|
||||
<input type="text" class="input-xxlarge" ng-model='current.url' placeholder="http://my.graphite.com:8080" required></input>
|
||||
<input type="text" style="width: 450px" ng-model='current.url' placeholder="http://my.graphite.com:8080" required></input>
|
||||
</div>
|
||||
<div class="editor-option">
|
||||
<label class="small">Access method <tip>Direct = url is used directly from browser, Proxy = Grafana backend will proxy the request</label>
|
||||
@@ -35,33 +35,7 @@
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="editor-row" ng-if="current.type === 'influxdb'">
|
||||
<div class="section">
|
||||
<h5>InfluxDB Details</h5>
|
||||
<div class="editor-option">
|
||||
<label class="small">Database name</label>
|
||||
<input type="text" class="input-large" required ng-model='current.database' placeholder=""></input>
|
||||
</div>
|
||||
<div class="editor-option">
|
||||
<label class="small">User</label>
|
||||
<input type="text" class="input-large" ng-model='current.user' placeholder=""></input>
|
||||
</div>
|
||||
<div class="editor-option">
|
||||
<label class="small">Password</label>
|
||||
<input type="password" class="input-large" ng-model='current.password' placeholder=""></input>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="editor-row" ng-if="current.type === 'elasticsearch'">
|
||||
<div class="section">
|
||||
<h5>Elastic search details</h5>
|
||||
<div class="editor-option">
|
||||
<label class="small">Index name</label>
|
||||
<input type="text" class="input-large" required ng-model='current.database' placeholder=""></input>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div ng-include="datasourceMeta.partials.config" ng-if="datasourceMeta.partials.config"></div>
|
||||
|
||||
<br>
|
||||
|
||||
|
||||
@@ -57,7 +57,6 @@ function (angular, _, config) {
|
||||
|
||||
$scope.setDatasource = function(datasource) {
|
||||
$scope.panel.datasource = datasource;
|
||||
debugger;
|
||||
datasourceSrv.get(datasource).then(function(ds) {
|
||||
$scope.datasource = ds;
|
||||
});
|
||||
|
||||
@@ -2,10 +2,16 @@
|
||||
|
||||
|
||||
<div class="editor-row" style="margin-top: 30px">
|
||||
<button class="btn btn-success pull-right" ng-click="addDataQuery(panel.target)">Add query</button>
|
||||
<button class="btn btn-inverse pull-right" ng-click="addDataQuery(panel.target)">
|
||||
<i class="fa fa-plus"></i>
|
||||
Add query
|
||||
</button>
|
||||
|
||||
<div class="btn-group pull-right" style="margin-right: 10px;">
|
||||
<button class="btn btn-info dropdown-toggle" data-toggle="dropdown" bs-tooltip="'Datasource'">{{datasource.name}} <span class="caret"></span></button>
|
||||
<button class="btn btn-inverse dropdown-toggle" data-toggle="dropdown" bs-tooltip="'Datasource'">
|
||||
<i class="fa fa-database"></i>
|
||||
{{datasource.name}} <span class="caret"></span>
|
||||
</button>
|
||||
|
||||
<ul class="dropdown-menu" role="menu">
|
||||
<li ng-repeat="datasource in datasources" role="menuitem">
|
||||
|
||||
@@ -0,0 +1,11 @@
|
||||
<div class="editor-row">
|
||||
<div class="section">
|
||||
<h5>Elastic search details</h5>
|
||||
<div class="editor-option">
|
||||
<label class="small">Index name</label>
|
||||
<input type="text" class="input-large" required ng-model='current.database' placeholder=""></input>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
|
||||
@@ -0,0 +1,16 @@
|
||||
{
|
||||
"pluginType": "datasource",
|
||||
"name": "Elasticsearch",
|
||||
|
||||
"type": "elasticsearch",
|
||||
"serviceName": "ElasticDatasource",
|
||||
|
||||
"module": "plugins/datasource/elasticsearch/datasource",
|
||||
|
||||
"partials": {
|
||||
"config": "app/plugins/datasource/elasticsearch/partials/config.html",
|
||||
"annotations": "app/plugins/datasource/elasticsearch/partials/query.editor.html"
|
||||
},
|
||||
|
||||
"annotations": true
|
||||
}
|
||||
@@ -0,0 +1,18 @@
|
||||
{
|
||||
"pluginType": "datasource",
|
||||
"name": "Graphite",
|
||||
|
||||
"type": "graphite",
|
||||
"serviceName": "GraphiteDatasource",
|
||||
|
||||
"module": "plugins/datasource/graphite/datasource",
|
||||
|
||||
"partials": {
|
||||
"config": "app/plugins/datasource/graphite/partials/config.html",
|
||||
"query": "app/plugins/datasource/graphite/partials/query.editor.html",
|
||||
"annotations": "app/plugins/datasource/graphite/partials/query.editor.html"
|
||||
},
|
||||
|
||||
"metrics": true,
|
||||
"annotations": true
|
||||
}
|
||||
@@ -0,0 +1,19 @@
|
||||
<div class="editor-row">
|
||||
<div class="section">
|
||||
<h5>InfluxDB Details</h5>
|
||||
<div class="editor-option">
|
||||
<label class="small">Database name</label>
|
||||
<input type="text" class="input-medium" required ng-model='current.database' placeholder=""></input>
|
||||
</div>
|
||||
<div class="editor-option">
|
||||
<label class="small">User</label>
|
||||
<input type="text" class="input-medium" ng-model='current.user' placeholder=""></input>
|
||||
</div>
|
||||
<div class="editor-option">
|
||||
<label class="small">Password</label>
|
||||
<input type="password" class="input-medium" ng-model='current.password' placeholder=""></input>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
|
||||
+1
-1
@@ -1,5 +1,5 @@
|
||||
<div class="editor-row">
|
||||
<div ng-repeat="target in panel.targets" ng-controller="InfluxQueryCtrl" ng-init="init()" ng-class="{'tight-form-disabled': target.hide}" class="tight-form-container">
|
||||
<div ng-repeat="target in panel.targets" ng-controller="InfluxQueryCtrl_08" ng-init="init()" ng-class="{'tight-form-disabled': target.hide}" class="tight-form-container">
|
||||
<div class="tight-form">
|
||||
<ul class="tight-form-list pull-right">
|
||||
<li class="tight-form-item">
|
||||
@@ -0,0 +1,18 @@
|
||||
{
|
||||
"pluginType": "datasource",
|
||||
"name": "InfluxDB 0.8.x",
|
||||
|
||||
"type": "influxdb_08",
|
||||
"serviceName": "InfluxDatasource_08",
|
||||
|
||||
"module": "plugins/datasource/influxdb_08/datasource",
|
||||
|
||||
"partials": {
|
||||
"config": "app/plugins/datasource/influxdb_08/partials/config.html",
|
||||
"query": "app/plugins/datasource/influxdb_08/partials/query.editor.html",
|
||||
"annotations": "app/plugins/datasource/influxdb_08/partials/query.editor.html"
|
||||
},
|
||||
|
||||
"metrics": true,
|
||||
"annotations": true
|
||||
}
|
||||
+1
-1
@@ -9,7 +9,7 @@ function (angular, _) {
|
||||
|
||||
var seriesList = null;
|
||||
|
||||
module.controller('InfluxQueryCtrl', function($scope, $timeout) {
|
||||
module.controller('InfluxQueryCtrl_08', function($scope, $timeout) {
|
||||
|
||||
$scope.init = function() {
|
||||
var target = $scope.target;
|
||||
@@ -1,18 +0,0 @@
|
||||
{
|
||||
"pluginType": "datasource",
|
||||
"description": "Graphite",
|
||||
|
||||
"type": "graphite",
|
||||
"serviceName": "GraphiteDatasource",
|
||||
|
||||
"module": "plugins/datasources/graphite/datasource",
|
||||
|
||||
"partials": {
|
||||
"config": "app/plugins/datasources/graphite/partials/config.html",
|
||||
"query": "app/plugins/datasources/graphite/partials/query.editor.html",
|
||||
"annotations": "app/plugins/datasources/graphite/partials/query.editor.html"
|
||||
},
|
||||
|
||||
"metrics": true,
|
||||
"annotations": true
|
||||
}
|
||||
@@ -1,18 +0,0 @@
|
||||
{
|
||||
"pluginType": "datasource",
|
||||
"description": "InfluxDB 0.8.x",
|
||||
|
||||
"type": "influxdb_08",
|
||||
"serviceName": "InfluxDatasource08",
|
||||
|
||||
"module": "plugins/datasources/influxdb_08/datasource",
|
||||
|
||||
"partials": {
|
||||
"config": "app/plugins/datasources/influxdb_08/partials/config.html",
|
||||
"query": "app/plugins/datasources/influxdb_08/partials/query.editor.html",
|
||||
"annotations": "app/plugins/datasources/influxdb_08/partials/query.editor.html"
|
||||
},
|
||||
|
||||
"metrics": true,
|
||||
"annotations": true
|
||||
}
|
||||
@@ -11,14 +11,15 @@ function (angular, _, config) {
|
||||
module.service('datasourceSrv', function($q, $injector, $rootScope) {
|
||||
var self = this;
|
||||
|
||||
this.datasources = {};
|
||||
this.metricSources = [];
|
||||
this.annotationSources = [];
|
||||
this.grafanaDB = new ($injector.get("GrafanaDatasource"));
|
||||
|
||||
this.init = function(dsSettingList) {
|
||||
config.datasources = dsSettingList;
|
||||
|
||||
this.datasources = {};
|
||||
this.metricSources = [];
|
||||
this.annotationSources = [];
|
||||
|
||||
_.each(config.datasources, function(value, key) {
|
||||
if (value.meta && value.meta.metrics) {
|
||||
self.metricSources.push({ value: key, name: key });
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
define([
|
||||
'features/graphite/gfunc'
|
||||
'plugins/datasource/graphite/gfunc'
|
||||
], function(gfunc) {
|
||||
'use strict';
|
||||
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
define([
|
||||
'helpers',
|
||||
'features/graphite/datasource'
|
||||
'plugins/datasource/graphite/datasource'
|
||||
], function(helpers) {
|
||||
'use strict';
|
||||
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
define([
|
||||
'helpers',
|
||||
'features/graphite/gfunc',
|
||||
'features/graphite/queryCtrl'
|
||||
'plugins/datasource/graphite/gfunc',
|
||||
'plugins/datasource/graphite/queryCtrl'
|
||||
], function(helpers, gfunc) {
|
||||
'use strict';
|
||||
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
define([
|
||||
'features/graphite/lexer'
|
||||
'plugins/datasource/graphite/lexer'
|
||||
], function(Lexer) {
|
||||
'use strict';
|
||||
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
define([
|
||||
'features/graphite/parser'
|
||||
'plugins/datasource/graphite/parser'
|
||||
], function(Parser) {
|
||||
'use strict';
|
||||
|
||||
|
||||
Reference in New Issue
Block a user