Commit 3c139016 by woodsaj

add ui elements for plugins.

This includes support for cusom plugin config directives.
parent c4a0fe02
......@@ -41,6 +41,9 @@ func Register(r *macaron.Macaron) {
r.Get("/admin/orgs", reqGrafanaAdmin, Index)
r.Get("/admin/orgs/edit/:id", reqGrafanaAdmin, Index)
r.Get("/plugins", reqSignedIn, Index)
r.Get("/plugins/edit/*", reqSignedIn, Index)
r.Get("/dashboard/*", reqSignedIn, Index)
r.Get("/dashboard-solo/*", reqSignedIn, Index)
......
......@@ -60,6 +60,10 @@ func setIndexViewData(c *middleware.Context) (*dtos.IndexViewData, error) {
Text: "Data Sources",
Icon: "fa fa-fw fa-database",
Href: "/datasources",
}, &dtos.NavLink{
Text: "Plugins",
Icon: "fa fa-fw fa-cubes",
Href: "/plugins",
})
}
......
......@@ -131,6 +131,16 @@ define([
templateUrl: 'app/partials/reset_password.html',
controller : 'ResetPasswordCtrl',
})
.when('/plugins', {
templateUrl: 'app/features/org/partials/plugins.html',
controller: 'PluginsCtrl',
resolve: loadOrgBundle,
})
.when('/plugins/edit/:type', {
templateUrl: 'app/features/org/partials/pluginEdit.html',
controller: 'PluginEditCtrl',
resolve: loadOrgBundle,
})
.otherwise({
templateUrl: 'app/partials/error.html',
controller: 'ErrorCtrl'
......
......@@ -6,4 +6,8 @@ define([
'./userInviteCtrl',
'./orgApiKeysCtrl',
'./orgDetailsCtrl',
'./pluginsCtrl',
'./pluginEditCtrl',
'./plugin_srv',
'./plugin_directive',
], function () {});
<div>
{{current.type}} plugin does not have any additional config.
</div>
<topnav title="Plugins" icon="fa fa-fw fa-cubes" subnav="true">
<ul class="nav">
<li ><a href="plugins">Overview</a></li>
<li class="active" ><a href="plugins/edit/{{current.type}}">Edit</a></li>
</ul>
</topnav>
<div class="page-container">
<div class="page">
<h2>Edit Plugin</h2>
<form name="editForm">
<div class="tight-form">
<ul class="tight-form-list">
<li class="tight-form-item" style="width: 80px">
Type
</li>
<li>
<li>
<input type="text" disabled="disabled" class="input-xlarge tight-form-input" ng-model="current.type">
</li>
</li>
<li class="tight-form-item">
Default&nbsp;
<input class="cr1" id="current.enabled" type="checkbox" ng-model="current.enabled" ng-checked="current.enabled">
<label for="current.enabled" class="cr1"></label>
</li>
</ul>
<div class="clearfix"></div>
</div>
<br>
<plugin-config-loader></plugin-config-loader>
<div class="pull-right" style="margin-top: 35px">
<button type="submit" class="btn btn-success" ng-click="update()">Save</button>
<a class="btn btn-inverse" href="plugins">Cancel</a>
</div>
<br>
</form>
</div>
</div>
\ No newline at end of file
<topnav title="Plugins" icon="fa fa-fw fa-cubes" subnav="true">
<ul class="nav">
<li class="active" ><a href="plugins">Overview</a></li>
</ul>
</topnav>
<div class="page-container">
<div class="page">
<h2>Plugins</h2>
<div ng-if="!plugins">
<em>No plugins defined</em>
</div>
<table class="grafana-options-table" ng-if="plugins">
<tr>
<td><strong>Type</strong></td>
<td></td>
<td></td>
</tr>
<tr ng-repeat="(type, p) in plugins">
<td style="width:1%">
<i class="fa fa-cubes"></i> &nbsp;
{{p.type}}
</td>
<td style="width: 1%">
<a href="plugins/edit/{{p.type}}" class="btn btn-inverse btn-mini">
<i class="fa fa-edit"></i>
Edit
</a>
</td>
<td style="width: 1%">
Enabled&nbsp;
<input id="p.enabled" type="checkbox" ng-model="p.enabled" ng-checked="p.enabled" ng-change="update(p)">
<label for="p.enabled"></label>
</td>
</tr>
</table>
</div>
</div>
\ No newline at end of file
define([
'angular',
'lodash',
'app/core/config',
],
function (angular, _, config) {
'use strict';
var module = angular.module('grafana.controllers');
module.controller('PluginEditCtrl', function($scope, pluginSrv, $routeParams) {
$scope.init = function() {
$scope.current = {};
$scope.getPlugins();
};
$scope.getPlugins = function() {
pluginSrv.get($routeParams.type).then(function(result) {
$scope.current = _.clone(result);
});
};
$scope.update = function() {
$scope._update();
};
$scope._update = function() {
pluginSrv.update($scope.current).then(function() {
window.location.href = config.appSubUrl + "plugins";
});
};
$scope.init();
});
});
\ No newline at end of file
define([
'angular',
],
function (angular) {
'use strict';
var module = angular.module('grafana.directives');
module.directive('pluginConfigLoader', function($compile) {
return {
restrict: 'E',
link: function(scope, elem) {
var directive = 'grafana-plugin-core';
if (scope.current.module) {
directive = 'grafana-plugin-'+scope.current.type;
}
scope.require([scope.current.module], function () {
var panelEl = angular.element(document.createElement(directive));
elem.append(panelEl);
$compile(panelEl)(scope);
});
}
};
});
module.directive('grafanaPluginCore', function() {
return {
restrict: 'E',
templateUrl: 'app/features/org/partials/pluginConfigCore.html',
transclude: true,
link: function(scope, elem) {
console.log("grafana plugin core", scope, elem);
scope.update = function() {
//Perform custom save events to the plugins own backend if needed.
// call parent update to commit the change to the plugin object.
// this will cause the page to reload.
scope._update();
};
}
};
});
});
\ No newline at end of file
define([
'angular',
'lodash',
],
function (angular, _) {
'use strict';
var module = angular.module('grafana.services');
module.service('pluginSrv', function($rootScope, $timeout, $q, backendSrv) {
var self = this;
this.init = function() {
console.log("pluginSrv init");
this.plugins = {};
};
this.get = function(type) {
return $q(function(resolve) {
if (type in self.plugins) {
return resolve(self.plugins[type]);
}
backendSrv.get('/api/plugins').then(function(results) {
_.forEach(results, function(p) {
self.plugins[p.type] = p;
});
return resolve(self.plugins[type]);
});
});
};
this.getAll = function() {
return $q(function(resolve) {
if (!_.isEmpty(self.plugins)) {
return resolve(self.plugins);
}
backendSrv.get('api/plugins').then(function(results) {
_.forEach(results, function(p) {
self.plugins[p.type] = p;
});
return resolve(self.plugins);
});
});
};
this.update = function(plugin) {
return $q(function(resolve, reject) {
backendSrv.post('/api/plugins', plugin).then(function(resp) {
self.plugins[plugin.type] = plugin;
resolve(resp);
}, function(resp) {
reject(resp);
});
});
};
this.init();
});
});
define([
'angular',
'app/core/config',
],
function (angular, config) {
'use strict';
var module = angular.module('grafana.controllers');
module.controller('PluginsCtrl', function($scope, $location, pluginSrv) {
$scope.init = function() {
$scope.plugins = {};
$scope.getPlugins();
};
$scope.getPlugins = function() {
pluginSrv.getAll().then(function(result) {
console.log(result);
$scope.plugins = result;
});
};
$scope.update = function(plugin) {
pluginSrv.update(plugin).then(function() {
window.location.href = config.appSubUrl + $location.path();
});
};
$scope.init();
});
});
\ No newline at end of file
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment