Skip to content

Commit

Permalink
Merge pull request #502 from EverythingMe/feature/alerts
Browse files Browse the repository at this point in the history
Feature: alerts on query results
  • Loading branch information
arikfr committed Jul 22, 2015
2 parents 63de247 + 658af52 commit d89dd2c
Show file tree
Hide file tree
Showing 22 changed files with 1,447 additions and 856 deletions.
13 changes: 8 additions & 5 deletions manage.py
Original file line number Diff line number Diff line change
Expand Up @@ -43,12 +43,15 @@ def make_shell_context():
@manager.command
def check_settings():
"""Show the settings as re:dash sees them (useful for debugging)."""
from types import ModuleType
for name, item in settings.all_settings().iteritems():
print "{} = {}".format(name, item)

for name in dir(settings):
item = getattr(settings, name)
if not callable(item) and not name.startswith("__") and not isinstance(item, ModuleType):
print "{} = {}".format(name, item)
@manager.command
def send_test_mail():
from redash import mail
from flask_mail import Message

mail.send(Message(subject="Test Message from re:dash", recipients=[settings.MAIL_DEFAULT_SENDER], body="Test message."))


if __name__ == '__main__':
Expand Down
8 changes: 8 additions & 0 deletions migrations/0010_create_alerts.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
from redash.models import db, Alert, AlertSubscription

if __name__ == '__main__':
with db.database.transaction():
Alert.create_table()
AlertSubscription.create_table()

db.close_db(None)
3 changes: 2 additions & 1 deletion rd_ui/.jshintrc
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@
"trailing": true,
"smarttabs": true,
"globals": {
"angular": false
"angular": false,
"_": false
}
}
4 changes: 4 additions & 0 deletions rd_ui/app/index.html
Original file line number Diff line number Diff line change
Expand Up @@ -73,6 +73,9 @@
<li><a href="/queries">Queries</a></li>
</ul>
</li>
<li>
<a href="/alerts">Alerts</a>
</li>
</ul>
<form class="navbar-form navbar-left" role="search" ng-submit="searchQueries()">
<div class="form-group">
Expand Down Expand Up @@ -164,6 +167,7 @@
<script src="/scripts/directives/query_directives.js"></script>
<script src="/scripts/directives/dashboard_directives.js"></script>
<script src="/scripts/filters.js"></script>
<script src="/scripts/controllers/alerts.js"></script>
<!-- endbuild -->

