PageRenderTime 57ms CodeModel.GetById 20ms RepoModel.GetById 0ms app.codeStats 1ms

/fangofmongo/static/fom/js/fangofmongo_ui.js

https://github.com/pgsql/Fang-of-Mongo
JavaScript | 986 lines | 565 code | 136 blank | 285 comment | 47 complexity | 66721ee64da433b32d8797911c83e48a MD5 | raw file
  1. /* Fang of Mongo init function */
  2. function fom_init_mongo_ui()
  3. /*
  4. Base class for all fom objects
  5. */
  6. {
  7. $(function() {
  8. /*
  9. Base class for fom objects
  10. */
  11. $.widget("ui.fom_object", {
  12. _init: function() {
  13. // init code for mywidget
  14. var defaults = {
  15. };
  16. this.options = $.extend({}, defaults, this.options);
  17. //alert('d:'+this.options.disabled);
  18. // can use this.options
  19. },
  20. //set_enabled(enabled) {}
  21. //value: function(a) { return a; },
  22. //length: function ( ) { return this.listeners.length; },
  23. signal: function(signal_name, signal_source, signal_data ) {
  24. },
  25. destroy: function() {
  26. $.widget.prototype.apply(this, arguments); // default destroy
  27. // now do other stuff particular to this widget
  28. }
  29. });
  30. $.extend($.ui.fom_object, {
  31. getters: "value length",
  32. /*defaults: {
  33. //hidden: true
  34. }*/
  35. });
  36. //end of fom_object
  37. /*
  38. * Plugin interface
  39. *
  40. */
  41. Fom_plugin = $.extend({}, $.ui.fom_object.prototype,{
  42. _init: function(){
  43. $.ui.fom_object.prototype._init.call(this); // call the original function
  44. },
  45. });
  46. $.widget("ui.fom_plugin", Fom_plugin);
  47. /*
  48. * Query builder elemen
  49. */
  50. Fom_query_builder = $.extend({}, $.ui.fom_object.prototype,{
  51. _init: function(){
  52. var defaults = {
  53. autocomplete: true,
  54. completion_source: [],
  55. layout: 'vertical', //horizontal or vertical
  56. };
  57. this.options = $.extend({}, defaults, this.options);
  58. $.ui.fom_object.prototype._init.call(this); // call the original function
  59. var this_obj = this;
  60. this.condition_count = 0;
  61. this.div = $('#' + this.options['div_id']);
  62. $(this.div).addClass('fom_query_builder');
  63. //$(this.div).append('<table><tr><td><button class="fom_query_builder_btn_add" title="add condition">+</button></td><td><button class="fom_query_builder_btn_del" title="remove condition">-</button></td></tr></table>');
  64. $(this.div).append('<table></table>');
  65. this.table = $(this.div).children()[0];
  66. /*$(this.table).find('.fom_query_builder_btn_add').click( function() {
  67. this_obj.add_query();
  68. });
  69. $(this.table).find('.fom_query_builder_btn_del').click( function() {
  70. this_obj.del_query();
  71. });*/
  72. this.add_query();
  73. },
  74. add_query: function() {
  75. var this_obj = this;
  76. var qb_field_condition = $('\
  77. <select class="fom_query_builder_field_condition">\
  78. <option value="_ignore">(ignore)</option>\
  79. <option value="$equals">equals</option>\
  80. <option value="$ne">is not equal</option>\
  81. <option value="$exists">exists</option>\
  82. <option value="$nexists">does not exists</option>\
  83. <option value="$gt">greather</option>\
  84. <option value="$gte">greather or equal</option>\
  85. <option value="$lt">lower</option>\
  86. <option value="$lte">lower or equal</option>\
  87. <option value="$in">is any of</option>\
  88. <option value="$nin">is not any of</option>\
  89. <option value="$all">contains all of</option>\
  90. <option value="$size">is of size</option>\
  91. <option value="$type">is of type</option>\
  92. <option value="$re">matches regular expression</option>\
  93. <option value="$elemMatch">matches element</option>\
  94. <option value="$where">matches condition ($where)</option>\
  95. </select>\
  96. ');
  97. var qb_field_name = $('<input type="text" value="" class="fom_query_builder_field_name"/>')
  98. .autocomplete({ minLength:0, source:this.options.completion_source})
  99. .css('display','inline');
  100. var qb_field_btn = $("<button>&nbsp;</button>")
  101. .attr("tabIndex", -1)
  102. .attr("title", "Show all field names")
  103. .button({
  104. icons: {
  105. primary: "ui-icon-triangle-1-s"
  106. },
  107. text: false
  108. }).removeClass("ui-corner-all")
  109. .addClass("ui-corner-right ui-button-icon")
  110. .click(function() {
  111. // close if already visible
  112. if (qb_field_name.autocomplete("widget").is(":visible")) {
  113. qb_field_name.autocomplete("close");
  114. return;
  115. }
  116. // pass empty string as value to search for, displaying all results
  117. qb_field_name.autocomplete("search", "");
  118. qb_field_name.focus();
  119. });
  120. var qb_field_value = $('<input type="text" class="fom_query_builder_field_value"/>');
  121. if (this.condition_count == 0)
  122. var qb_condition_btn = $('<button title="Add more condition to query" />')
  123. .html('More conditions')
  124. .click( function() { this_obj.add_query(); } );
  125. else
  126. var qb_condition_btn = $('<button title="Remove this condition" />')
  127. .html('x')
  128. .click( function() { $(this).parent().parent().remove(); } );
  129. var new_row = $('<tr></tr>').html(
  130. $('<td/>').html('Field')
  131. .add( $('<td/>').html($(qb_field_name).add(qb_field_btn)))
  132. .add( $('<td/>').html(qb_field_condition))
  133. .add( $('<td/>').html(qb_field_value))
  134. .add( $('<td/>').html(qb_condition_btn))
  135. );
  136. //$(this.table).find('tr').last().before(new_row);
  137. $(this.table).append(new_row);
  138. this.condition_count++;
  139. this.build_query();
  140. },
  141. clear_query: function() {
  142. while(rows = $(this.table).find('tr'), rows.length > 1) {
  143. rows.last().remove();
  144. }
  145. $(rows.last().children('td')[1]).children('input').val('');
  146. $(rows.last().children('td')[2]).children('select').get(0).selectedIndex=0;
  147. $(rows.last().children('td')[3]).children('input').val('');
  148. this.condition_count = 1;
  149. },
  150. del_query: function() {
  151. if (this.condition_count > 1) {
  152. $(this.table).find('tr').last().prev().remove();
  153. this.condition_count--;
  154. }
  155. },
  156. build_query: function() {
  157. /*
  158. FIXME: detect if adding new query condition conflicts with existing ones
  159. function enhance_query(q, f, cond){
  160. if (!(f in q)) {
  161. q[f] = cond;
  162. } else {
  163. //check conflicting queries
  164. };
  165. return q;
  166. }*/
  167. var field_names = $(this.table).find('.fom_query_builder_field_name');
  168. var field_conditions = $(this.table).find('.fom_query_builder_field_condition');
  169. var field_values = $(this.table).find('.fom_query_builder_field_value');
  170. var rows = $(this.table).find('tr');
  171. var query = {};
  172. for(var i=0; i<field_names.length; i++)
  173. {
  174. var field = $(field_names[i]).val();
  175. var condition = $(field_conditions[i]).val();
  176. var value = $(field_values[i]).val();
  177. try {
  178. if (value != "")
  179. value = $('#fom_utils').fom_utils('json_to_strict', eval('res=' + value));
  180. } catch(e) {
  181. alert('query parsing error:' + e + ' for value:' + value )
  182. throw(e);
  183. };
  184. if ((field == "" && condition != "$where") || condition =="_ignore") continue;
  185. switch(condition) {
  186. case '$exists':
  187. q = {}
  188. q[field]={$exists: true}
  189. $.extend(true, query, q);
  190. break;
  191. case '$nexists':
  192. q = {}
  193. q[field]={$exists: false}
  194. $.extend(true, query, q);
  195. break;
  196. case '$equals':
  197. //query[field] = value;
  198. q = {}
  199. q[field]=value
  200. $.extend(true, query, q);
  201. break;
  202. case '$ne':
  203. q = {}
  204. q[field] = {$ne:value};
  205. $.extend(true, query, q);
  206. break;
  207. case '$gt' :
  208. case '$gte':
  209. case '$lt' :
  210. case '$lte':
  211. q = {}
  212. q[field] = {};
  213. q[field][condition] = value;
  214. $.extend(true, query, q);
  215. break;
  216. case '$in':
  217. case '$nin':
  218. q = {}
  219. q[field] = {};
  220. q[field][condition] = value;
  221. $.extend(true, query, q);
  222. break;
  223. case '$all':
  224. q = {}
  225. q[field] = {$all: value};
  226. $.extend(true, query, q);
  227. break;
  228. case '$size':
  229. q = {}
  230. q[field] = {$size: value};
  231. $.extend(true, query, q);
  232. break;
  233. case '$type':
  234. q = {}
  235. q[field] = {$type: value};
  236. $.extend(true, query, q);
  237. break;
  238. case '$re':
  239. q = {}
  240. q[field] = value;//{$regex:value};
  241. $.extend(true, query, q);
  242. break;
  243. case '$elemMatch':
  244. //alert('val:' + JSON.stringify(value));
  245. q = {}
  246. q[field] = {$elemMatch: value};
  247. //query[field] = q;
  248. $.extend(true, query, q);
  249. break;
  250. case '$where':
  251. q = {$where: value};
  252. $.extend(true, query, q);
  253. break;
  254. };
  255. };
  256. //alert(JSON.stringify(query));
  257. return query;
  258. },
  259. /*
  260. pass array of values to field name autocomplete widget
  261. */
  262. completion_source: function(completions) {
  263. this.options.completion_source = completions;
  264. $(this.table).find('tr td input.fom_query_builder_field_name').autocomplete({minLength:0, source: completions});
  265. },
  266. });
  267. $.widget("ui.fom_query_builder", Fom_query_builder);
  268. /**
  269. *
  270. * Message bus
  271. *
  272. */
  273. Fom_bus = $.extend({}, $.ui.fom_object.prototype,{
  274. _init: function(){
  275. $.ui.fom_object.prototype._init.call(this); // call the original function
  276. this.listeners = new Array();
  277. },
  278. length: function ( ) { return this.listeners.length; },
  279. /* add listeners
  280. params:
  281. listener: fom_object
  282. */
  283. add_listener: function(listener) {
  284. this.listeners[this.listeners.length] = listener;
  285. },
  286. /* send signal
  287. params:
  288. signal_name: name of the signal
  289. signal_source: fom_object instance originating the signal
  290. signal_data: json data related to signal (content depends on signal)
  291. */
  292. signal: function(signal_name, signal_source, signal_data ) {
  293. $.ui.fom_object.prototype.signal.call(this);
  294. for ( var obj in this.listeners)
  295. {
  296. this.listeners[obj].signal(signal_name, signal_source, signal_data);
  297. };
  298. },
  299. });
  300. $.widget("ui.fom_bus", Fom_bus);
  301. //end of message bus
  302. /**
  303. *
  304. * Console ui object - commented out, but I'LL BE BACK)
  305. *
  306. */
  307. /*
  308. Fom_ui_console = $.extend({}, $.ui.fom_object.prototype,{
  309. _init: function(){
  310. $.ui.fom_object.prototype._init.call(this); // call the original function
  311. this.dialog_id = this.options['div_id'] + '_dialog';
  312. this.console_id = this.options['div_id'] + '_console_div';
  313. this.input_id = this.options['div_id'] + '_input';
  314. this.button_id = this.options['div_id'] + '_button';
  315. $('#' + this.options['div_id']).append("<div id='" + this.dialog_id + "'><input type='text' name='" + this.input_id +"' id='" + this.input_id + "'/><button id='" + this.button_id + "'>Run</button><div id='" + this.console_id + "'></div><div></div></div>");
  316. var my_id = '#' + this.options['div_id'];
  317. var input_id = this.input_id;
  318. $('#' + this.button_id).click(function() { $(my_id).trigger('console_exec', [$('#' + input_id).get(0).value]) } );
  319. $('#' + this.input_id).keypress(function(event) { if (event.keyCode == 13) { $(my_id).trigger('console_exec', [$('#' + input_id).get(0).value]) }} );
  320. //dialog - item list
  321. $('#' + this.options['div_id'] + '_dialog').dialog({
  322. autoOpen: true,
  323. height: 500,
  324. width: 400,
  325. modal: false,
  326. closeOnEscape: false,
  327. buttons: {},
  328. title: this.options['title'],
  329. position : [220,100],
  330. }); //end of dialog
  331. $('#' + this.dialog_id).dialog('open');
  332. var dialog_id = this.dialog_id;
  333. //$('#' + this.options['tool_button_id']).click(function () { $('#' + dialog_id).dialog('isOpen')? $('#' + dialog_id).dialog('close') : $('#' + dialog_id).dialog('open');});
  334. },
  335. response_error : function (err) {
  336. }, //end of reponse_error
  337. response : function (data) {
  338. //alert(data);
  339. if (data.type == 'html') {
  340. $('#' + this.console_id).prepend('<div class="fom_console_message">' + data.data + '</div>')
  341. };
  342. }, //end of reponse_error
  343. });
  344. $.widget("ui.fom_ui_console", Fom_ui_console);
  345. //end of console ui object
  346. */
  347. /**
  348. *
  349. * Console object
  350. *
  351. */
  352. /*
  353. Fom_console = $.extend({}, $.ui.fom_object.prototype, {
  354. _init: function(){
  355. $.ui.fom_object.prototype._init.call(this); // call the original function
  356. $('#mongo_ui_header_tools_bus').fom_bus('add_listener', this);
  357. $('#mongo_ui_container').append("<div id='mongo_ui_console'></div>");
  358. $('#mongo_ui_console').fom_ui_console({'title':'Mongo console', 'div_id': 'mongo_ui_console', 'tool_button_id' : 'mongo_ui_header_tools_console' });
  359. var this_obj = this;
  360. $('#mongo_ui_console').bind('console_exec', function(e, cmd){ this_obj.exec_cmd(cmd); });
  361. },
  362. signal: function(signal_name, signal_source, signal_data ) {
  363. if (signal_name == 'app_init')
  364. {
  365. }
  366. else if ( signal_name == 'database_selected')
  367. {
  368. $('#mongo_ui_console_dialog').dialog('option','title','Mongo console [' + signal_data['database'] + ']');
  369. //$('#mongo_ui_database_list').fom_ui_list('set_list', signal_data['data'], signal_data['search'], signal_data['method']);
  370. }
  371. else if ( signal_name == 'collection_selected')
  372. {
  373. var db_name = $('#mongo_ajax').fom_object_mongo_ajax('option','database');
  374. $('#mongo_ui_console_dialog').dialog('option','title','Mongo console [' + db_name + ' -> ' + signal_data['collection'] + ']');
  375. }
  376. },
  377. exec_cmd: function(cmd){
  378. cmd = cmd.trim();
  379. if (cmd.length == 0) {
  380. return;
  381. }
  382. var my_console_instance = this;
  383. if (cmd[0] == ':') { //server command
  384. $('#mongo_ajax').fom_object_mongo_ajax('exec_cmd', my_console_instance, cmd);
  385. } else {
  386. alert('Unknown command: ' + cmd);
  387. }
  388. //alert('cmd:'+ cmd);
  389. },
  390. //process cmd response
  391. process_response: function(data){
  392. if (data.error) {
  393. $('#mongo_ui_console').fom_ui_console('response_error',data.error);
  394. } else {
  395. $('#mongo_ui_console').fom_ui_console('response', data);
  396. }
  397. },
  398. destroy: function(){
  399. $.ui.fom_object.prototype.destroy.call(this); // call the original function
  400. },
  401. });
  402. $.widget("ui.fom_console", Fom_console);
  403. //end of console
  404. */
  405. /**
  406. *
  407. * Item list ui object
  408. * - dialog displaying list of items, with ability to search
  409. */
  410. Fom_item_list = $.extend({}, $.ui.fom_object.prototype,{
  411. _init: function(){
  412. $.ui.fom_object.prototype._init.call(this); // call the original function
  413. this.options['title_prefix'] = this.options['title'];
  414. this.options['has_selected'] = false;
  415. this.dialog_id = this.options['div_id'] + '_dialog';
  416. this.item_list_id = this.options['div_id'] + '_list';
  417. this.input_id = this.options['div_id'] + '_input';
  418. this.search_id = this.options['div_id'] + '_search';
  419. this.clear_id = this.options['div_id'] + '_clear';
  420. var this_obj = this;
  421. $('#' + this.options['div_id']).append("\
  422. <div id='" + this.dialog_id + "'>\
  423. <div class='fom_ui_note'></div>\
  424. <div class='fom_ui_list_items'>\
  425. <div style='width: 99%;' id='" + this.item_list_id + "'></div>\
  426. </div>\
  427. <div class='search_toolbox'>\
  428. <input type='text' name='" + this.input_id +"' id='" + this.input_id + "'/>\
  429. <button id='" + this.search_id + "'>Search</button>\
  430. <button id='" + this.clear_id + "'>Clear</button>\
  431. </div>\
  432. <div class='toolbox'>\
  433. </div>\
  434. </div>");
  435. var my_id = '#' + this.options['div_id'];
  436. var search_id = this.search_id;
  437. var clear_id = this.clear_id;
  438. var input_id = this.input_id;
  439. this.toolbox = $('#'+this_obj.dialog_id).find('.toolbox').get(0);
  440. this.search_toolbox = $('#'+this_obj.dialog_id).find('.search_toolbox').get(0);
  441. $('#' + this.dialog_id).dialog('open');
  442. var dialog_id = this.dialog_id;
  443. $('#' + this.options['tool_button_id']).click(function () {
  444. $('#' + dialog_id).dialog('isOpen')? $('#' + dialog_id).dialog('close') : $('#' + dialog_id).dialog('open');
  445. });
  446. $('#' + this.search_id).button();
  447. $('#' + this.clear_id).button();
  448. //set title properly when appending filter there
  449. $('#' + dialog_id).dialog('option','title_prefix',this.options['title']);
  450. $('#' + search_id).click(function() {
  451. search_term = $('#' + input_id).get(0).value.trim();
  452. if (search_term != '')
  453. dialog_title = $('#' + dialog_id).dialog('option','title_prefix')+' ~' + search_term;
  454. else
  455. dialog_title = $('#' + dialog_id).dialog('option','title_prefix');
  456. $('#' + dialog_id).dialog('option','title', dialog_title); $(my_id).trigger('search', [$('#' + input_id).get(0).value])
  457. });
  458. $('#' + clear_id).click(function() {
  459. $('#' + dialog_id).dialog('option','title',$('#' + dialog_id).dialog('option','title_prefix'));
  460. $('#' + input_id).get(0).value = '';
  461. $(my_id).trigger('search', [''])
  462. });
  463. $('#' + input_id).keyup(function(event) {
  464. if (event.keyCode == 13) {
  465. $('#' + search_id).click();
  466. }
  467. })
  468. if (this.options.disabled) {
  469. this.disable();
  470. };
  471. }, //end of _init
  472. /*
  473. Set list of items
  474. */
  475. set_list: function(item_list, search, method){
  476. var id_name = '#' + this.item_list_id;
  477. var this_obj = this;
  478. this.options['has_selected'] = false;
  479. $('#' + this.item_list_id).empty();
  480. $.each(item_list, function(){
  481. var dn = document.createElement('div');
  482. dn.fom_db = this;
  483. $(dn).addClass('fom_ui_list_item');
  484. dn.innerHTML = $('#fom_utils').fom_utils('escape_html', this);
  485. $(id_name).append( dn );
  486. });
  487. var my_id = '#' + this.options['div_id'];
  488. $('#' + this.item_list_id).children().click(function(){
  489. $(id_name).children().each(function() {
  490. $(this).removeClass('fom_ui_list_item_selected');
  491. });
  492. $(this).addClass('fom_ui_list_item_selected');
  493. this_obj.options['has_selected'] = true;
  494. $(my_id).trigger('fom_item_selected', [this.fom_db]);
  495. });
  496. }, //end of set_list
  497. get_ui_element: function(element) {
  498. switch(element) {
  499. case 'search_input': return $('#' + this.input_id);
  500. case 'search_btn': return $('#' + this.search_id);
  501. case 'clear_btn': return $('#' + this.clear_id);
  502. case 'toolbox': return $(this.toolbox);
  503. default: return null;
  504. };
  505. },
  506. /*
  507. * Clear items
  508. */
  509. clear: function() {
  510. this.options['has_selected'] = false;
  511. $('#' + this.item_list_id).empty();
  512. },
  513. enable: function() {
  514. this.set_enabled(true);
  515. },
  516. disable: function() {
  517. this.set_enabled(false);
  518. },
  519. /*
  520. Check if database has selected items
  521. */
  522. has_selected: function(){
  523. return this.options['has_selected'];
  524. },
  525. /*
  526. Helper: single function for enabling/disabling
  527. */
  528. set_enabled: function(enabled) {
  529. if (enabled) {
  530. $.ui.fom_object.prototype.enable.call(this); // call the original function
  531. method = 'enable';
  532. } else {
  533. method = 'disable';
  534. $.ui.fom_object.prototype.disable.call(this); // call the original function
  535. }
  536. $('#' + this.dialog_id ).dialog(method);
  537. $('#' + this.search_id).button(method);
  538. $('#' + this.clear_id).button(method);
  539. $('#' + this.input_id).attr('disabled', !enabled);
  540. },
  541. destroy: function(){
  542. $.ui.fom_object.prototype.destroy.call(this); // call the original function
  543. },
  544. });
  545. $.widget("ui.fom_ui_list", Fom_item_list);
  546. //end of item list ui object
  547. /*
  548. DATABASE ACCESS
  549. class which allows to access mongodb via ajax calls
  550. */
  551. Fom_mongo_ajax = $.extend({}, $.ui.fom_object.prototype, {
  552. _init: function() {
  553. $('#mongo_ui_header_tools_bus').fom_bus('add_listener', this);
  554. //this.host = null;
  555. //this.port = null;
  556. //this.collection = null;
  557. //this.database = null; },
  558. },
  559. // process server response to exec_cmd
  560. process_response: function(caller_id, data) {
  561. caller_id.process_response(data);
  562. }, // end of process_reponse
  563. /* //this is intended to be use for console plugin
  564. exec_cmd: function(console_obj, cmd){
  565. var url = '/fangofmongo/rest/mongo/cmd/';
  566. var caller_id = console_obj;
  567. var my_console = this;
  568. $.post(url, {'cmd':'help'}, function(data){ my_console.process_response(caller_id, data); }, "json");
  569. }, //end of exec_cmd:*/
  570. /*
  571. * run command against database
  572. * params:
  573. * command: Object with command to perform
  574. */
  575. run_command: function(database, command, callback){
  576. var url = '/fangofmongo/rest/mongo/' + encodeURIComponent(this.options['host']) + '/' + encodeURIComponent(this.options['port']) + '/';
  577. url += 'database/' + encodeURIComponent(database) + '/cmd/'
  578. $.getJSON( url,
  579. {cmd:JSON.stringify(command)},
  580. function(data){
  581. if ( 'error' in data ) { alert('error: ' + data['error']); return data; }
  582. //alert(JSON.stringify(data));
  583. callback(data);
  584. });
  585. }, //end of run_command
  586. /* Get list of databases from mongo server
  587. params:
  588. search (string, optional): text to search
  589. method (string, optional): search method, either null (text search) or 're' (search will be interpreted as regular expression)
  590. */
  591. get_db_list: function(search, method){
  592. this.run_command('admin', //database
  593. {listDatabases : 1}, //command
  594. function(data) { // callback
  595. if ( 'error' in data ) { alert('error: ' + data['error']); return; }
  596. var db_list = Array();
  597. for(obj in data['data']['databases'])
  598. {
  599. db_list.push(data['data']['databases'][obj]['name']);
  600. }
  601. db_list.sort();
  602. if(search) {
  603. db_list = $('#fom_utils').fom_utils('filter_list',db_list, search, method);
  604. }
  605. $('#mongo_ui_header_tools_bus').fom_bus('signal', 'database_list_received', this, {'search':search, 'method':method, 'data' : db_list } );
  606. }
  607. );
  608. }, //end of get_db_list:
  609. /* Get list of collections from mongo server
  610. params:
  611. search (string, optional): text to search
  612. method (string, optional): search method, either null (text search) or 're' (search will be interpreted as regular expression)
  613. */
  614. get_collection_list: function(search, method){
  615. this.get_data(
  616. {$where :'this.name.indexOf("' + this.options['database'] + '.") == 0 && this.name.indexOf("$") == -1'},
  617. {
  618. sort: [['name',1]],
  619. limit: 100,
  620. callback: function(data){
  621. if ( 'error' in data ) { alert('error: ' + data['error']); return; }
  622. var coll_list = Array();
  623. for(obj in data['data'])
  624. coll_list.push(data['data'][obj]['name'].substr(this.options['database'].length+1)); //strip database_name and dot
  625. if (search)
  626. coll_list = $('#fom_utils').fom_utils('filter_list',coll_list, search, method);
  627. $('#mongo_ui_header_tools_bus').fom_bus('signal', 'collection_list_received', this, {'search':search, 'method':method, 'data' : coll_list } );
  628. },
  629. context: this,
  630. database: this.options['database'],
  631. collection: 'system.namespaces'
  632. }
  633. );
  634. }, // end of get_collection_list
  635. /*
  636. save document
  637. options:
  638. document: json data in strict format
  639. callback: function to call when we have response
  640. context
  641. */
  642. save_document: function(options) {
  643. var url = '/fangofmongo/rest/mongo/' + this.options['host'] + '/' + this.options['port'] + '/';
  644. if (!("document" in options)) {
  645. throw("save_document: Missing document");
  646. }
  647. try {
  648. $.ajax({
  649. type: 'POST',
  650. url: url + 'collection/' + encodeURIComponent(this.options['database']) +'/' + encodeURIComponent(this.options['collection']) + '/save_document/',
  651. data: {document: JSON.stringify(options["document"])},
  652. dataType: 'json',
  653. context: ('context' in options) ? options['context'] : null,
  654. success: function(data){
  655. if ( 'error' in data ) { alert('error: ' + data['error']); };
  656. if ('callback' in options)
  657. options['callback'](data);
  658. },
  659. error: function(XMLHttpRequest, textStatus, errorThrown) {
  660. alert('save_document failed status' + textStatus + ' error:' + errorThrown);
  661. },
  662. }); //end of $.ajax
  663. } catch(e) {alert(e); throw(e);};
  664. }, //end of save_document
  665. /*
  666. retrieve collection statistics for selected collection
  667. */
  668. get_collection_stats: function(){
  669. var url = '/fangofmongo/rest/mongo/' + encodeURIComponent(this.options['host']) + '/' + encodeURIComponent(this.options['port']) + '/';
  670. var params = '';
  671. if (params != '') { params = '?' + params; };
  672. try{
  673. $.getJSON( url + 'collection/' + encodeURIComponent(this.options['database']) +'/' + encodeURIComponent(this.options['collection']) + '/stats/' + params,
  674. function(data){
  675. if ( 'error' in data ) { alert('error: ' + data['error']); return; }
  676. $('#mongo_ui_header_tools_bus').fom_bus('signal', 'collection_stats_received', this, {'data' : data['data'] } );
  677. }
  678. ); //end of $.getJSON
  679. } catch(e) {alert(e); throw(e);};
  680. }, // end of get_collection_stats
  681. /*
  682. retrieve collection indexes for selected collection
  683. */
  684. get_collection_indexes: function(){
  685. var url = '/fangofmongo/rest/mongo/' + encodeURIComponent(this.options['host']) + '/' + encodeURIComponent(this.options['port']) + '/';
  686. var params = '';
  687. if (params != '') { params = '?' + params; };
  688. try{
  689. $.getJSON( url + 'collection/' + encodeURIComponent(this.options['database']) +'/' + encodeURIComponent(this.options['collection']) + '/indexes/' + params,
  690. function(data){
  691. if ( 'error' in data ) { alert('error: ' + data['error']); return; }
  692. $('#mongo_ui_header_tools_bus').fom_bus('signal', 'collection_indexes_received', this, {'data' : data['data'] } );
  693. }
  694. ); //end of $.getJSON
  695. } catch(e) {alert(e);};
  696. }, // end of get_collection_stats
  697. /*
  698. get documents matching given criteria
  699. params:
  700. query: JSON representing query
  701. options: dictionary with:
  702. limit: number of documents to retrieve
  703. skip: how many documents ommit from results
  704. sort: sort order, in mongo format: array of arrays ["fieldname", "ordering"], for example: [["_id",1]]
  705. callback: callback function
  706. context: context object
  707. returns JSON with results
  708. */
  709. get_data: function(query, options){
  710. var url = '/fangofmongo/rest/mongo/' + encodeURIComponent(this.options['host']) + '/' + encodeURIComponent(this.options['port']) + '/';
  711. var params = '';
  712. query_data = {
  713. q: JSON.stringify(query),
  714. limit: options['limit'],
  715. skip: options['skip']
  716. };
  717. var db = 'database' in options ? options['database'] : this.options['database'];
  718. var coll = 'collection' in options ? options['collection'] : this.options['collection'];
  719. if (options['sort'])
  720. query_data['sort'] = JSON.stringify(options['sort']);
  721. $.ajax({
  722. url: url + 'collection/' + encodeURIComponent(db) + '/' + encodeURIComponent(coll) + '/query/' + params,
  723. dataType: 'json',
  724. data: query_data,
  725. success: options['callback'],
  726. context: ('context' in options) ? options['context'] : null,
  727. error: function(XMLHttpRequest, textStatus, errorThrown) {
  728. alert('get_data failed status' + textStatus + ' error:' + errorThrown);
  729. },
  730. });
  731. }, //end of get_data
  732. /*
  733. Perform operation on mongodb
  734. params:
  735. options: dictionary with options. Available options depend on the operation
  736. operation: name of the operations
  737. subject: one of: server, database, collection, document
  738. callback: function to perform when operation is complete
  739. context: context object passed to callback
  740. */
  741. operation : function(options) {
  742. if (!('operation' in options) || !('subject' in options)) {
  743. throw 'operation: missing params';
  744. }
  745. var url = '/fangofmongo/rest/mongo/' + encodeURIComponent(this.options['host']) + '/' + encodeURIComponent(this.options['port']) + '/cmd/';
  746. var data = {};
  747. switch(options['subject']) {
  748. case 'server':
  749. switch(options['operation']) {
  750. case 'create_database':
  751. data['cmd'] = 'create_database';
  752. data['database_name'] = options['database_name'];
  753. break;
  754. case 'drop_database':
  755. data['cmd'] = 'drop_database';
  756. data['database_name'] = options['database_name'];
  757. break;
  758. default: throw ('operation: incorrect params');
  759. }
  760. break;
  761. case 'database':
  762. switch(options['operation']) {
  763. case 'create_collection':
  764. data['cmd'] = 'create_collection';
  765. data['database'] = options['database']
  766. data['collection_name'] = options['collection_name'];
  767. break;
  768. case 'drop_collection':
  769. data['cmd'] = 'drop_collection';
  770. data['database'] = options['database']
  771. data['collection_name'] = options['collection_name'];
  772. break;
  773. default: throw ('operation: incorrect params');
  774. }
  775. break;
  776. default: throw ('operation: incorrect params');
  777. }
  778. $.ajax({
  779. url: url,
  780. type: 'POST',
  781. success: options['callback'],
  782. data: data,
  783. dataType: 'json',
  784. context: ('context' in options) ? options['context'] : null,
  785. error: function(XMLHttpRequest, textStatus, errorThrown) {
  786. alert('operation failed status: ' + textStatus + ' error:' + errorThrown);
  787. },
  788. });
  789. },
  790. signal: function(signal_name, signal_source, signal_data ) {
  791. if (signal_name == 'database_selected')
  792. {
  793. this.options['database'] = signal_data['database'];
  794. }
  795. if (signal_name == 'collection_selected')
  796. {
  797. this.options['collection'] = signal_data['collection'];
  798. }
  799. },
  800. }); //end of widget ui.fom_object.db
  801. $.widget("ui.fom_object_mongo_ajax", Fom_mongo_ajax);
  802. /**
  803. *
  804. * Init UI objects
  805. *
  806. */
  807. //init utils
  808. $('#fom_utils').fom_utils();
  809. //init bus
  810. $('#mongo_ui_header_tools_bus').fom_bus();
  811. $('#mongo_ui_container').append("<div id='mongo_ajax'></div>");
  812. $('#mongo_ajax').fom_object_mongo_ajax({'host':connection_params['host'], 'port': connection_params['port'], 'database' : null, 'collection' : null });
  813. //init console
  814. //$('#mongo_ui_container').append("<div id='mongo_console'></div>");
  815. //$('#mongo_console').fom_console();
  816. //set locale
  817. $.format.locale({
  818. number: {
  819. groupingSeparator: ' ',
  820. decimalSeparator: '.'
  821. }
  822. });
  823. //initialize all plugins
  824. fom_init_about();
  825. fom_init_coll_info();
  826. fom_init_coll_list();
  827. fom_init_db_list();
  828. //tell everybody we are starting the party
  829. $(window).load( function() {
  830. $('#mongo_ui_header_tools_bus').fom_bus('signal', 'app_init', this, {} );
  831. });
  832. //hide error msg
  833. $('#errormsg').hide();
  834. }); //end of function
  835. } //end of fom_init_mongo_ui