1 function removeReportAtom (args) {
4 var active_tab = filterByAttribute(
5 $('used-source-fields-tabbox').getElementsByTagName('tab'),
9 var tabname = active_tab.getAttribute('id');
11 var tabpanel = $( tabname + 'panel' );
12 var tree = tabpanel.getElementsByTagName('tree')[0];
13 var fields = getSelectedItems(tree);
16 for (var i in fields) {
17 var field = fields[i];
18 var colname = field.firstChild.firstChild.nextSibling.getAttribute('label');
19 var relation_alias = field.getAttribute('relation');
21 delete rpt_rel_cache[relation_alias].fields[tabname][colname];
22 if (tabname == 'dis_tab') {
24 for each (var _o_col in rpt_rel_cache.order_by) {
25 if (_o_col.relation == relation_alias && _o_col.field == colname) continue;
26 _o_tmp.push( _o_col );
28 rpt_rel_cache.order_by = _o_tmp
31 with (rpt_rel_cache[relation_alias].fields) {
32 if ( getKeys(dis_tab).length == 0 && getKeys(filter_tab).length == 0 && getKeys(aggfilter_tab).length == 0 )
33 delete rpt_rel_cache[relation_alias];
42 function getSourceDefinition(class) {
43 var class_obj = getIDLClass(class);
44 return class_obj.getAttributeNS(persistNS,'tablename') || '(' + class_obj.getElementsByTagNameNS(persistNS,'source_definition')[0].nodeValue + ')';
47 function addReportAtoms () {
48 var nope = $( 'source-add' ).getAttribute('disabled');
49 if (nope == 'true') return false;
51 var class_tree = $('class-view');
52 var transform_tree = $('trans-view');
54 var active_tab = filterByAttribute(
55 $('used-source-fields-tabbox').getElementsByTagName('tab'),
60 var tabname = active_tab.getAttribute('id')
62 var items = getSelectedItems(class_tree);
63 var transform = getSelectedItems(transform_tree)[0];
65 var reltype = $('path-label').getAttribute('reltype');
66 var class_label = $('path-label').value;
67 var relation_alias = hex_md5(class_label);
69 for (var i in items) {
72 var class_path = item.getAttribute('fullpath');
73 var field_class = item.getAttribute('idlclass');
74 var datatype = item.getAttribute('datatype');
75 var colname = item.getAttribute('idlfield');
76 var field_label = item.firstChild.firstChild.getAttribute('label');
78 var table_name = getSourceDefinition(field_class);
80 if ( !rpt_rel_cache[relation_alias] ) {
81 rpt_rel_cache[relation_alias] =
82 { label : class_label,
83 alias : relation_alias,
86 idlclass : field_class,
88 fields: { dis_tab : {}, filter_tab : {}, aggfilter_tab : {} }
92 if ( !rpt_rel_cache[relation_alias].fields[tabname][colname] ) {
93 rpt_rel_cache[relation_alias].fields[tabname][colname] =
95 transform : (transform && transform.getAttribute('name')) || 'Bare',
96 aggregate : transform && transform.getAttribute('aggregate'),
97 params : transform && transform.getAttribute('params'),
98 transform_label: (transform && transform.getAttribute('alias')) || 'Raw Data',
106 if (!rpt_rel_cache.order_by)
107 rpt_rel_cache.order_by = [];
109 if (tabname == 'dis_tab')
110 rpt_rel_cache.order_by.push( { relation : relation_alias, field : colname } );
114 'You have already added the [' + field_label +
115 '] field\nfrom the [' + class_label + '] source. Click OK if you\nwould like ' +
116 'to reset this field.'
119 rpt_rel_cache[relation_alias].fields[tabname][colname] =
121 transform : (transform && transform.getAttribute('name')) || 'Bare',
122 aggregate : transform && transform.getAttribute('aggregate'),
123 params : transform && transform.getAttribute('params'),
124 transform_label: (transform && transform.getAttribute('alias')) || 'Raw Data',
139 function changeDisplayOrder (dir) {
140 var active_tab = filterByAttribute(
141 $('used-source-fields-tabbox').getElementsByTagName('tab'),
146 var tabname = active_tab.getAttribute('id');
148 var tabpanel = $( tabname + 'panel' );
149 var tree = tabpanel.getElementsByTagName('tree')[0];
150 var item = getSelectedItems(tree)[0];
152 var item_pos = tree.view.selection.currentIndex;
155 if ( item.previousSibling ) {
156 item.parentNode.insertBefore( item, item.previousSibling );
159 } else if (dir == 'd') {
160 if ( item.nextSibling ) {
161 if (item.nextSibling.nextSibling ) item.parentNode.insertBefore( item, item.nextSibling.nextSibling );
162 else item.parentNode.appendChild( item );
167 rpt_rel_cache.order_by = [];
168 var ordered_list = tree.getElementsByTagName('treeitem');
169 for (var i = 0; i < ordered_list.length; i++) {
170 rpt_rel_cache.order_by.push(
171 { relation : ordered_list[i].getAttribute('relation'),
172 field : ordered_list[i].firstChild.firstChild.nextSibling.getAttribute('label')
177 tree.view.selection.select( item_pos );
181 function alterColumnLabel () {
182 var active_tab = filterByAttribute(
183 $('used-source-fields-tabbox').getElementsByTagName('tab'),
188 var tabname = active_tab.getAttribute('id');
190 var tabpanel = $( tabname + 'panel' );
191 var tree = tabpanel.getElementsByTagName('tree')[0];
192 var item_pos = tree.view.selection.currentIndex;
194 var item = getSelectedItems(tree)[0];
195 var relation_alias = item.getAttribute('relation');
197 var field = item.firstChild.firstChild;
198 var colname = field.nextSibling.getAttribute('label');
200 var new_label = prompt(
201 "Change the column header to:",
202 field.getAttribute("label")
206 rpt_rel_cache[relation_alias].fields[tabname][colname].alias = new_label;
208 tree.view.selection.select( item_pos );
216 function alterColumnTransform (trans) {
218 var transform = OILS_RPT_TRANSFORMS[trans];
220 var active_tab = filterByAttribute(
221 $('used-source-fields-tabbox').getElementsByTagName('tab'),
226 var tabname = active_tab.getAttribute('id');
228 var tabpanel = $( tabname + 'panel' );
229 var tree = tabpanel.getElementsByTagName('tree')[0];
230 var item_pos = tree.view.selection.currentIndex;
231 var item = getSelectedItems(tree)[0];
232 var relation_alias = item.getAttribute('relation');
234 var field = item.firstChild.firstChild;
235 var colname = field.nextSibling.getAttribute('label');
237 rpt_rel_cache[relation_alias].fields[tabname][colname].transform = trans;
238 rpt_rel_cache[relation_alias].fields[tabname][colname].aggregate = transform.aggregate;
239 rpt_rel_cache[relation_alias].fields[tabname][colname].params = transform.params;
240 rpt_rel_cache[relation_alias].fields[tabname][colname].transform_label = transform.label;
243 tree.view.selection.select( item_pos );
247 $(tabname + '_trans_menu').hidePopup();
251 function changeOperator (args) {
253 var active_tab = filterByAttribute(
254 $('used-source-fields-tabbox').getElementsByTagName('tab'),
259 var tabname = active_tab.getAttribute('id');
261 var tabpanel = $( tabname + 'panel' );
262 var tree = tabpanel.getElementsByTagName('tree')[0];
263 var item_pos = tree.view.selection.currentIndex;
264 var item = getSelectedItems(tree)[0];
266 var relation_alias = item.getAttribute('relation');
268 var field = item.firstChild.firstChild;
269 var colname = field.nextSibling.getAttribute('label');
271 rpt_rel_cache[relation_alias].fields[tabname][colname].op = args.op;
272 rpt_rel_cache[relation_alias].fields[tabname][colname].op_label = args.label;
275 tree.view.selection.select( item_pos );
279 $(tabname + '_op_menu').hidePopup();
283 function removeTemplateFilterValue () {
285 var active_tab = filterByAttribute(
286 $('used-source-fields-tabbox').getElementsByTagName('tab'),
291 var tabname = active_tab.getAttribute('id');
293 var tabpanel = $( tabname + 'panel' );
294 var tree = tabpanel.getElementsByTagName('tree')[0];
295 var item_pos = tree.view.selection.currentIndex;
296 var items = getSelectedItems(tree);
298 for (var i in items) {
300 var relation_alias = item.getAttribute('relation');
302 var field = item.firstChild.firstChild;
303 var colname = field.nextSibling.getAttribute('label');
305 rpt_rel_cache[relation_alias].fields[tabname][colname].op_value = {};
309 tree.view.selection.select( item_pos );
313 function timestampSetDate (obj, cal, date) {
314 obj.op_value.value = date;
315 obj.op_value.object = cal.date;
316 obj.op_value.label = '"' + date + '"';
324 function changeTemplateFilterValue () {
326 var active_tab = filterByAttribute(
327 $('used-source-fields-tabbox').getElementsByTagName('tab'),
332 var tabname = active_tab.getAttribute('id');
334 var tabpanel = $( tabname + 'panel' );
335 var tree = tabpanel.getElementsByTagName('tree')[0];
336 var items = getSelectedItems(tree);
338 var targetCmd = $( tabname + '_value_action' );
340 targetCmd.menu = null;
341 targetCmd.command = null;
342 targetCmd.oncommand = null;
343 targetCmd.removeEventListener( 'command', __handler_cache, true );
345 for (var i in items) {
347 var relation_alias = item.getAttribute('relation');
349 var field = item.firstChild.firstChild;
350 var colname = field.nextSibling.getAttribute('label');
352 var obj = rpt_rel_cache[relation_alias].fields[tabname][colname]
353 var operation = OILS_RPT_FILTERS[obj.op];
355 switch (obj.datatype) {
357 var cal_popup = $('calendar-widget');
359 while (cal_popup.firstChild) cal_popup.removeChild(cal_popup.lastChild);
360 var calendar = new Calendar(
363 function (cal,date) { return timestampSetDate(obj,cal,date) },
364 function (cal) { cal_popup.hidePopup(); cal.destroy(); return true; }
367 var format = OILS_RPT_TRANSFORMS[obj.transform].cal_format || '%Y-%m-%d';
369 calendar.setDateFormat(format);
370 calendar.create(cal_popup);
372 targetCmd.menu = 'calendar-widget';
378 function __bool_value_event_handler () {
382 // get a reference to the prompt service component.
383 var promptService = Components.classes["@mozilla.org/embedcomp/prompt-service;1"]
384 .getService(Components.interfaces.nsIPromptService);
386 // set the buttons that will appear on the dialog. It should be
387 // a set of constants multiplied by button position constants. In this case,
388 // three buttons appear, Save, Cancel and a custom button.
389 var flags=promptService.BUTTON_TITLE_IS_STRING * promptService.BUTTON_POS_0 +
390 promptService.BUTTON_TITLE_IS_STRING * promptService.BUTTON_POS_1 +
391 promptService.BUTTON_TITLE_CANCEL * promptService.BUTTON_POS_2;
393 // display the dialog box. The flags set above are passed
394 // as the fourth argument. The next three arguments are custom labels used for
395 // the buttons, which are used if BUTTON_TITLE_IS_STRING is assigned to a
396 // particular button. The last two arguments are for an optional check box.
397 answer = promptService.select(
400 "Select the value, or cancel:",
401 2, ["True", "False"], state
405 state = confirm("Click OK for TRUE and Cancel for FALSE.");
406 state ? state = 0 : state = 1;
411 obj.op_value.value = 'f';
412 obj.op_value.label = 'False';
414 obj.op_value.value = 't';
415 obj.op_value.label = 'True';
419 targetCmd.removeEventListener( 'command', __bool_value_event_handler, true );
421 tree.view.selection.select( item_pos );
425 __handler_cache = __bool_value_event_handler;
426 targetCmd.addEventListener( 'command', __bool_value_event_handler, true );
433 var promptstring = "Field does not match one of list (comma separated):";
437 promptstring = "Field value is not between (comma separated):";
441 promptstring = "Field value is between (comma separated):";
445 promptstring = "Field does not match one of list (comma separated):";
449 promptstring = "Field matches one of list (comma separated):";
453 promptstring = "Value " + obj.op_label + ":";
457 function __default_value_event_handler () {
459 if (_v = prompt( promptstring, obj.op_value.value || '' )) {
465 obj.op_value.value = _v.split(/\s*,\s*/);
469 obj.op_value.value = _v;
473 obj.op_value.label = '"' + obj.op_value.value + '"';
476 targetCmd.removeEventListener( 'command', __default_value_event_handler, true );
478 tree.view.selection.select( item_pos );
482 __handler_cache = __default_value_event_handler;
483 targetCmd.addEventListener( 'command', __default_value_event_handler, true );
492 function populateOperatorContext () {
494 var active_tab = filterByAttribute(
495 $('used-source-fields-tabbox').getElementsByTagName('tab'),
500 var tabname = active_tab.getAttribute('id');
502 var tabpanel = $( tabname + 'panel' );
503 var tree = tabpanel.getElementsByTagName('tree')[0];
504 var items = getSelectedItems(tree);
507 for (var i in items) {
509 dtypes.push( item.getAttribute('datatype') );
512 var menu = $(tabname + '_op_menu');
513 while (menu.firstChild) menu.removeChild(menu.lastChild);
515 for (var i in OILS_RPT_FILTERS) {
516 var o = OILS_RPT_FILTERS[i];
520 onmouseup : "changeOperator({op:'"+i+"',label:'"+o.label+"'})"
525 var keys = getKeys(o.labels);
526 for ( var k in keys ) {
528 if ( grep(function(x){return key==x},dtypes).length ) {
531 { label : o.labels[key],
532 onmouseup : "changeOperator({op:'"+i+"',label:'"+o.labels[key]+"'});"
542 function populateTransformContext () {
544 var active_tab = filterByAttribute(
545 $('used-source-fields-tabbox').getElementsByTagName('tab'),
550 var tabname = active_tab.getAttribute('id');
552 var tabpanel = $( tabname + 'panel' );
553 var tree = tabpanel.getElementsByTagName('tree')[0];
554 var items = getSelectedItems(tree);
557 for (var i in items) {
559 var dtype = item.getAttribute('datatype');
560 var item_transforms = getTransforms({ datatype : dtype });
562 for (var j in item_transforms) {
563 transforms[item_transforms[j]] = OILS_RPT_TRANSFORMS[item_transforms[j]];
564 transforms[item_transforms[j]].name = item_transforms[j];
568 var transformList = [];
569 for (var i in transforms) {
570 transformList.push( transforms[i] );
573 transformList.sort( sortHashLabels );
575 var menu = $(tabname + '_trans_menu');
576 while (menu.firstChild) menu.removeChild(menu.lastChild);
578 for (var i in transformList) {
579 var t = transformList[i];
581 if (tabname.match(/filter/)) {
582 if (tabname.match(/^agg/)) {
583 if (!t.aggregate) continue;
585 if (t.aggregate) continue;
591 { aggregate : t.aggregate,
596 onmouseup : "alterColumnTransform('"+t.name+"')"
602 menu.parentNode.setAttribute('disabled','false');
603 if (menu.childNodes.length == 0) {
604 menu.parentNode.setAttribute('disabled','true');
609 function renderSources (selected) {
611 var tree = $('used-sources');
612 var sources = $('used-sources-treetop');
613 var tabs = $('used-source-fields-tabbox').getElementsByTagName('tab');
616 while (sources.firstChild) sources.removeChild(sources.lastChild);
618 selected = getSelectedItems(tree);
619 if (!selected.length) {
620 selected = undefined;
621 while (sources.firstChild) sources.removeChild(sources.lastChild);
625 for (var j = 0; j < tabs.length; j++) {
627 var tabname = tab.getAttribute('id')
628 var tabpanel = $( tab.getAttribute('id') + 'panel' );
629 var fieldtree = tabpanel.getElementsByTagName('treechildren')[0];
631 while (fieldtree.firstChild) fieldtree.removeChild(fieldtree.lastChild);
634 for (var relation_alias in rpt_rel_cache) {
635 if (!rpt_rel_cache[relation_alias].fields) continue;
641 return x.getAttribute('relation') == relation_alias;
648 $('used-sources-treetop').appendChild(
650 { relation : rpt_rel_cache[relation_alias].alias,
651 idlclass : rpt_rel_cache[relation_alias].idlclass,
652 reltype : rpt_rel_cache[relation_alias].reltype,
653 path : rpt_rel_cache[relation_alias].path,
657 createTreeCell({ label : rpt_rel_cache[relation_alias].label }),
658 createTreeCell({ label : rpt_rel_cache[relation_alias].table }),
659 createTreeCell({ label : rpt_rel_cache[relation_alias].alias }),
660 createTreeCell({ label : rpt_rel_cache[relation_alias].reltype })
666 for each (var tabname in ['filter_tab','aggfilter_tab']) {
667 tabpanel = $( tabname + 'panel' );
668 fieldtree = tabpanel.getElementsByTagName('treechildren')[0];
670 for (var colname in rpt_rel_cache[relation_alias].fields[tabname]) {
671 with (rpt_rel_cache[relation_alias].fields[tabname][colname]) {
672 fieldtree.appendChild(
674 { relation : relation_alias, datatype : datatype },
677 createTreeCell({ label : alias }),
678 createTreeCell({ label : colname }),
679 createTreeCell({ label : datatype }),
680 createTreeCell({ label : transform_label }),
681 createTreeCell({ label : transform })
686 fieldtree.lastChild.firstChild.appendChild(
687 createTreeCell({ op : op, label : op_label })
690 if (op_value.value != undefined) {
691 fieldtree.lastChild.firstChild.appendChild(
692 createTreeCell({ label : op_value.label })
700 tabpanel = $( 'dis_tabpanel' );
701 fieldtree = tabpanel.getElementsByTagName('treechildren')[0];
702 for each (var order in rpt_rel_cache.order_by) {
708 return x.getAttribute('relation') == order.relation;
715 with (rpt_rel_cache[order.relation].fields.dis_tab[order.field]) {
716 fieldtree.appendChild(
718 { relation : order.relation, datatype : datatype },
721 createTreeCell({ label : alias }),
722 createTreeCell({ label : colname }),
723 createTreeCell({ label : datatype }),
724 createTreeCell({ label : transform_label }),
725 createTreeCell({ label : transform })
730 fieldtree.lastChild.firstChild.appendChild(
731 createTreeCell({ op : op, label : op_label })
734 if (op_value.value != undefined) {
735 fieldtree.lastChild.firstChild.appendChild(
736 createTreeCell({ label : op_value.label })
746 filter_tab : 'where',
747 aggfilter_tab : 'having',
751 function save_template () {
756 core_class : $('sources-treetop').getElementsByTagName('treeitem')[0].getAttribute('idlclass'),
764 for (var relname in rpt_rel_cache) {
765 var relation = rpt_rel_cache[relname];
766 if (!relation.fields) continue;
768 // first, add the where and having clauses (easier)
769 for each (var tab_name in [ 'filter_tab', 'aggfilter_tab' ]) {
770 var tab = relation.fields[tab_name];
771 for (var field in tab) {
772 fleshTemplateField( template, relation, tab_name, field );
776 // now the from clause
777 fleshFromPath( template, relation );
780 // and now for select (based on order_by)
781 for each (var order in rpt_rel_cache.order_by)
782 fleshTemplateField( template, rpt_rel_cache[order.relation], 'dis_tab', order.field );
784 template.rel_cache = rpt_rel_cache;
786 //prompt( 'template', js2JSON( template ) );
788 // and the saving throw ...
790 var session = cgi.param('ses');
791 fetchUser( session );
794 tmpl.name( $('template-name').value );
795 tmpl.description( $('template-description').value );
796 tmpl.owner(USER.id());
797 tmpl.folder(cgi.param('folder'));
798 tmpl.data(js2JSON(template));
800 if(!confirm('Name : '+tmpl.name() + '\nDescription: ' + tmpl.description()+'\nSave Template?'))
803 var req = new Request('open-ils.reporter:open-ils.reporter.template.create', session, tmpl);
804 req.request.alertEvent = false;
807 var res = r.getResultObject();
808 if(checkILSEvent(res)) {
811 if( res && res != '0' ) {
812 confirm('Template ' + tmpl.name() + ' was successfully saved.');
813 _l('../oils_rpt.xhtml');
822 function fleshFromPath ( template, rel ) {
823 var table_path = rel.path.split( /\./ );
824 if (table_path.length > 1 || rel.path.indexOf('-') > -1) table_path.push( rel.idlclass );
828 var current_path = '';
829 var current_obj = template.from;
831 while (link = table_path.shift()) {
832 if (current_path) current_path += '-';
833 current_path += link;
835 var leaf = table_path.length == 0 ? true : false;
837 current_obj.path = current_path;
838 current_obj.table = getSourceDefinition( link.split(/-/)[0] );
840 if (prev_link != '') {
841 var prev_class = getIDLClass( prev_link.split(/-/)[0] );
842 var prev_field = prev_link.split(/-/)[1];
844 var current_link = getIDLLink( prev_class, prev_field );
845 current_obj.key = current_link.getAttribute('key');
849 current_link.getAttribute('reltype') != 'has_a' ||
850 prev_type == 'left' ||
851 rel.reltype != 'has_a'
853 // getKeys(rel.fields.filter_tab).length == 0 &&
854 // getKeys(rel.fields.aggfitler_tab).length == 0
856 ) current_obj.type = 'left';
858 prev_type = current_obj.type;
862 current_obj.label = rel.label;
863 current_obj.alias = rel.alias;
864 current_obj.idlclass = rel.idlclass;
865 current_obj.template_path = rel.path;
867 var current_class = getIDLClass( link.split(/-/)[0] );
868 var join_field = link.split(/-/)[1];
869 var join_link = getIDLLink(current_class, join_field);
871 if (join_link.getAttribute('reltype') != 'has_a') {
872 var fields_el = current_class.getElementsByTagName('fields')[0];
874 fields_el.getAttributeNS(persistNS, 'primary') +
875 '-' + join_link.getAttribute('class') +
876 '-' + join_link.getAttribute('key');
879 if (!current_obj.alias) current_obj.alias = hex_md5( current_path ) ;
880 join_field += '-' + current_obj.alias;
882 if (!current_obj.join) current_obj.join = {};
883 if (!current_obj.join[join_field]) current_obj.join[join_field] = {};
885 if (current_obj.type == 'left') current_obj.join[join_field].type = 'left';
887 current_obj = current_obj.join[join_field];
896 function fleshTemplateField ( template, rel, tab_name, field ) {
898 if (!rel.fields[tab_name] || !rel.fields[tab_name][field]) return;
900 var tab = rel.fields[tab_name];
902 var table_path = rel.path.split( /\./ );
903 if (table_path.length > 1 || rel.path.indexOf('-') > -1)
904 table_path.push( rel.idlclass );
906 table_path.push( field );
908 var field_path = table_path.join('-');
911 alias : tab[field].alias,
914 transform : tab[field].transform,
915 transform_label : tab[field].transform_label
921 if (tab_name.match(/filter/)) {
922 element.condition = {};
923 if (tab[field].op == 'is' || tab[field].op == 'is not' || tab[field].op == 'is blank' || tab[field].op == 'is not blank') {
924 element.condition[tab[field].op] = null;
926 element.condition[tab[field].op] =
927 tab[field].op_value.value ?
928 tab[field].op_value.value :
929 '::P' + param_count++;
933 template[tab_use[tab_name]].push(element);