<script>
Expand Down
11 changes: 8 additions & 3 deletions rd_ui/app/scripts/app.js
Original file line number Diff line number Diff line change
Expand Up @@ -80,9 +80,14 @@ angular.module('redash', [
templateUrl: '/views/admin_status.html',
controller: 'AdminStatusCtrl'
});
$routeProvider.when('/admin/workers', {
templateUrl: '/views/admin_workers.html',
controller: 'AdminWorkersCtrl'

$routeProvider.when('/alerts', {
templateUrl: '/views/alerts/list.html',
controller: 'AlertsCtrl'
});
$routeProvider.when('/alerts/:alertId', {
templateUrl: '/views/alerts/edit.html',
controller: 'AlertCtrl'
});

$routeProvider.when('/', {
Expand Down
171 changes: 171 additions & 0 deletions rd_ui/app/scripts/controllers/alerts.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,171 @@
(function() {

var AlertsCtrl = function($scope, Events, Alert) {
Events.record(currentUser, "view", "page", "alerts");
$scope.$parent.pageTitle = "Alerts";

$scope.alerts = []
Alert.query(function(alerts) {
var stateClass = {
'ok': 'label label-success',
'triggered': 'label label-danger',
'unknown': 'label label-warning'
};
_.each(alerts, function(alert) {
alert.class = stateClass[alert.state];
})
$scope.alerts = alerts;

});

$scope.gridConfig = {
isPaginationEnabled: true,
itemsByPage: 50,
maxSize: 8,
};


$scope.gridColumns = [
{
"label": "Name",
"map": "name",
"cellTemplate": '<a href="/alerts/{{dataRow.id}}">{{dataRow.name}}</a> (<a href="/queries/{{dataRow.query.id}}">query</a>)'
},
{
'label': 'Created By',
'map': 'user.name'
},
{
'label': 'State',
'cellTemplate': '<span ng-class="dataRow.class">{{dataRow.state | uppercase}}</span> since <span am-time-ago="dataRow.updated_at"></span>'
},
{
'label': 'Created At',
'cellTemplate': '<span am-time-ago="dataRow.created_at"></span>'
}
];
};

var AlertCtrl = function($scope, $routeParams, growl, Query, Events, Alert) {
$scope.$parent.pageTitle = "Alerts";

$scope.alertId = $routeParams.alertId;
if ($scope.alertId === "new") {
Events.record(currentUser, 'view', 'page', 'alerts/new');
} else {
Events.record(currentUser, 'view', 'alert', $scope.alertId);
}

$scope.onQuerySelected = function(item) {
$scope.selectedQuery = item;
item.getQueryResultPromise().then(function(result) {
$scope.queryResult = result;
$scope.alert.options.column = result.getColumnNames()[0];
});
};

if ($scope.alertId === "new") {
$scope.alert = new Alert({options: {}});
} else {
$scope.alert = Alert.get({id: $scope.alertId}, function(alert) {
$scope.onQuerySelected(new Query($scope.alert.query));
});
}

$scope.ops = ['greater than', 'less than', 'equals'];
$scope.selectedQuery = null;

$scope.getDefaultName = function() {
if (!$scope.alert.query) {
return undefined;
}
return _.template("<%= query.name %>: <%= options.column %> <%= options.op %> <%= options.value %>", $scope.alert);
};

$scope.searchQueries = function (term) {
if (!term || term.length < 3) {
return;
}

Query.search({q: term}, function(results) {
$scope.queries = results;
});
};

$scope.saveChanges = function() {
if ($scope.alert.name === undefined || $scope.alert.name === '') {
$scope.alert.name = $scope.getDefaultName();
}

$scope.alert.$save(function() {
growl.addSuccessMessage("Saved.");
}, function() {
growl.addErrorMessage("Failed saving alert.");
});
};
};

angular.module('redash.directives').directive('alertSubscribers', ['AlertSubscription', function (AlertSubscription) {
return {
restrict: 'E',
replace: true,
templateUrl: '/views/alerts/subscribers.html',
scope: {
'alertId': '='
},
controller: function ($scope) {
$scope.subscribers = AlertSubscription.query({alertId: $scope.alertId});
}
}
}]);

angular.module('redash.directives').directive('subscribeButton', ['AlertSubscription', 'growl', function (AlertSubscription, growl) {
return {
restrict: 'E',
replace: true,
template: '<button class="btn btn-default btn-xs" ng-click="toggleSubscription()"><i ng-class="class"></i></button>',
controller: function ($scope) {
var updateClass = function() {
if ($scope.subscription) {
$scope.class = "fa fa-eye-slash";
} else {
$scope.class = "fa fa-eye";
}
}

$scope.subscribers.$promise.then(function() {
$scope.subscription = _.find($scope.subscribers, function(subscription) {
return (subscription.user.email == currentUser.email);
});

updateClass();
});

$scope.toggleSubscription = function() {
if ($scope.subscription) {
$scope.subscription.$delete(function() {
$scope.subscribers = _.without($scope.subscribers, $scope.subscription);
$scope.subscription = undefined;
updateClass();
}, function() {
growl.addErrorMessage("Failed saving subscription.");
});
} else {
$scope.subscription = new AlertSubscription({alert_id: $scope.alertId});
$scope.subscription.$save(function() {
$scope.subscribers.push($scope.subscription);
updateClass();
}, function() {
growl.addErrorMessage("Unsubscription failed.");
});
}
}
}
}
}]);

angular.module('redash.controllers')
.controller('AlertsCtrl', ['$scope', 'Events', 'Alert', AlertsCtrl])
.controller('AlertCtrl', ['$scope', '$routeParams', 'growl', 'Query', 'Events', 'Alert', AlertCtrl])

})();
6 changes: 2 additions & 4 deletions rd_ui/app/scripts/controllers/controllers.js
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,7 @@
},
{
'label': 'Created By',
'map': 'user_name'
'map': 'user.name'
},
{
'label': 'Created At',
Expand All @@ -45,7 +45,6 @@
Query.search({q: $scope.term }, function(results) {
$scope.queries = _.map(results, function(query) {
query.created_at = moment(query.created_at);
query.user_name = query.user.name;
return query;
});
});
Expand Down Expand Up @@ -93,7 +92,6 @@
$scope.allQueries = _.map(queries, function (query) {
query.created_at = moment(query.created_at);
query.retrieved_at = moment(query.retrieved_at);
query.user_name = query.user.name;
return query;
});

Expand All @@ -108,7 +106,7 @@
},
{
'label': 'Created By',
'map': 'user_name'
'map': 'user.name'
},
{
'label': 'Created At',
Expand Down
Loading

0 comments on commit d89dd2c

Please sign in to comment.