definition_details_controller.js 12 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377
  1. /**
  2. * Licensed to the Apache Software Foundation (ASF) under one
  3. * or more contributor license agreements. See the NOTICE file
  4. * distributed with this work for additional information
  5. * regarding copyright ownership. The ASF licenses this file
  6. * to you under the Apache License, Version 2.0 (the
  7. * "License"); you may not use this file except in compliance
  8. * with the License. You may obtain a copy of the License at
  9. *
  10. * http://www.apache.org/licenses/LICENSE-2.0
  11. *
  12. * Unless required by applicable law or agreed to in writing, software
  13. * distributed under the License is distributed on an "AS IS" BASIS,
  14. * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  15. * See the License for the specific language governing permissions and
  16. * limitations under the License.
  17. */
  18. var validator = require('utils/validator');
  19. App.MainAlertDefinitionDetailsController = Em.Controller.extend({
  20. name: 'mainAlertDefinitionDetailsController',
  21. alerts: function () {
  22. return App.AlertInstanceLocal.find().toArray()
  23. .filterProperty('definitionId', this.get('content.id'));
  24. }.property('App.router.mainAlertInstancesController.isLoaded', 'App.router.mainAlertInstancesController.reload'),
  25. // stores object with editing form data (label)
  26. editing: Em.Object.create({
  27. label: Em.Object.create({
  28. name: 'label',
  29. isEditing: false,
  30. value: '',
  31. originalValue: '',
  32. isError: false,
  33. bindingValue: 'content.label'
  34. })
  35. }),
  36. /**
  37. * Host to count of alerts on this host during last day map
  38. * @type {Object}
  39. */
  40. lastDayAlertsCount: null,
  41. /**
  42. * List of all group names related to alert definition
  43. * @type {Array}
  44. */
  45. groupsList: Em.computed.mapBy('content.groups', 'displayName'),
  46. /**
  47. * Validation function to define if label field populated correctly
  48. * @method labelValidation
  49. */
  50. labelValidation: function () {
  51. this.set('editing.label.isError', !this.get('editing.label.value').trim());
  52. }.observes('editing.label.value'),
  53. /**
  54. * Set init values for variables
  55. */
  56. clearStep: function () {
  57. var editing = this.get('editing');
  58. Em.keys(editing).forEach(function (key) {
  59. editing.get(key).set('isEditing', false);
  60. });
  61. },
  62. /**
  63. * Load alert instances for current alertDefinition
  64. * Start updating loaded data
  65. * @method loadAlertInstances
  66. */
  67. loadAlertInstances: function () {
  68. App.router.get('mainAlertInstancesController').loadAlertInstancesByAlertDefinition(this.get('content.id'));
  69. App.router.set('mainAlertInstancesController.isUpdating', true);
  70. this.loadAlertInstancesHistory();
  71. },
  72. /**
  73. * Load alert instances history data
  74. * used to count instances number of the last 24 hour
  75. * @method loadAlertInstancesHistory
  76. */
  77. loadAlertInstancesHistory: function () {
  78. this.set('lastDayAlertsCount', null);
  79. return App.ajax.send({
  80. name: 'alerts.get_instances_history',
  81. sender: this,
  82. data: {
  83. definitionName: this.get('content.name'),
  84. timestamp: App.dateTime() - 86400000 // timestamp for time 24-hours ago
  85. },
  86. success: 'loadAlertInstancesHistorySuccess'
  87. });
  88. },
  89. /**
  90. * Success-callback for <code>loadAlertInstancesHistory</code>
  91. */
  92. loadAlertInstancesHistorySuccess: function (data) {
  93. var lastDayAlertsCount = {};
  94. data.items.forEach(function (alert) {
  95. if (!lastDayAlertsCount[alert.AlertHistory.host_name]) {
  96. lastDayAlertsCount[alert.AlertHistory.host_name] = 1;
  97. } else {
  98. lastDayAlertsCount[alert.AlertHistory.host_name] += 1;
  99. }
  100. });
  101. this.set('lastDayAlertsCount', lastDayAlertsCount);
  102. },
  103. /**
  104. * Edit button handler
  105. * @param {object} event
  106. * @method edit
  107. */
  108. edit: function (event) {
  109. var element = event.context;
  110. var value = this.get(element.get('bindingValue'));
  111. element.set('originalValue', value);
  112. element.set('value', value);
  113. element.set('isEditing', true);
  114. },
  115. /**
  116. * Cancel button handler
  117. * @param {object} event
  118. * @method cancelEdit
  119. */
  120. cancelEdit: function (event) {
  121. var element = event.context;
  122. element.set('value', element.get('originalValue'));
  123. element.set('isEditing', false);
  124. },
  125. /**
  126. * Save button handler, could save label of alert definition
  127. * @param {object} event
  128. * @returns {$.ajax}
  129. * @method saveEdit
  130. */
  131. saveEdit: function (event) {
  132. var element = event.context;
  133. this.set(element.get('bindingValue'), element.get('value'));
  134. element.set('isEditing', false);
  135. var data = Em.Object.create({});
  136. var property_name = "AlertDefinition/" + element.get('name');
  137. data.set(property_name, element.get('value'));
  138. var alertDefinition_id = this.get('content.id');
  139. return App.ajax.send({
  140. name: 'alerts.update_alert_definition',
  141. sender: this,
  142. data: {
  143. id: alertDefinition_id,
  144. data: data
  145. }
  146. });
  147. },
  148. /**
  149. * Onclick handler for save button on Save popup
  150. * Save changes of label and configs
  151. */
  152. saveLabelAndConfigs: function () {
  153. var configsController = App.router.get('mainAlertDefinitionConfigsController');
  154. if (configsController.get('canEdit')) {
  155. configsController.saveConfigs();
  156. }
  157. if (this.get('editing.label.isEditing')) {
  158. this.saveEdit({
  159. context: this.get('editing.label')
  160. });
  161. }
  162. },
  163. /**
  164. * "Delete" button handler
  165. * @param {object} event
  166. * @method deleteAlertDefinition
  167. */
  168. deleteAlertDefinition: function (event) {
  169. var alertDefinition = this.get('content');
  170. var self = this;
  171. App.showConfirmationPopup(function () {
  172. App.ajax.send({
  173. name: 'alerts.delete_alert_definition',
  174. sender: self,
  175. success: 'deleteAlertDefinitionSuccess',
  176. error: 'deleteAlertDefinitionError',
  177. data: {
  178. id: alertDefinition.get('id')
  179. }
  180. });
  181. }, null, function () {
  182. });
  183. },
  184. /**
  185. * Success-callback for <code>deleteAlertDefinition</code>
  186. * @method deleteAlertDefinitionSuccess
  187. */
  188. deleteAlertDefinitionSuccess: function () {
  189. App.router.transitionTo('main.alerts.index');
  190. },
  191. /**
  192. * Error-callback for <code>deleteAlertDefinition</code>
  193. * @method deleteAlertDefinitionError
  194. */
  195. deleteAlertDefinitionError: function (xhr, textStatus, errorThrown, opt) {
  196. xhr.responseText = "{\"message\": \"" + xhr.statusText + "\"}";
  197. App.ajax.defaultErrorHandler(xhr, opt.url, 'DELETE', xhr.status);
  198. },
  199. /**
  200. * "Disable / Enable" button handler
  201. * @method toggleState
  202. */
  203. toggleState: function () {
  204. var alertDefinition = this.get('content');
  205. var self = this;
  206. var bodyMessage = Em.Object.create({
  207. confirmMsg: alertDefinition.get('enabled') ? Em.I18n.t('alerts.table.state.enabled.confirm.msg') : Em.I18n.t('alerts.table.state.disabled.confirm.msg'),
  208. confirmButton: alertDefinition.get('enabled') ? Em.I18n.t('alerts.table.state.enabled.confirm.btn') : Em.I18n.t('alerts.table.state.disabled.confirm.btn')
  209. });
  210. return App.showConfirmationFeedBackPopup(function (query) {
  211. self.toggleDefinitionState(alertDefinition);
  212. }, bodyMessage);
  213. },
  214. /**
  215. * Enable/disable alertDefinition
  216. * @param {object} alertDefinition
  217. * @param {string} property
  218. * @returns {$.ajax}
  219. * @method toggleDefinitionState
  220. */
  221. toggleDefinitionState: function (alertDefinition) {
  222. var newState = !alertDefinition.get('enabled');
  223. alertDefinition.set('enabled', newState);
  224. return App.ajax.send({
  225. name: 'alerts.update_alert_definition',
  226. sender: this,
  227. data: {
  228. id: alertDefinition.get('id'),
  229. data: {
  230. "AlertDefinition/enabled": newState
  231. }
  232. }
  233. });
  234. },
  235. globalAlertsRepeatTolerance: function () {
  236. return App.router.get('clusterController.clusterEnv.properties.alerts_repeat_tolerance') || "1";
  237. }.property('App.router.clusterController.clusterEnv'),
  238. enableRepeatTolerance: function (enable) {
  239. var alertDefinition = this.get('content');
  240. alertDefinition.set('repeat_tolerance_enabled', enable);
  241. return App.ajax.send({
  242. name: 'alerts.update_alert_definition',
  243. sender: this,
  244. data: {
  245. id: alertDefinition.get('id'),
  246. data: {
  247. "AlertDefinition/repeat_tolerance_enabled": enable
  248. }
  249. }
  250. });
  251. },
  252. editRepeatTolerance: function () {
  253. var self = this;
  254. var alertDefinition = this.get('content');
  255. var alertsRepeatTolerance = App.router.get('clusterController.clusterEnv.properties.alerts_repeat_tolerance') || "1";
  256. return App.ModalPopup.show({
  257. classNames: ['fourty-percent-width-modal'],
  258. header: Em.I18n.t('alerts.actions.editRepeatTolerance.header'),
  259. primary: Em.I18n.t('common.save'),
  260. secondary: Em.I18n.t('common.cancel'),
  261. inputValue: self.get('content.repeat_tolerance_enabled') ? (self.get('content.repeat_tolerance') || 1) : alertsRepeatTolerance,
  262. errorMessage: Em.I18n.t('alerts.actions.editRepeatTolerance.error'),
  263. isInvalid: function () {
  264. var intValue = Number(this.get('inputValue'));
  265. return this.get('inputValue') !== 'DEBUG' && (!validator.isValidInt(intValue) || intValue < 1 || intValue > 99);
  266. }.property('inputValue'),
  267. isChanged: function () {
  268. var intValue = Number(this.get('inputValue'));
  269. var isValueChanged = intValue != alertsRepeatTolerance;
  270. return isValueChanged;
  271. }.property('inputValue'),
  272. doRestoreDefaultValue: function () {
  273. this.set('inputValue', alertsRepeatTolerance);
  274. this.$('[data-toggle=tooltip]').tooltip('destroy');
  275. },
  276. disablePrimary: Em.computed.alias('isInvalid'),
  277. onPrimary: function () {
  278. if (this.get('isInvalid')) {
  279. return;
  280. }
  281. var input = this.get('inputValue');
  282. self.set('content.repeat_tolerance', input);
  283. if (input == alertsRepeatTolerance) {
  284. self.enableRepeatTolerance(false);
  285. } else {
  286. self.enableRepeatTolerance(true);
  287. }
  288. App.ajax.send({
  289. name: 'alerts.update_alert_definition',
  290. sender: self,
  291. data: {
  292. id: alertDefinition.get('id'),
  293. data: {
  294. "AlertDefinition/repeat_tolerance": input
  295. }
  296. }
  297. });
  298. this.hide();
  299. },
  300. didInsertElement: function () {
  301. App.tooltip(this.$('[data-toggle=tooltip]'));
  302. },
  303. bodyClass: Ember.View.extend({
  304. templateName: require('templates/common/modal_popups/prompt_popup'),
  305. title: Em.I18n.t('alerts.actions.editRepeatTolerance.title'),
  306. description: Em.I18n.t('alerts.actions.editRepeatTolerance.description'),
  307. label: Em.I18n.t('alerts.actions.editRepeatTolerance.label')
  308. })
  309. });
  310. },
  311. /**
  312. * Define if label or configs are in edit mode
  313. * @type {Boolean}
  314. */
  315. isEditing: Em.computed.or('editing.label.isEditing', 'App.router.mainAlertDefinitionConfigsController.canEdit'),
  316. /**
  317. * If some configs or label are changed and user navigates away, show this popup with propose to save changes
  318. * @param {String} path
  319. * @method showSavePopup
  320. */
  321. showSavePopup: function (callback) {
  322. var self = this;
  323. return App.ModalPopup.show({
  324. header: Em.I18n.t('common.warning'),
  325. bodyClass: Em.View.extend({
  326. template: Ember.Handlebars.compile('{{t alerts.saveChanges}}')
  327. }),
  328. primary: Em.I18n.t('common.save'),
  329. secondary: Em.I18n.t('common.discard'),
  330. third: Em.I18n.t('common.cancel'),
  331. disablePrimary: Em.computed.or('App.router.mainAlertDefinitionDetailsController.editing.label.isError', 'App.router.mainAlertDefinitionConfigsController.hasErrors'),
  332. onPrimary: function () {
  333. self.saveLabelAndConfigs();
  334. callback();
  335. this.hide();
  336. },
  337. onSecondary: function () {
  338. callback();
  339. this.hide();
  340. },
  341. onThird: function () {
  342. this.hide();
  343. }
  344. });
  345. }
  346. });