module.js 6.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193
  1. /*
  2. ## Dashcontrol
  3. Dash control allows for saving, loading and sharing of dashboards. Do not
  4. disable the dashcontrol module as a special instance of it allows for loading
  5. the default dashboard from dashboards/default
  6. ### Parameters
  7. * save
  8. ** gist :: Allow saving to gist. Requires registering an oauth domain with Github
  9. ** elasticsearch :: Allow saving to a special Kibana index within Elasticsearch
  10. ** local :: Allow saving to local file
  11. * load
  12. ** gist :: Allow loading from gists
  13. ** elasticsearch :: Allow searching and loading of elasticsearch saved dashboards
  14. ** local :: Allow loading of dashboards from Elasticsearch
  15. * hide_control :: Upon save, hide this panel
  16. * elasticsearch_size :: show this many dashboards under the ES section in the load drop down
  17. * temp :: Allow saving of temp dashboards
  18. * temp_ttl :: How long should temp dashboards persist
  19. ### Group Events
  20. #### Sends
  21. * dashboard :: An object containing an entire dashboard to be loaded
  22. */
  23. angular.module('kibana.dashcontrol', [])
  24. .controller('dashcontrol', function($scope, $http, timer, dashboard) {
  25. $scope.panel = $scope.panel || {};
  26. // Set and populate defaults
  27. var _d = {
  28. status : "Stable",
  29. group : "default",
  30. save : {
  31. gist: false,
  32. elasticsearch: true,
  33. local: true,
  34. 'default': true
  35. },
  36. load : {
  37. gist: true,
  38. elasticsearch: true,
  39. local: true
  40. },
  41. hide_control: false,
  42. elasticsearch_size: 20,
  43. temp: true,
  44. temp_ttl: '30d'
  45. }
  46. _.defaults($scope.panel,_d);
  47. // A hash of defaults for the dashboard object
  48. var _dash = {
  49. title: "",
  50. editable: true,
  51. rows: [],
  52. services: {}
  53. }
  54. $scope.init = function() {
  55. $scope.gist_pattern = /(^\d{5,}$)|(^[a-z0-9]{10,}$)|(gist.github.com(\/*.*)\/[a-z0-9]{5,}\/*$)/;
  56. $scope.gist = {};
  57. $scope.elasticsearch = {};
  58. }
  59. $scope.set_default = function() {
  60. if(dashboard.set_default()) {
  61. $scope.alert('Local Default Set',dashboard.current.title+' has been set as your local default','success',5000)
  62. } else {
  63. $scope.alert('Incompatible Browser','Sorry, your browser is too old for this feature','error',5000)
  64. }
  65. }
  66. $scope.purge_default = function() {
  67. if(dashboard.purge_default()) {
  68. $scope.alert('Local Default Clear','Your local default dashboard has been cleared','success',5000)
  69. } else {
  70. $scope.alert('Incompatible Browser','Sorry, your browser is too old for this feature','error',5000)
  71. }
  72. }
  73. $scope.elasticsearch_save = function(type,ttl) {
  74. dashboard.elasticsearch_save(type,($scope.elasticsearch.title || dashboard.current.title),ttl).then(
  75. function(result) {
  76. if(!_.isUndefined(result._id)) {
  77. $scope.alert('Dashboard Saved','This dashboard has been saved to Elasticsearch as "' +
  78. result._id + '"','success',5000)
  79. if(type === 'temp') {
  80. $scope.share = dashboard.share_link(dashboard.current.title,'temp',result._id)
  81. }
  82. } else {
  83. $scope.alert('Save failed','Dashboard could not be saved to Elasticsearch','error',5000)
  84. }
  85. })
  86. }
  87. $scope.elasticsearch_delete = function(id) {
  88. dashboard.elasticsearch_delete(id).then(
  89. function(result) {
  90. if(!_.isUndefined(result)) {
  91. if(result.found) {
  92. $scope.alert('Dashboard Deleted',id+' has been deleted','success',5000)
  93. // Find the deleted dashboard in the cached list and remove it
  94. var toDelete = _.where($scope.elasticsearch.dashboards,{_id:id})[0]
  95. $scope.elasticsearch.dashboards = _.without($scope.elasticsearch.dashboards,toDelete)
  96. } else {
  97. $scope.alert('Dashboard Not Found','Could not find '+id+' in Elasticsearch','warning',5000)
  98. }
  99. } else {
  100. $scope.alert('Dashboard Not Deleted','An error occurred deleting the dashboard',error,5000)
  101. }
  102. }
  103. )
  104. }
  105. $scope.elasticsearch_dblist = function(query) {
  106. dashboard.elasticsearch_list(query,$scope.panel.elasticsearch_size).then(
  107. function(result) {
  108. if(!_.isUndefined(result.hits)) {
  109. $scope.panel.error = false;
  110. $scope.hits = result.hits.total;
  111. $scope.elasticsearch.dashboards = result.hits.hits
  112. }
  113. })
  114. }
  115. $scope.save_gist = function() {
  116. dashboard.save_gist($scope.gist.title).then(
  117. function(link) {
  118. if(!_.isUndefined(link)) {
  119. $scope.gist.last = link;
  120. $scope.alert('Gist saved','You will be able to access your exported dashboard file at <a href="'+link+'">'+link+'</a> in a moment','success');
  121. } else {
  122. $scope.alert('Save failed','Gist could not be saved','error',5000)
  123. }
  124. })
  125. }
  126. $scope.gist_dblist = function(id) {
  127. dashboard.gist_list(id).then(
  128. function(files) {
  129. if(files && files.length > 0) {
  130. $scope.gist.files = files;
  131. } else {
  132. $scope.alert('Gist Failed','Could not retrieve dashboard list from gist','error',5000)
  133. }
  134. })
  135. }
  136. })
  137. .directive('dashUpload', function(timer, dashboard){
  138. return {
  139. restrict: 'A',
  140. link: function(scope, elem, attrs) {
  141. function file_selected(evt) {
  142. var files = evt.target.files; // FileList object
  143. // files is a FileList of File objects. List some properties.
  144. var output = [];
  145. for (var i = 0, f; f = files[i]; i++) {
  146. var reader = new FileReader();
  147. reader.onload = (function(theFile) {
  148. return function(e) {
  149. dashboard.dash_load(JSON.parse(e.target.result))
  150. scope.$apply();
  151. };
  152. })(f);
  153. reader.readAsText(f);
  154. }
  155. }
  156. // Check for the various File API support.
  157. if (window.File && window.FileReader && window.FileList && window.Blob) {
  158. // Something
  159. document.getElementById('dashupload').addEventListener('change', file_selected, false);
  160. } else {
  161. alert('Sorry, the HTML5 File APIs are not fully supported in this browser.');
  162. }
  163. }
  164. }
  165. }).filter('gistid', function() {
  166. var gist_pattern = /(\d{5,})|([a-z0-9]{10,})|(gist.github.com(\/*.*)\/[a-z0-9]{5,}\/*$)/;
  167. return function(input, scope) {
  168. //return input+"boners"
  169. if(!(_.isUndefined(input))) {
  170. var output = input.match(gist_pattern);
  171. if(!_.isNull(output) && !_.isUndefined(output))
  172. return output[0].replace(/.*\//, '');
  173. }
  174. }
  175. });;