]> git.evergreen-ils.org Git - working/Evergreen.git/blob - Open-ILS/xul/staff_client/server/serial/manage_subs.js
Serial Control: Use Dijit-based issuance editor
[working/Evergreen.git] / Open-ILS / xul / staff_client / server / serial / manage_subs.js
1 dump('entering serial/manage_subs.js\n');
2 // vim:et:sw=4:ts=4:
3
4 if (typeof serial == 'undefined') serial = {};
5 serial.manage_subs = function (params) {
6     try {
7         netscape.security.PrivilegeManager.enablePrivilege("UniversalXPConnect");
8         JSAN.use('util.error'); this.error = new util.error();
9     } catch(E) {
10         dump('serial/manage_subs: ' + E + '\n');
11     }
12 };
13
14 serial.manage_subs.prototype = {
15
16     'map_tree' : {},
17     'map_ssub' : {},
18     'map_sdist' : {},
19     'map_siss' : {},
20     'map_scap' : {},
21     'sel_list' : [],
22     'funcs' : [],
23     'editor_indexes' : { 'ssub' : 1, 'sdist' : 2, 'siss' : 3, 'scap' : 4 },
24
25     'ids_from_sel_list' : function(type) {
26         var obj = this;
27         JSAN.use('util.functional');
28
29         var list = util.functional.map_list(
30             util.functional.filter_list(
31                 obj.sel_list,
32                 function (o) {
33                     return o.split(/_/)[0] == type;
34                 }
35             ),
36             function (o) {
37                 return o.split(/_/)[1];
38             }
39         );
40
41         return list;
42     },
43
44     'editor_init' : function(type, mode, params) {
45         var obj = this;
46         try {
47             $('serial_manage_subs_editor_deck').selectedIndex = obj.editor_indexes[type];
48
49             if (type == "siss") { // begin transition from xul to dojo editors
50                 var iframe = dojo.byId('alt_siss_editor');
51                 var src;
52                 if (mode == "add") {
53                     src = '/eg/serial/edit_siss/new/' + params.sisses[0].subscription();
54                     iframe.refresh_command = function () {obj.refresh_list();};
55                 } else {
56                     src = '/eg/serial/edit_siss/' + params.siss_ids[0];
57                     iframe.refresh_command = function () { /* TODO: redraw tree node */ };
58                 }
59                 iframe.setAttribute("src", src);
60             } else {
61                 var editor_type = type + '_editor';
62                 if (typeof obj[editor_type] == 'undefined') {
63                     JSAN.use('serial.' + editor_type);
64                     obj[editor_type] = new serial[editor_type]();
65                 }
66
67                 params.do_edit = true;
68                 params.handle_update = true;
69                 params.trigger_refresh = true;
70                 if (mode == 'add') {
71                     params.refresh_command = function () {obj.refresh_list();};
72                 } else {
73                     params.refresh_command = function () {obj.remap_node(type, this);};
74                 }
75
76                 obj[editor_type].init(params);
77             }
78         } catch(E) {
79             obj.error.standard_unexpected_error_alert('editor_init() error',E);
80         }
81     },
82
83     // while not a true tree node repace, this should at least prevent
84     // non-display side-effects.  True node replace is TODO
85     'remap_node' : function(type, editor_obj) {
86         var obj = this;
87         try {
88             for (i = 0; i < editor_obj[editor_obj.fm_type_plural].length; i++) {
89                 var new_obj = editor_obj[editor_obj.fm_type_plural][i];
90                 var old_obj = obj['map_' + type][type + '_' + new_obj.id()];
91                 if (type == 'ssub') { // add children back on
92                     new_obj.distributions(old_obj.distributions());
93                     new_obj.issuances(old_obj.issuances());
94                     new_obj.scaps(old_obj.scaps());
95                 }
96                 obj['map_' + type][type + '_' + new_obj.id()] = new_obj;
97             }
98             editor_obj.render();
99         } catch(E) {
100             obj.error.standard_unexpected_error_alert('remap_node() error',E);
101         }
102     },
103
104     'do_delete' : function(type, method, overridable_events) {
105         var obj = this;
106         try {
107             JSAN.use('util.functional');
108
109             var list = util.functional.filter_list(
110                 obj.sel_list,
111                 function (o) {
112                     return o.split(/_/)[0] == type;
113                 }
114             );
115
116             list = util.functional.map_list(
117                 list,
118                 function (o) {
119                     return JSON2js( js2JSON( obj['map_' + type][ type + '_' + o.split(/_/)[1] ] ) );
120                 }
121             );
122
123             //TODO: proper messages
124             var delete_msg;
125             if (list.length != 1) {
126                 delete_msg = document.getElementById('serialStrings').getFormattedString('staff.serial.manage_subs.delete_' + type + '.confirm.plural', [list.length]);
127             } else {
128                 delete_msg = document.getElementById('serialStrings').getString('staff.serial.manage_subs.delete_' + type + '.confirm');
129             }
130             var r = obj.error.yns_alert(
131                     delete_msg,
132                     document.getElementById('serialStrings').getString('staff.serial.manage_subs.delete_' + type + '.title'),
133                     document.getElementById('catStrings').getString('staff.cat.copy_browser.delete_items.delete'),
134                     document.getElementById('catStrings').getString('staff.cat.copy_browser.delete_items.cancel'),
135                     null,
136                     document.getElementById('commonStrings').getString('common.confirm')
137             );
138
139             if (r == 0) {
140                 for (var i = 0; i < list.length; i++) {
141                     list[i].isdeleted('1');
142                 }
143                 var robj = obj.network.request(
144                     'open-ils.serial', 
145                     method, 
146                     [ ses(), list, true ],
147                     null,
148                     {
149                         'title' : document.getElementById('serialStrings').getString('staff.serial.manage_subs.delete_' + type + '.override'),
150                         'overridable_events' : overridable_events
151                     }
152                 );
153                 if (robj == null) throw(robj);
154                 if (typeof robj.ilsevent != 'undefined') {
155                     if (robj.ilsevent != 0) {
156                         var overridable = false;
157                         for (i = 0; i < overridable_events.length; i++) {
158                             if (overridable_events[i] == robj.ilsevent) {
159                                 overridable = true;
160                                 break;
161                             }
162                         }
163                         if (!overridable) throw(robj);
164                     }
165                 }
166                 obj.refresh_list();
167             }
168         } catch(E) {
169             obj.error.standard_unexpected_error_alert(document.getElementById('serialStrings').getString('staff.serial.manage_subs.delete.error'),E);
170             obj.refresh_list();
171         }
172     },
173
174     'init' : function( params ) {
175
176         try {
177             netscape.security.PrivilegeManager.enablePrivilege("UniversalXPConnect");
178             var obj = this;
179
180             obj.docid = params.docid;
181
182             JSAN.use('util.network'); obj.network = new util.network();
183             JSAN.use('OpenILS.data'); obj.data = new OpenILS.data(); obj.data.init({'via':'stash'});
184             JSAN.use('util.controller'); obj.controller = new util.controller();
185             obj.controller.init(
186                 {
187                     control_map : {
188                         'save_columns' : [ [ 'command' ], function() { obj.list.save_columns(); } ],
189                         'sel_clip' : [
190                             ['command'],
191                             function() { obj.list.clipboard(); }
192                         ],
193                         'cmd_broken' : [
194                             ['command'],
195                             function() { 
196                                 alert(document.getElementById('commonStrings').getString('common.unimplemented'));
197                             }
198                         ],
199                         'cmd_show_my_libs' : [
200                             ['command'],
201                             function() { 
202                                 obj.show_my_libs(); 
203                             }
204                         ],
205                         'cmd_show_all_libs' : [
206                             ['command'],
207                             function() {
208                                 obj.show_all_libs();
209                             }
210                         ],
211                         'cmd_show_libs_with_distributions' : [
212                             ['command'],
213                             function() {
214                                 obj.show_libs_with_distributions();
215                             }
216                         ],
217                         'cmd_clear' : [
218                             ['command'],
219                             function() {
220                                 obj.map_tree = {};
221                                 obj.list.clear();
222                             }
223                         ],
224                         'cmd_add_scap' : [
225                             ['command'],
226                             function() {
227                                 try {
228                                     var list = obj.ids_from_sel_list('ssub');
229                                     if (list.length == 0) list = obj.ids_from_sel_list('scap-group');
230                                     if (list.length == 0) return;
231
232                                     /*TODO: permission check?
233                                     //populate 'list' with owning_libs of subs, TODO
234                                     var edit = 0;
235                                     try {
236                                         edit = obj.network.request(
237                                             api.PERM_MULTI_ORG_CHECK.app,
238                                             api.PERM_MULTI_ORG_CHECK.method,
239                                             [ 
240                                                 ses(), 
241                                                 obj.data.list.au[0].id(), 
242                                                 list,
243                                                 [ 'CREATE_COPY' ]
244                                             ]
245                                         ).length == 0 ? 1 : 0;
246                                     } catch(E) {
247                                         obj.error.sdump('D_ERROR','batch permission check: ' + E);
248                                     }
249
250                                     if (edit==0) return; // no read-only view for this interface */
251                                     var new_scap = new scap();
252                                     new_scap.subscription(list[0]);//TODO: add multiple at once support?
253                                     new_scap.isnew(1);
254                                     var params = {};
255                                     params.scaps = [new_scap];
256                                     obj.editor_init('scap', 'add', params);
257                                 } catch(E) {
258                                     obj.error.standard_unexpected_error_alert(document.getElementById('serialStrings').getString('staff.serial.manage_subs.add.error'),E);
259                                 }
260                             }
261                         ],
262                         'cmd_add_siss' : [
263                             ['command'],
264                             function() {
265                                 try {
266                                     var list = obj.ids_from_sel_list('ssub');
267                                     if (list.length == 0) list = obj.ids_from_sel_list('siss-group');
268                                     if (list.length == 0) return;
269
270                                     /*TODO: permission check?
271                                     //populate 'list' with owning_libs of subs, TODO
272                                     var edit = 0;
273                                     try {
274                                         edit = obj.network.request(
275                                             api.PERM_MULTI_ORG_CHECK.app,
276                                             api.PERM_MULTI_ORG_CHECK.method,
277                                             [ 
278                                                 ses(), 
279                                                 obj.data.list.au[0].id(), 
280                                                 list,
281                                                 [ 'CREATE_COPY' ]
282                                             ]
283                                         ).length == 0 ? 1 : 0;
284                                     } catch(E) {
285                                         obj.error.sdump('D_ERROR','batch permission check: ' + E);
286                                     }
287
288                                     if (edit==0) return; // no read-only view for this interface */
289                                     var new_siss = new siss();
290                                     new_siss.subscription(list[0]);//TODO: add multiple at once support?
291                                     new_siss.isnew(1);
292                                     var params = {};
293                                     params.sisses = [new_siss];
294                                     obj.editor_init('siss', 'add', params);
295                                 } catch(E) {
296                                     obj.error.standard_unexpected_error_alert(document.getElementById('serialStrings').getString('staff.serial.manage_subs.add.error'),E);
297                                 }
298                             }
299                         ],
300                         'cmd_add_sdist' : [
301                             ['command'],
302                             function() {
303                                 try {
304                                     var list = obj.ids_from_sel_list('ssub');
305                                     if (list.length == 0) list = obj.ids_from_sel_list('sdist-group');
306                                     if (list.length == 0) return;
307
308                                     /*TODO: permission check?
309                                     //populate 'list' with owning_libs of subs, TODO
310                                     var edit = 0;
311                                     try {
312                                         edit = obj.network.request(
313                                             api.PERM_MULTI_ORG_CHECK.app,
314                                             api.PERM_MULTI_ORG_CHECK.method,
315                                             [ 
316                                                 ses(), 
317                                                 obj.data.list.au[0].id(), 
318                                                 list,
319                                                 [ 'CREATE_COPY' ]
320                                             ]
321                                         ).length == 0 ? 1 : 0;
322                                     } catch(E) {
323                                         obj.error.sdump('D_ERROR','batch permission check: ' + E);
324                                     }
325
326                                     if (edit==0) return; // no read-only view for this interface */
327                                     var new_sdist = new sdist();
328                                     new_sdist.subscription(list[0]);//TODO: add multiple at once support?
329                                     new_sdist.holding_lib(obj.map_ssub['ssub_' + list[0]].owning_lib());//default to sub owning lib
330                                     new_sdist.label($('serialStrings').getString('serial.common.default'));
331                                     new_sdist.isnew(1);
332                                     var params = {};
333                                     params.sdists = [new_sdist];
334                                     obj.editor_init('sdist', 'add', params);
335                                 } catch(E) {
336                                     obj.error.standard_unexpected_error_alert(document.getElementById('serialStrings').getString('staff.serial.manage_subs.add.error'),E);
337                                 }
338                             }
339                         ],
340                         'cmd_delete_scap' : [
341                             ['command'],
342                             function() {
343                                 var overridable_events = [
344                                     11001 // SERIAL_CAPTION_AND_PATTERN_HAS_ISSUANCES
345                                 ];
346                                 obj.do_delete('scap', 'open-ils.serial.caption_and_pattern.batch.update', overridable_events);
347                             }
348                         ],
349                         'cmd_delete_sdist' : [
350                             ['command'],
351                             function() {
352                                 var overridable_events = [ //TODO: proper overrides
353                                 ];
354                                 obj.do_delete('sdist', 'open-ils.serial.distribution.fleshed.batch.update', overridable_events);
355                             }
356                         ],
357                         'cmd_delete_siss' : [
358                             ['command'],
359                             function() {
360                                 var overridable_events = [ //TODO: proper overrides
361                                 ];
362                                 obj.do_delete('siss', 'open-ils.serial.issuance.fleshed.batch.update', overridable_events);
363                             }
364                         ],
365                         'cmd_delete_ssub' : [
366                             ['command'],
367                             function() {
368                                 var overridable_events = [
369                                     11000 // SERIAL_SUBSCRIPTION_NOT_EMPTY
370                                 ];
371                                 obj.do_delete('ssub', 'open-ils.serial.subscription.fleshed.batch.update', overridable_events);
372                             }
373                         ],
374                         /*dbw2 'cmd_delete_ssub' : [
375                             ['command'],
376                             function() {
377                                 try {
378                                     JSAN.use('util.functional');
379
380                                     var list = util.functional.filter_list(
381                                         obj.sel_list,
382                                         function (o) {
383                                             return o.split(/_/)[0] == 'ssub';
384                                         }
385                                     );
386
387                                     list = util.functional.map_list(
388                                         list,
389                                         function (o) {
390                                             return JSON2js( js2JSON( obj.map_ssub[ 'ssub_' + o.split(/_/)[1] ] ) );
391                                         }
392                                     );
393
394                                     var del_prompt;
395                                     if (list.length == 1) {
396                                         //TODO: correct prompts
397                                         del_prompt = document.getElementById('catStrings').getString('staff.cat.copy_browser.delete_volume.prompt');
398                                     } else {
399                                         del_prompt = document.getElementById('catStrings').getFormattedString('staff.cat.copy_browser.delete_volume.prompt.plural', [list.length]);
400                                     }
401
402                                     var r = obj.error.yns_alert(
403                                             del_prompt,
404                                             document.getElementById('catStrings').getString('staff.cat.copy_browser.delete_volume.title'),
405                                             document.getElementById('catStrings').getString('staff.cat.copy_browser.delete_volume.delete'),
406                                             document.getElementById('catStrings').getString('staff.cat.copy_browser.delete_volume.cancel'),
407                                             null,
408                                             document.getElementById('commonStrings').getString('common.confirm')
409                                     );
410
411                                     if (r == 0) {
412                                         for (var i = 0; i < list.length; i++) {
413                                             list[i].isdeleted('1');
414                                         }
415                                         var robj = obj.network.simple_request(
416                                             'FM_ACN_TREE_UPDATE', 
417                                             [ ses(), list, true ],
418                                             null,
419                                             {
420                                                 'title' : document.getElementById('catStrings').getString('staff.cat.copy_browser.delete_volume.override'),
421                                                 'overridable_events' : [
422                                                 ]
423                                             }
424                                         );
425                                         if (robj == null) throw(robj);
426                                         if (typeof robj.ilsevent != 'undefined') {
427                                             if (robj.ilsevent == 1206 ) { // VOLUME_NOT_EMPTY
428                                                 alert(document.getElementById('catStrings').getString('staff.cat.copy_browser.delete_volume.copies_remain'));
429                                                 return;
430                                             }
431                                             if (robj.ilsevent != 0) throw(robj);
432                                         }
433                                         alert(document.getElementById('catStrings').getString('staff.cat.copy_browser.delete_volume.success'));
434                                         obj.refresh_list();
435                                     }
436                                 } catch(E) {
437                                     obj.error.standard_unexpected_error_alert(document.getElementById('catStrings').getString('staff.cat.copy_browser.delete_volume.exception'),E);
438                                     obj.refresh_list();
439                                 }
440
441                             }
442                         ], dbw2*/
443                         'cmd_mark_library' : [
444                             ['command'],
445                             function() {
446                                 try {
447                                     var list = obj.ids_from_sel_list('aou');
448                                     if (list.length == 1) {
449                                         obj.data.marked_library = { 'lib' : list[0], 'docid' : obj.docid };
450                                         obj.data.stash('marked_library');
451                                         alert(document.getElementById('catStrings').getString('staff.cat.copy_browser.mark_library.alert'));
452                                     } else {
453                                         obj.error.yns_alert(
454                                                 document.getElementById('catStrings').getString('staff.cat.copy_browser.mark_library.prompt'),
455                                                 document.getElementById('catStrings').getString('staff.cat.copy_browser.mark_library.title'),
456                                                 document.getElementById('commonStrings').getString('common.ok'),
457                                                 null,
458                                                 null,
459                                                 document.getElementById('commonStrings').getString('common.confirm')
460                                                 );
461                                     }
462                                 } catch(E) {
463                                     obj.error.standard_unexpected_error_alert('manage_subs.js -> mark library',E);
464                                 }
465                             }
466                         ],
467
468                         'cmd_mark_subscription' : [
469                             ['command'],
470                             function() {
471                                 try {
472                                     var list = obj.ids_from_sel_list('ssub');
473                                     if (list.length == 1) {
474                                         obj.data.marked_subscription = list[0];
475                                         obj.data.stash('marked_subscription');
476                                         alert(document.getElementById('catStrings').getString('staff.cat.copy_browser.mark_volume.alert'));
477                                     } else {
478                                         obj.error.yns_alert(
479                                                 document.getElementById('catStrings').getString('staff.cat.copy_browser.mark_volume.prompt'),
480                                                 document.getElementById('catStrings').getString('staff.cat.copy_browser.mark_volume.title'),
481                                                 document.getElementById('commonStrings').getString('common.ok'),
482                                                 null,
483                                                 null,
484                                                 document.getElementById('commonStrings').getString('common.confirm')
485                                                 );
486                                     }
487                                 } catch(E) {
488                                     obj.error.standard_unexpected_error_alert('manage_subs.js -> mark subscription',E);
489                                 }
490                             }
491                         ],
492                         'cmd_add_subscriptions' : [
493                             ['command'],
494                             function() {
495                                 try {
496                                     var list = obj.ids_from_sel_list('aou');
497                                     if (list.length == 0) return;
498                                     //TODO: permission check?
499                                     /*var edit = 0;
500                                     try {
501                                         edit = obj.network.request(
502                                             api.PERM_MULTI_ORG_CHECK.app,
503                                             api.PERM_MULTI_ORG_CHECK.method,
504                                             [ 
505                                                 ses(), 
506                                                 obj.data.list.au[0].id(), 
507                                                 list,
508                                                 [ 'CREATE_VOLUME', 'CREATE_COPY' ]
509                                             ]
510                                         ).length == 0 ? 1 : 0;
511                                     } catch(E) {
512                                         obj.error.sdump('D_ERROR','batch permission check: ' + E);
513                                     }
514
515                                     if (edit==0) {
516                                         alert(document.getElementById('catStrings').getString('staff.cat.copy_browser.add_volume.permission_error'));
517                                         return; // no read-only view for this interface
518                                     } */
519                                     var new_ssub = new ssub();
520                                     new_ssub.owning_lib(list[0]);//TODO: add multiple at once support?
521                                     new_ssub.isnew(1);
522                                     new_ssub.record_entry(obj.docid);
523                                     var params = {};
524                                     params.ssubs = [new_ssub];
525                                     obj.editor_init('ssub', 'add', params);
526                                 } catch(E) {
527                                     obj.error.standard_unexpected_error_alert(document.getElementById('serialStrings').getString('staff.serial.manage_subs.add.error'),E);
528                                 }
529                             }
530                         ],
531                         'cmd_transfer_subscription' : [
532                             ['command'],
533                             function() {
534                                 try {
535                                     obj.data.stash_retrieve();
536                                     if (!obj.data.marked_library) {
537                                         alert(document.getElementById('catStrings').getString('staff.cat.copy_browser.transfer_volume.alert'));
538                                         return;
539                                     }
540                                     
541                                     var list = obj.ids_from_sel_list('ssub');
542
543                                     netscape.security.PrivilegeManager.enablePrivilege('UniversalXPConnect UniversalBrowserWrite');
544
545                                     JSAN.use('util.functional');
546
547                                     var ssub_list = util.functional.map_list(
548                                         list,
549                                         function (o) {
550                                             return obj.map_ssub[ 'ssub_' + o ].start_date();
551                                         }
552                                     ).join(document.getElementById('commonStrings').getString('common.grouping_string'));
553
554                                     var xml = '<vbox xmlns="http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul" flex="1" style="overflow: auto">';
555                                     xml += '<description>';
556                                     xml += document.getElementById('catStrings').getFormattedString('staff.cat.copy_browser.transfer.prompt', [ssub_list, obj.data.hash.aou[ obj.data.marked_library.lib ].shortname()]);
557                                     xml += '</description>';
558                                     xml += '<hbox><button label="' + document.getElementById('catStrings').getString('staff.cat.copy_browser.transfer.submit.label') + '" name="fancy_submit"/>';
559                                     xml += '<button label="' 
560                                         + document.getElementById('catStrings').getString('staff.cat.copy_browser.transfer.cancel.label') 
561                                         + '" accesskey="' 
562                                         + document.getElementById('catStrings').getString('staff.cat.copy_browser.transfer.cancel.accesskey') 
563                                         + '" name="fancy_cancel"/></hbox>';
564                                     xml += '<iframe style="overflow: scroll" flex="1" src="' + urls.XUL_BIB_BRIEF + '?docid=' + obj.data.marked_library.docid + '"/>';
565                                     xml += '</vbox>';
566                                     JSAN.use('OpenILS.data');
567                                     var data = new OpenILS.data(); data.init({'via':'stash'});
568                                     //data.temp_transfer = xml; data.stash('temp_transfer');
569                                     JSAN.use('util.window'); var win = new util.window();
570                                     var fancy_prompt_data = win.open(
571                                         urls.XUL_FANCY_PROMPT,
572                                         //+ '?xml_in_stash=temp_transfer'
573                                         //+ '&title=' + window.escape('Volume Transfer'),
574                                         'fancy_prompt', 'chrome,resizable,modal,width=500,height=300',
575                                         {
576                                             'xml' : xml,
577                                             'title' : document.getElementById('catStrings').getString('staff.cat.copy_browser.transfer.title')
578                                         }
579                                     );
580
581                                     if (fancy_prompt_data.fancy_status == 'incomplete') {
582                                         alert(document.getElementById('catStrings').getString('staff.cat.copy_browser.transfer.incomplete'));
583                                         return;
584                                     }
585
586                                     var robj = obj.network.simple_request(
587                                         'FM_ACN_TRANSFER', 
588                                         [ ses(), { 'docid' : obj.data.marked_library.docid, 'lib' : obj.data.marked_library.lib, 'subscriptions' : list } ],
589                                         null,
590                                         {
591                                             'title' : document.getElementById('catStrings').getString('staff.cat.copy_browser.transfer.override.failure'),
592                                             'overridable_events' : [
593                                                 1208, // TITLE_LAST_COPY
594                                                 1219, // COPY_REMOTE_CIRC_LIB
595                                             ],
596                                         }
597                                     );
598
599                                     if (typeof robj.ilsevent != 'undefined') {
600                                         if (robj.ilsevent == 1221) { // ORG_CANNOT_HAVE_VOLS
601                                             alert(document.getElementById('catStrings').getString('staff.cat.copy_browser.transfer.ineligible_destination'));
602                                         } else {
603                                             throw(robj);
604                                         }
605                                     } else {
606                                         alert(document.getElementById('catStrings').getString('staff.cat.copy_browser.transfer.success'));
607                                     }
608
609                                 } catch(E) {
610                                     obj.error.standard_unexpected_error_alert(document.getElementById('catStrings').getString('staff.cat.copy_browser.transfer.unexpected_error'),E);
611                                 }
612                                 obj.refresh_list();
613                             }
614                         ],
615
616                         'cmd_transfer_sdists' : [
617                             ['command'],
618                             function() {
619                                 try {
620                                     obj.data.stash_retrieve();
621                                     if (!obj.data.marked_subscription) {
622                                         alert(document.getElementById('catStrings').getString('staff.cat.copy_browser.transfer_items.missing_volume'));
623                                         return;
624                                     }
625                                     
626                                     JSAN.use('util.functional');
627
628                                     var list = obj.ids_from_sel_list('sdist');
629                                     var subscription = obj.network.simple_request('FM_ACN_RETRIEVE.authoritative',[ obj.data.marked_subscription ]);
630
631                                     JSAN.use('cat.util'); cat.util.transfer_copies( { 
632                                         'distribution_ids' : list, 
633                                         'docid' : subscription.record(),
634                                         'subscription_label' : subscription.start_date(),
635                                         'owning_lib' : subscription.owning_lib(),
636                                     } );
637
638                                 } catch(E) {
639                                     obj.error.standard_unexpected_error_alert(document.getElementById('catStrings').getString('staff.cat.copy_browser.transfer_items.unexpected_error'),E);
640                                 }
641                                 obj.refresh_list();
642                             }
643                         ],
644                         'cmd_refresh_list' : [
645                             ['command'],
646                             function() {
647                                 obj.refresh_list();
648                             }
649                         ],
650                         'cmd_make_predictions' : [
651                             ['command'],
652                             function() {
653                                 try {
654                                     var list = obj.ids_from_sel_list('ssub');
655                                     if (list.length == 0) {
656                                         alert($('serialStrings').getString('serial.manage_subs.predict.alert')); //TODO: better error
657                                         return;
658                                     }
659
660                                     var num_to_predict = prompt($('serialStrings').getString('serial.manage_subs.predict.prompt'),
661                                             '12',
662                                             $('serialStrings').getString('serial.manage_subs.predict.prompt.text'));
663                                     num_to_predict = String( num_to_predict ).replace(/\D/g,'');
664                                     if (num_to_predict == '') {
665                                         alert($('serialStrings').getString('serial.manage_subs.invalid_number')); //TODO: better error
666                                         return;
667                                     }
668
669                                     for (i = 0; i < list.length; i++) {
670                                         var robj = obj.network.request(
671                                                 'open-ils.serial',
672                                                 'open-ils.serial.make_predictions',
673                                                 [ ses(), {"ssub_id":list[i], "num_to_predict":num_to_predict}]
674                                         );
675                                         alert($('serialStrings').getFormattedString('serial.manage_subs.predict_success', [robj.length, list[i]]));
676                                     }
677
678                                     obj.refresh_list();
679
680                                 } catch(E) {
681                                     obj.error.standard_unexpected_error_alert('cmd_make_predictions failed!',E);
682                                 }
683                             }
684                         ],
685 /*dbw2                      'sel_distribution_details' : [
686                             ['command'],
687                             function() {
688                                 JSAN.use('util.functional');
689
690                                 var list = util.functional.filter_list(
691                                     obj.sel_list,
692                                     function (o) {
693                                         return o.split(/_/)[0] == 'sdist';
694                                     }
695                                 );
696
697                                 list = util.functional.map_list(
698                                     list,
699                                     function (o) {
700                                         return o.split(/_/)[1];
701                                     }
702                                 );
703     
704                                 JSAN.use('circ.util');
705                                 for (var i = 0; i < list.length; i++) {
706                                     circ.util.show_copy_details( list[i] );
707                                 }
708                             }
709                         ],
710                         'cmd_edit_sdists' : [
711                             ['command'],
712                             function() {
713                                 try {
714                                     JSAN.use('util.functional');
715
716                                     var list = util.functional.filter_list(
717                                         obj.sel_list,
718                                         function (o) {
719                                             return o.split(/_/)[0] == 'sdist';
720                                         }
721                                     );
722
723                                     list = util.functional.map_list(
724                                         list,
725                                         function (o) {
726                                             return o.split(/_/)[1];
727                                         }
728                                     );
729
730                                     JSAN.use('cat.util'); cat.util.spawn_copy_editor( { 'copy_ids' : list, 'edit' : 1 } );
731                                     obj.refresh_list();
732
733                                 } catch(E) {
734                                     obj.error.standard_unexpected_error_alert(document.getElementById('catStrings').getString('staff.cat.copy_browser.edit_items.error'),E);
735                                 }
736                             }
737                         ], dbw2*/
738
739 /*dbw2                      'cmd_print_spine_labels' : [
740                             ['command'],
741                             function() {
742                                 try {
743                                     JSAN.use('util.functional');
744                                     
745                                     var list = util.functional.filter_list(
746                                         obj.sel_list,
747                                         function (o) {
748                                             return o.split(/_/)[0] == 'sdist';
749                                         }
750                                     );
751
752                                     list = util.functional.map_list(
753                                         list,
754                                         function (o) {
755                                             return obj.map_sdist[ o ];
756                                         }
757                                     );
758
759                                     obj.data.temp_barcodes_for_labels = util.functional.map_list( list, function(o){return o.barcode();}) ; 
760                                     obj.data.stash('temp_barcodes_for_labels');
761                                     xulG.new_tab(
762                                         xulG.url_prefix( urls.XUL_SPINE_LABEL ),
763                                         { 'tab_name' : document.getElementById('catStrings').getString('staff.cat.copy_browser.print_spine.tab') },
764                                         {}
765                                     );
766                                 } catch(E) {
767                                     obj.error.standard_unexpected_error_alert(document.getElementById('catStrings').getString('staff.cat.copy_browser.print_spine.error'),E);
768                                 }
769                             }
770                         ],
771                         'cmd_edit_subscriptions' : [
772                             ['command'],
773                             function() {
774                                 try {
775                                     JSAN.use('util.functional');
776                                     var list = util.functional.map_list(
777                                         util.functional.filter_list(
778                                             obj.sel_list,
779                                             function (o) {
780                                                 return o.split(/_/)[0] == 'ssub';
781                                             }
782                                         ),
783                                         function (o) {
784                                             return o.split(/_/)[1];
785                                         }
786                                     );
787                                     if (list.length == 0) return;
788
789                                     var edit = 0;
790                                     try {
791                                         edit = obj.network.request(
792                                             api.PERM_MULTI_ORG_CHECK.app,
793                                             api.PERM_MULTI_ORG_CHECK.method,
794                                             [ 
795                                                 ses(), 
796                                                 obj.data.list.au[0].id(), 
797                                                 util.functional.map_list(
798                                                     list,
799                                                     function (o) {
800                                                         return obj.map_ssub[ 'ssub_' + o ].owning_lib();
801                                                     }
802                                                 ),
803                                                 [ 'UPDATE_VOLUME' ]
804                                             ]
805                                         ).length == 0 ? 1 : 0;
806                                     } catch(E) {
807                                         obj.error.sdump('D_ERROR','batch permission check: ' + E);
808                                     }
809
810                                     if (edit==0) {
811                                         alert(document.getElementById('catStrings').getString('staff.cat.copy_browser.edit_volume.permission_error'));
812                                         return; // no read-only view for this interface
813                                     }
814
815                                     list = util.functional.map_list(
816                                         list,
817                                         function (o) {
818                                             var my_ssub = obj.map_ssub['ssub_' + o];
819                                             return function(r){return r;}(my_ssub);
820                                         }
821                                     );
822
823                                     var title;
824                                     if (list.length == 1) {
825                                         title = document.getElementById('catStrings').getString('staff.cat.copy_browser.edit_volume.title');
826                                     } else {
827                                         title = document.getElementById('catStrings').getString('staff.cat.copy_browser.edit_volume.title.plural');
828                                     }
829
830                                     JSAN.use('util.window'); var win = new util.window();
831                                     //obj.data.volumes_temp = js2JSON( list );
832                                     //obj.data.stash('volumes_temp');
833                                     var my_xulG = win.open(
834                                         window.xulG.url_prefix(urls.XUL_VOLUME_EDITOR),
835                                         title,
836                                         'chrome,modal,resizable',
837                                         { 'subscriptions' : JSON2js(js2JSON(list)) }
838                                     );
839
840                                     // FIXME -- need to unique the temp space, and not rely on modalness of window
841                                     //obj.data.stash_retrieve();
842                                     if (typeof my_xulG.update_these_subscriptions == 'undefined') { return; }
843                                     var subscriptions = my_xulG.subscriptions;
844                                     if (!subscriptions) return;
845                                 
846                                     subscriptions = util.functional.filter_list(
847                                         subscriptions,
848                                         function (o) {
849                                             return o.ischanged() == '1';
850                                         }
851                                     );
852
853                                     subscriptions = util.functional.map_list(
854                                         subscriptions,
855                                         function (o) {
856                                             o.record( obj.docid ); // staff client 2 did not do this.  Does it matter?
857                                             return o;
858                                         }
859                                     );
860
861                                     if (subscriptions.length == 0) return;
862
863                                     try {
864                                         var r = obj.network.request(
865                                             api.FM_ACN_TREE_UPDATE.app,
866                                             api.FM_ACN_TREE_UPDATE.method,
867                                             [ ses(), subscriptions, true ]
868                                         );
869                                         if (typeof r.ilsevent != 'undefined') {
870                                             switch(Number(r.ilsevent)) {
871                                                 case 1705 : // VOLUME_LABEL_EXISTS
872                                                     alert(document.getElementById('catStrings').getString('staff.cat.copy_browser.edit_volume.failed'));
873                                                     break;
874                                                 default: throw(r);
875                                             }
876                                         } else {
877                                             alert(document.getElementById('catStrings').getString('staff.cat.copy_browser.edit_volume.success'));
878                                         }
879                                     } catch(E) {
880                                         obj.error.standard_unexpected_error_alert(document.getElementById('catStrings').getString('staff.cat.copy_browser.edit_volume.error'),E);
881                                     }
882                                     obj.refresh_list();
883
884                                 } catch(E) {
885                                     obj.error.standard_unexpected_error_alert(document.getElementById('catStrings').getString('staff.cat.copy_browser.edit_volume.exception'),E);
886                                 }
887                             }
888                         ], dbw2*/
889                     }
890                 }
891             );
892
893             obj.list_init(params);
894
895             obj.org_ids = obj.network.simple_request('FM_SSUB_AOU_IDS_RETRIEVE_VIA_RECORD_ID.authoritative',[ obj.docid ]);
896             if (typeof obj.org_ids.ilsevent != 'undefined') throw(obj.org_ids);
897             JSAN.use('util.functional'); 
898             obj.org_ids = util.functional.map_list( obj.org_ids, function (o) { return Number(o); });
899
900             var org = obj.data.hash.aou[ obj.data.list.au[0].ws_ou() ];
901             //obj.show_libs( org );
902
903             //obj.show_my_libs();
904
905             JSAN.use('util.file'); JSAN.use('util.widgets');
906
907             var file; var list_data; var ml; 
908
909             file = new util.file('offline_ou_list'); 
910             if (file._file.exists()) {
911                 list_data = file.get_object(); file.close();
912                 ml = util.widgets.make_menulist( list_data[0], list_data[1] );
913                 ml.setAttribute('id','lib_menu'); document.getElementById('serial_sub_lib_menu').appendChild(ml);
914                 //TODO: class this menu properly
915                 for (var i = 0; i < obj.org_ids.length; i++) {
916                     ml.getElementsByAttribute('value',obj.org_ids[i])[0].setAttribute('class','has_distributions');
917                 }
918                 ml.firstChild.addEventListener(
919                     'popupshown',
920                     function(ev) {
921                         document.getElementById('legend').setAttribute('hidden','false');
922                     },
923                     false
924                 );
925                 ml.firstChild.addEventListener(
926                     'popuphidden',
927                     function(ev) {
928                         document.getElementById('legend').setAttribute('hidden','true');
929                     },
930                     false
931                 );
932                 ml.addEventListener(
933                     'command',
934                     function(ev) {
935                         if (document.getElementById('refresh_button')) document.getElementById('refresh_button').focus(); 
936                         JSAN.use('util.file'); var file = new util.file('manage_subs_prefs.'+obj.data.server_unadorned);
937                         util.widgets.save_attributes(file, { 'lib_menu' : [ 'value' ], 'show_ssubs' : [ 'checked' ], 'show_ssub_groups' : [ 'checked' ] });
938                         obj.refresh_list();
939                     },
940                     false
941                 );
942             } else {
943                 throw(document.getElementById('catStrings').getString('staff.cat.copy_browser.missing_library') + '\n');
944             }
945
946             file = new util.file('manage_subs_prefs.'+obj.data.server_unadorned);
947             util.widgets.load_attributes(file);
948             ml.value = ml.getAttribute('value');
949             if (! ml.value) {
950                 ml.value = org.id();
951                 ml.setAttribute('value',ml.value);
952             }
953
954             document.getElementById('show_ssubs').addEventListener(
955                 'command',
956                 function(ev) {
957                     JSAN.use('util.file'); var file = new util.file('manage_subs_prefs.'+obj.data.server_unadorned);
958                     util.widgets.save_attributes(file, { 'lib_menu' : [ 'value' ], 'show_ssubs' : [ 'checked' ], 'show_ssub_groups' : [ 'checked' ] });
959                 },
960                 false
961             );
962
963             document.getElementById('show_ssub_groups').addEventListener(
964                 'command',
965                 function(ev) {
966                     JSAN.use('util.file'); var file = new util.file('manage_subs_prefs.'+obj.data.server_unadorned);
967                     util.widgets.save_attributes(file, { 'lib_menu' : [ 'value' ], 'show_ssubs' : [ 'checked' ], 'show_ssub_groups' : [ 'checked' ] });
968                 },
969                 false
970             );
971
972             obj.show_my_libs( ml.value );
973
974             JSAN.use('util.exec'); var exec = new util.exec(20); exec.timer(obj.funcs,100);
975
976             obj.toggle_actions(); // disable menus initially
977
978         } catch(E) {
979             this.error.standard_unexpected_error_alert('serial/manage_subs.init: ',E);
980         }
981     },
982
983     'show_my_libs' : function(org) {
984         var obj = this;
985         try {
986             if (!org) {
987                 org = obj.data.hash.aou[ obj.data.list.au[0].ws_ou() ];
988             } else {
989                 if (typeof org != 'object') org = obj.data.hash.aou[ org ];
990             }
991             obj.show_libs( org, false );
992         
993             var p_org = obj.data.hash.aou[ org.parent_ou() ];
994             if (p_org) {
995                 obj.funcs.push( function() { 
996                     document.getElementById('cmd_refresh_list').setAttribute('disabled','true'); 
997                     document.getElementById('cmd_show_libs_with_distributions').setAttribute('disabled','true'); 
998                     document.getElementById('lib_menu').setAttribute('disabled','true'); 
999                 } );
1000                 for (var i = 0; i < p_org.children().length; i++) {
1001                     obj.funcs.push(
1002                         function(o) {
1003                             return function() {
1004                                 obj.show_libs( o, false );
1005                             }
1006                         }( p_org.children()[i] )
1007                     );
1008                 }
1009                 obj.funcs.push( function() { 
1010                     document.getElementById('cmd_refresh_list').setAttribute('disabled','false'); 
1011                     document.getElementById('cmd_show_libs_with_distributions').setAttribute('disabled','false'); 
1012                     document.getElementById('lib_menu').setAttribute('disabled','false'); 
1013                 } );
1014             }
1015         } catch(E) {
1016             alert(E);
1017         }
1018     },
1019
1020     'show_all_libs' : function() {
1021         var obj = this;
1022         try {
1023             obj.show_my_libs();
1024
1025             obj.show_libs( obj.data.tree.aou );
1026
1027             obj.funcs.push( function() { 
1028                 document.getElementById('cmd_refresh_list').setAttribute('disabled','true'); 
1029                 document.getElementById('cmd_show_libs_with_distributions').setAttribute('disabled','true'); 
1030                 document.getElementById('lib_menu').setAttribute('disabled','true'); 
1031             } );
1032
1033             for (var i = 0; i < obj.data.tree.aou.children().length; i++) {
1034                 obj.funcs.push(
1035                     function(o) {
1036                         return function() {
1037                             obj.show_libs( o );
1038                         }
1039                     }( obj.data.tree.aou.children()[i] )
1040                 );
1041             }
1042             obj.funcs.push( function() { 
1043                 document.getElementById('cmd_refresh_list').setAttribute('disabled','false'); 
1044                 document.getElementById('cmd_show_libs_with_distributions').setAttribute('disabled','false'); 
1045                 document.getElementById('lib_menu').setAttribute('disabled','false'); 
1046             } );
1047
1048         } catch(E) {
1049             alert(E);
1050         }
1051     },
1052
1053     'show_libs_with_distributions' : function() {
1054         var obj = this;
1055         try {
1056             JSAN.use('util.functional');
1057
1058             var orgs = util.functional.map_list(
1059                 obj.org_ids,
1060                 function(id) { return obj.data.hash.aou[id]; }
1061             ).sort(
1062                 function( a, b ) {
1063                     if (a.shortname() < b.shortname()) return -1;
1064                     if (a.shortname() > b.shortname()) return 1;
1065                     return 0;
1066                 }
1067             );
1068             obj.funcs.push( function() { 
1069                 document.getElementById('cmd_refresh_list').setAttribute('disabled','true'); 
1070                 document.getElementById('cmd_show_libs_with_distributions').setAttribute('disabled','true'); 
1071                 document.getElementById('lib_menu').setAttribute('disabled','true'); 
1072             } );
1073
1074             for (var i = 0; i < orgs.length; i++) {
1075                 obj.funcs.push(
1076                     function(o) {
1077                         return function() {
1078                             obj.show_libs(o,false);
1079                         }
1080                     }( orgs[i] )
1081                 );
1082             }
1083             obj.funcs.push( function() { 
1084                 document.getElementById('cmd_refresh_list').setAttribute('disabled','false'); 
1085                 document.getElementById('cmd_show_libs_with_distributions').setAttribute('disabled','false'); 
1086                 document.getElementById('lib_menu').setAttribute('disabled','false'); 
1087             } );
1088
1089         } catch(E) {
1090             alert(E);
1091         }
1092     },
1093
1094     'show_libs' : function(start_aou,show_open) {
1095         var obj = this;
1096         try {
1097             if (!start_aou) throw('show_libs: Need a start_aou');
1098             JSAN.use('OpenILS.data'); obj.data = new OpenILS.data(); obj.data.init({'via':'stash'});
1099             JSAN.use('util.functional'); 
1100
1101             var parents = [];
1102             var temp_aou = start_aou;
1103             while ( temp_aou.parent_ou() ) {
1104                 temp_aou = obj.data.hash.aou[ temp_aou.parent_ou() ];
1105                 parents.push( temp_aou );
1106             }
1107             parents.reverse();
1108
1109             for (var i = 0; i < parents.length; i++) {
1110                 obj.funcs.push(
1111                     function(o,p) {
1112                         return function() { 
1113                             obj.append_org(o,p,{'container':'true','open':'true'}); 
1114                         };
1115                     }(parents[i], obj.data.hash.aou[ parents[i].parent_ou() ])
1116                 );
1117             }
1118
1119             obj.funcs.push(
1120                 function(o,p) {
1121                     return function() { obj.append_org(o,p); };
1122                 }(start_aou,obj.data.hash.aou[ start_aou.parent_ou() ])
1123             );
1124
1125             obj.funcs.push(
1126                 function() {
1127                     if (start_aou.children()) {
1128                         var x = obj.map_tree[ 'aou_' + start_aou.id() ];
1129                         x.setAttribute('container','true');
1130                         if (show_open) x.setAttribute('open','true');
1131                         for (var i = 0; i < start_aou.children().length; i++) {
1132                             obj.funcs.push(
1133                                 function(o,p) {
1134                                     return function() { obj.append_org(o,p); };
1135                                 }( start_aou.children()[i], start_aou )
1136                             );
1137                         }
1138                     }
1139                 }
1140             );
1141
1142         } catch(E) {
1143             alert(E);
1144         }
1145     },
1146
1147     'on_select' : function(list,twisty) {
1148         var obj = this;
1149         var sel_lists = {};
1150
1151         for (var i = 0; i < list.length; i++) {
1152             var row_type = list[i].split('_')[0];
1153             var id = list[i].split('_')[1];
1154
1155             if (!sel_lists[row_type]) sel_lists[row_type] = [];
1156             sel_lists[row_type].push(id);
1157
1158             switch(row_type) {
1159                 case 'aou' : obj.on_click_aou(id,twisty); break;
1160                 case 'ssub' : obj.on_select_ssub(id,twisty); break;
1161                 default: break;
1162             }
1163         }
1164
1165         if (!obj.focused_node_retrieve_id) return;
1166
1167         var row_type = obj.focused_node_retrieve_id.split('_')[0];
1168         var id = obj.focused_node_retrieve_id.split('_')[1];
1169
1170         if (sel_lists[row_type]) { // the type focused is in the selection (usually the case)
1171             switch(row_type) {
1172                 case 'aou' : obj.on_click_aou(id,twisty); break;
1173                 default: if (obj['on_click_' + row_type]) obj['on_click_' + row_type](sel_lists[row_type],twisty);
1174             }
1175         }
1176     },
1177
1178     'on_select_ssub' : function(ssub_id,twisty) {
1179         var obj = this;
1180         try {
1181             //typo? var ssub_tree = obj.map_sdist[ 'ssub_' + ssub_id ];
1182             var ssub_tree = obj.map_ssub[ 'ssub_' + ssub_id ];
1183             obj.funcs.push( function() { 
1184                 document.getElementById('cmd_refresh_list').setAttribute('disabled','true'); 
1185                 document.getElementById('cmd_show_libs_with_distributions').setAttribute('disabled','true'); 
1186                 document.getElementById('lib_menu').setAttribute('disabled','true'); 
1187             } );
1188             if (ssub_tree.distributions()) {
1189                 for (var i = 0; i < ssub_tree.distributions().length; i++) {
1190                     obj.funcs.push(
1191                         function(c,a) {
1192                             return function() {
1193                                 obj.append_member(c,a,[],'sdist');
1194                             }
1195                         }( ssub_tree.distributions()[i], ssub_tree )
1196                     )
1197                 }
1198             }
1199             if (ssub_tree.issuances()) {
1200                 for (var i = 0; i < ssub_tree.issuances().length; i++) {
1201                     obj.funcs.push(
1202                         function(c,a) {
1203                             return function() {
1204                                 obj.append_member(c,a,[],'siss');
1205                             }
1206                         }( ssub_tree.issuances()[i], ssub_tree )
1207                     )
1208                 }
1209             }
1210             if (ssub_tree.scaps()) {
1211                 for (var i = 0; i < ssub_tree.scaps().length; i++) {
1212                     obj.funcs.push(
1213                         function(c,a) {
1214                             return function() {
1215                                 obj.append_member(c,a,[],'scap');
1216                             }
1217                         }( ssub_tree.scaps()[i], ssub_tree )
1218                     )
1219                 }
1220             }
1221             obj.funcs.push( function() { 
1222                 document.getElementById('cmd_refresh_list').setAttribute('disabled','false'); 
1223                 document.getElementById('cmd_show_libs_with_distributions').setAttribute('disabled','false'); 
1224                 document.getElementById('lib_menu').setAttribute('disabled','false'); 
1225             } );
1226         } catch(E) {
1227             alert(E);
1228         }
1229     },
1230
1231     'on_click_ssub' : function(ssub_ids,twisty) {
1232         var obj = this;
1233         try {
1234             // draw sdist editor
1235             if (typeof twisty == 'undefined') {
1236                 var params = {};
1237                 params.ssub_ids = ssub_ids;
1238                 obj.editor_init('ssub', 'edit', params);
1239             }
1240         } catch(E) {
1241             alert(E);
1242         }
1243     },
1244
1245     'on_click_sdist' : function(sdist_ids,twisty) {
1246         var obj = this;
1247         try {
1248             // draw sdist editor
1249             if (typeof twisty == 'undefined') {
1250                 var params = {};
1251                 params.sdist_ids = sdist_ids;
1252                 obj.editor_init('sdist', 'edit', params);
1253             }
1254         } catch(E) {
1255             alert(E);
1256         }
1257     },
1258
1259     'on_click_siss' : function(siss_ids,twisty) {
1260         var obj = this;
1261         try {
1262             // draw siss editor
1263             if (typeof twisty == 'undefined') {
1264                 var params = {};
1265                 params.siss_ids = siss_ids;
1266                 obj.editor_init('siss', 'edit', params);
1267             }
1268         } catch(E) {
1269             alert(E);
1270         }
1271     },
1272
1273     'on_click_scap' : function(scap_ids,twisty) {
1274         var obj = this;
1275         try {
1276             // draw scap editor
1277             if (typeof twisty == 'undefined') {
1278                 var params = {};
1279                 params.scap_ids = scap_ids;
1280                 obj.editor_init('scap', 'edit', params);
1281             }
1282         } catch(E) {
1283             alert(E);
1284         }
1285     },
1286
1287     'on_click_aou' : function(org_id,twisty) {
1288         var obj = this;
1289         var org = obj.data.hash.aou[ org_id ];
1290         obj.funcs.push( function() { 
1291             document.getElementById('cmd_refresh_list').setAttribute('disabled','true'); 
1292             document.getElementById('cmd_show_libs_with_distributions').setAttribute('disabled','true'); 
1293             document.getElementById('lib_menu').setAttribute('disabled','true'); 
1294         } );
1295         if (org.children()) {
1296             for (var i = 0; i < org.children().length; i++) {
1297                 obj.funcs.push(
1298                     function(o,p) {
1299                         return function() {
1300                             obj.append_org(o,p)
1301                         }
1302                     }(org.children()[i],org)
1303                 );
1304             }
1305         } 
1306         if (obj.map_ssub[ 'aou_' + org_id ]) {
1307             for (var i = 0; i < obj.map_ssub[ 'aou_' + org_id ].length; i++) {
1308                 obj.funcs.push(
1309                     function(o,a) {
1310                         return function() {
1311                             obj.append_ssub(o,a);
1312                         }
1313                     }( org, obj.map_ssub[ 'aou_' + org_id ][i] )
1314                 );
1315             }
1316         }
1317         obj.funcs.push( function() { 
1318             document.getElementById('cmd_refresh_list').setAttribute('disabled','false'); 
1319             document.getElementById('cmd_show_libs_with_distributions').setAttribute('disabled','false'); 
1320             document.getElementById('lib_menu').setAttribute('disabled','false'); 
1321         } );
1322
1323         // remove current editor
1324         if (typeof twisty == 'undefined') {
1325             document.getElementById('serial_manage_subs_editor_deck').selectedIndex = 0;
1326         }
1327     },
1328
1329     'append_org' : function (org,parent_org,params) {
1330         var obj = this;
1331         try {
1332             if (obj.map_tree[ 'aou_' + org.id() ]) {
1333                 var x = obj.map_tree[ 'aou_' + org.id() ];
1334                 if (params) {
1335                     for (var i in params) {
1336                         x.setAttribute(i,params[i]);
1337                     }
1338                 }
1339                 return x;
1340             }
1341
1342             var data = {
1343                 'row' : {
1344                     'my' : {
1345                         'aou' : org,
1346                     }
1347                 },
1348                 'skip_all_columns_except' : [0,1,2],
1349                 'retrieve_id' : 'aou_' + org.id(),
1350                 'to_bottom' : true,
1351                 'no_auto_select' : true,
1352             };
1353         
1354             var ssub_tree_list;
1355             if ( obj.org_ids.indexOf( Number( org.id() ) ) == -1 ) {
1356                 if ( get_bool( obj.data.hash.aout[ org.ou_type() ].can_have_vols() ) ) {
1357                     data.row.my.subscription_count = '0';
1358                     //data.row.my.distribution_count = '<0>';
1359                 } else {
1360                     data.row.my.subscription_count = '';
1361                     //data.row.my.distribution_count = '';
1362                 }
1363             } else {
1364                 var v_count = 0; var d_count = 0;
1365                 ssub_tree_list = obj.network.simple_request(
1366                     'FM_SSUB_TREE_LIST_RETRIEVE_VIA_RECORD_ID_AND_ORG_IDS.authoritative',
1367                     [ ses(), obj.docid, [ org.id() ] ]
1368                 );
1369                 for (var i = 0; i < ssub_tree_list.length; i++) {
1370                     v_count++;
1371                     obj.map_ssub[ 'ssub_' + ssub_tree_list[i].id() ] = function(r){return r;}(ssub_tree_list[i]);
1372                     var distributions = ssub_tree_list[i].distributions();
1373                     //if (distributions) d_count += distributions.length;
1374                     for (var j = 0; j < distributions.length; j++) {
1375                         obj.map_sdist[ 'sdist_' + distributions[j].id() ] = function(r){return r;}(distributions[j]);
1376                     }
1377                     var issuances = ssub_tree_list[i].issuances();
1378                     for (var j = 0; j < issuances.length; j++) {
1379                         obj.map_siss[ 'siss_' + issuances[j].id() ] = function(r){return r;}(issuances[j]);
1380                     }
1381                     var scaps = ssub_tree_list[i].scaps();
1382                     for (var j = 0; j < scaps.length; j++) {
1383                         obj.map_scap[ 'scap_' + scaps[j].id() ] = function(r){return r;}(scaps[j]);
1384                     }
1385                 }
1386                 data.row.my.subscription_count = v_count;
1387                 //data.row.my.distribution_count = '<' + d_count + '>';
1388             }
1389             if (parent_org) {
1390                 data.node = obj.map_tree[ 'aou_' + parent_org.id() ];
1391             }
1392             var nparams = obj.list.append(data);
1393             var node = nparams.treeitem_node;
1394             if (params) {
1395                 for (var i in params) {
1396                     node.setAttribute(i,params[i]);
1397                 }
1398             }
1399             obj.map_tree[ 'aou_' + org.id() ] = node;
1400
1401             if (org.children()) {
1402                 node.setAttribute('container','true');
1403             }
1404
1405             if (parent_org) {
1406                 if ( obj.data.hash.aou[ obj.data.list.au[0].ws_ou() ].parent_ou() == parent_org.id() ) {
1407                     data.node.setAttribute('open','true');
1408                 }
1409             } else {
1410                 obj.map_tree[ 'aou_' + org.id() ].setAttribute('open','true');
1411             }
1412
1413             if (ssub_tree_list) {
1414                 obj.map_ssub[ 'aou_' + org.id() ] = ssub_tree_list;
1415                 node.setAttribute('container','true');
1416             }
1417
1418             if (document.getElementById('show_ssubs').checked) {
1419                 obj.funcs.push( function() { obj.on_click_aou( org.id() ); } );
1420                 node.setAttribute('open','true');
1421             }
1422
1423         } catch(E) {
1424             dump(E+'\n');
1425             alert(E);
1426         }
1427     },
1428
1429     'append_ssub' : function( org, ssub_tree, params ) {
1430         var obj = this;
1431         try {
1432             if (obj.map_tree[ 'ssub_' + ssub_tree.id() ]) {
1433                 var x = obj.map_tree[ 'ssub_' + ssub_tree.id() ];
1434                 if (params) {
1435                     for (var i in params) {
1436                         x.setAttribute(i,params[i]);
1437                     }
1438                 }
1439                 return x;
1440             }
1441
1442             var parent_node = obj.map_tree[ 'aou_' + org.id() ];
1443             var data = {
1444                 'row' : {
1445                     'my' : {
1446                         'aou' : org,
1447                         'ssub' : ssub_tree,
1448                         'subscription_count' : '',
1449                         //'distribution_count' : ssub_tree.distributions() ? ssub_tree.distributions().length : '0',
1450                     }
1451                 },
1452                 'skip_all_columns_except' : [0,1,2],
1453                 'retrieve_id' : 'ssub_' + ssub_tree.id(),
1454                 'node' : parent_node,
1455                 'to_bottom' : true,
1456                 'no_auto_select' : true,
1457             };
1458             var nparams = obj.list.append(data);
1459             var node = nparams.treeitem_node;
1460             obj.map_tree[ 'ssub_' + ssub_tree.id() ] =  node;
1461             if (params) {
1462                 for (var i in params) {
1463                     node.setAttribute(i,params[i]);
1464                 }
1465             }
1466             if (ssub_tree.distributions() || ssub_tree.scaps() || ssub_tree.issuances()) {
1467                 //did this support a later typo? obj.map_sdist[ 'ssub_' + ssub_tree.id() ] = ssub_tree;
1468                 node.setAttribute('container','true');
1469             }
1470             if (document.getElementById('show_ssub_groups').checked) {
1471                 node.setAttribute('open','true');
1472                 obj.funcs.push( function() { obj.on_select_ssub( ssub_tree.id(), true ); } );
1473             }
1474             var sdist_group_node_data = {
1475                 'row' : {
1476                     'my' : {
1477                         'label' : $('serialStrings').getString('serial.manage_subs.distributions'),
1478                     }
1479                 },
1480                 'retrieve_id' : 'sdist-group_' + ssub_tree.id(),
1481                 'node' : node,
1482                 'to_bottom' : true,
1483                 'no_auto_select' : true,
1484             };
1485             nparams = obj.list.append(sdist_group_node_data);
1486             obj.map_tree[ 'ssub_sdist_group_' + ssub_tree.id() ] =  nparams.treeitem_node;
1487
1488             var siss_group_node_data = {
1489                 'row' : {
1490                     'my' : {
1491                         'label' : $('serialStrings').getString('serial.manage_subs.issuances'),
1492                     }
1493                 },
1494                 'retrieve_id' : 'siss-group_' + ssub_tree.id(),
1495                 'node' : node,
1496                 'to_bottom' : true,
1497                 'no_auto_select' : true,
1498             };
1499             nparams = obj.list.append(siss_group_node_data);
1500             obj.map_tree[ 'ssub_siss_group_' + ssub_tree.id() ] =  nparams.treeitem_node;
1501
1502             var scap_group_node_data = {
1503                 'row' : {
1504                     'my' : {
1505                         'label' : $('serialStrings').getString('serial.manage_subs.captions_patterns'),
1506                     }
1507                 },
1508                 'retrieve_id' : 'scap-group_' + ssub_tree.id(),
1509                 'node' : node,
1510                 'to_bottom' : true,
1511                 'no_auto_select' : true,
1512             };
1513             nparams = obj.list.append(scap_group_node_data);
1514             obj.map_tree[ 'ssub_scap_group_' + ssub_tree.id() ] =  nparams.treeitem_node;
1515         } catch(E) {
1516             dump(E+'\n');
1517             alert(E);
1518         }
1519     },
1520
1521     'append_member' : function( item, ssub_tree, attributes, type ) {
1522         var obj = this;
1523         try {
1524             if (obj.map_tree[ type + '_' + item.id() ]) {
1525                 var x = obj.map_tree[ type + '_' + item.id() ];
1526                 if (attributes) {
1527                     for (var i in attributes) {
1528                         x.setAttribute(i,attributes[i]);
1529                     }
1530                 }
1531                 return x;
1532             }
1533
1534             var parent_node = obj.map_tree[ 'ssub_' + type + '_group_' + ssub_tree.id() ];
1535             var data = {
1536                 'row' : {
1537                     'my' : {
1538                         'aou' : obj.data.hash.aou[ ssub_tree.owning_lib() ],
1539                         'ssub' : ssub_tree,
1540                         'subscription_count' : '',
1541                         //'distribution_count' : '',
1542                     }
1543                 },
1544                 'retrieve_id' : type + '_' + item.id(),
1545                 'node' : parent_node,
1546                 'to_bottom' : true,
1547                 'no_auto_select' : true,
1548             };
1549             data['row']['my'][type] = item; // TODO: future optimization: get only the IDs of these leaves, then fetch the full row in 'retrieve_row'
1550             var nparams = obj.list.append(data);
1551             var node = nparams.treeitem_node;
1552             obj.map_tree[ type + '_' + item.id() ] =  node;
1553             if (attributes) {
1554                 for (var i in attributes) {
1555                     node.setAttribute(i,attributes[i]);
1556                 }
1557             }
1558
1559         } catch(E) {
1560             dump(E+'\n');
1561             alert(E);
1562         }
1563     },
1564
1565     'list_init' : function( params ) {
1566
1567         try {
1568             netscape.security.PrivilegeManager.enablePrivilege("UniversalXPConnect");
1569             var obj = this;
1570             
1571             JSAN.use('circ.util');
1572             var columns = [
1573                 {
1574                     'id' : 'tree_location',
1575                     'label' : $('serialStrings').getString('serial.manage_subs.tree_location'),
1576                     'flex' : 1, 'primary' : true, 'hidden' : false, 
1577                     'render' : function(my) { 
1578                         if (my.sdist) { return my.sdist.label(); }
1579                         if (my.siss) { return my.siss.label(); }
1580                         if (my.scap) { return $('serialStrings').getFormattedString('serial.manage_subs.scap_id', [my.scap.id()]); }
1581                         if (my.ssub) { return $('serialStrings').getFormattedString('serial.manage_subs.ssub_id', [my.ssub.id()]); }
1582                         if (my.aou) { return $('serialStrings').getFormattedString('serial.manage_dists.library_label', [my.aou.shortname(), my.aou.name()]); }
1583                         if (my.label) { return my.label; }
1584                         /* If all else fails... */
1585                         return "???"; 
1586                     },
1587                 },
1588                 {
1589                     'id' : 'subscription_count',
1590                     'label' : $('serialStrings').getString('serial.manage_subs.subscriptions'),
1591                     'flex' : 0, 'primary' : false, 'hidden' : false, 
1592                     'render' : function(my) { return my.subscription_count; },
1593                 },
1594                 /*{
1595                     'id' : 'distribution_count',
1596                     'label' : 'Members',
1597                     'flex' : 0,
1598                     'primary' : false, 'hidden' : false, 
1599                     'render' : function(my) { return my.distribution_count; },
1600                 },*/
1601             ];
1602             JSAN.use('util.list'); obj.list = new util.list('subs_tree');
1603             obj.list.init(
1604                 {
1605                     'no_auto_select' : true,
1606                     'columns' : columns,
1607                     'retrieve_row' : function(params) {
1608
1609                         var row = params.row;
1610                         obj.funcs.push(
1611                             function() {
1612
1613                                 if (typeof params.on_retrieve == 'function') {
1614                                     params.on_retrieve(row);
1615                                 }
1616
1617                             }
1618                         );
1619
1620                         return row;
1621                     },
1622                     'on_click' : function(ev) {
1623                         netscape.security.PrivilegeManager.enablePrivilege('UniversalXPConnect UniversalBrowserRead');
1624                         var row = {}; var col = {}; var nobj = {};
1625                         obj.list.node.treeBoxObject.getCellAt(ev.clientX,ev.clientY,row,col,nobj); 
1626                         if ((row.value == -1)||(nobj.value != 'twisty')) { return; } // on_click runs for twistys only
1627
1628                         var node = obj.list.node.contentView.getItemAtIndex(row.value);
1629                         var list = [ node.getAttribute('retrieve_id') ];
1630                         if (typeof obj.on_select == 'function') {
1631                             obj.on_select(list,true);
1632                         }
1633                         if (typeof window.xulG == 'object' && typeof window.xulG.on_select == 'function') {
1634                             window.xulG.on_select(list);
1635                         }
1636                     },
1637                     'on_select' : function(ev) {
1638                         JSAN.use('util.functional');
1639                         
1640                         // get the actual node clicked to determine which editor to use
1641                         if (obj.list.node.view.selection.currentIndex > -1) {
1642                             var node = obj.list.node.contentView.getItemAtIndex(obj.list.node.view.selection.currentIndex);
1643                             obj.focused_node_retrieve_id = node.getAttribute('retrieve_id');
1644                         }
1645
1646                         var sel = obj.list.retrieve_selection();
1647                         obj.controller.view.sel_clip.disabled = sel.length < 1;
1648                         obj.sel_list = util.functional.map_list(
1649                             sel,
1650                             function(o) { return o.getAttribute('retrieve_id'); }
1651                         );
1652                         obj.toggle_actions();
1653                         if (typeof obj.on_select == 'function') {
1654                             obj.on_select(obj.sel_list);
1655                         }
1656                         if (typeof window.xulG == 'object' && typeof window.xulG.on_select == 'function') {
1657                             window.xulG.on_select(obj.sel_list);
1658                         }
1659                     },
1660                 }
1661             );
1662
1663             obj.controller.render();
1664
1665         } catch(E) {
1666             this.error.sdump('D_ERROR','serial/manage_subs.list_init: ' + E + '\n');
1667             alert(E);
1668         }
1669     },
1670
1671     'toggle_actions' : function() {
1672         var obj = this;
1673         try {
1674             var found_aou = false; var found_ssub = false; var found_sdist = false; var found_siss = false; var found_scap = false; var found_sdist_group = false; var found_siss_group = false; var found_scap_group = false;
1675             for (var i = 0; i < obj.sel_list.length; i++) {
1676                 var type = obj.sel_list[i].split(/_/)[0];
1677                 switch(type) {
1678                     case 'aou' : 
1679                         found_aou = true; 
1680                     break;
1681                     case 'ssub' : found_ssub = true; break;
1682                     case 'sdist' : found_sdist = true; break;
1683                     case 'siss' : found_siss = true; break;
1684                     case 'scap' : found_scap = true; break;
1685                     case 'sdist-group' : found_sdist_group = true; break;
1686                     case 'siss-group' : found_siss_group = true; break;
1687                     case 'scap-group' : found_scap_group = true; break;
1688                 }
1689             }
1690             obj.controller.view.cmd_add_sdist.setAttribute('disabled','true');
1691             obj.controller.view.cmd_add_siss.setAttribute('disabled','true');
1692             obj.controller.view.cmd_add_scap.setAttribute('disabled','true');
1693             obj.controller.view.cmd_make_predictions.setAttribute('disabled','true');
1694             obj.controller.view.cmd_delete_sdist.setAttribute('disabled','true');
1695             obj.controller.view.cmd_delete_siss.setAttribute('disabled','true');
1696             obj.controller.view.cmd_delete_scap.setAttribute('disabled','true');
1697             obj.controller.view.cmd_add_subscriptions.setAttribute('disabled','true');
1698             obj.controller.view.cmd_mark_library.setAttribute('disabled','true');
1699             obj.controller.view.cmd_delete_ssub.setAttribute('disabled','true');
1700             obj.controller.view.cmd_mark_subscription.setAttribute('disabled','true');
1701             obj.controller.view.cmd_transfer_subscription.setAttribute('disabled','true');
1702             obj.controller.view.cmd_transfer_sdists.setAttribute('disabled','true');
1703             if (found_aou) {
1704                 obj.controller.view.cmd_add_subscriptions.setAttribute('disabled','false');
1705                 obj.controller.view.cmd_mark_library.setAttribute('disabled','false');
1706             }
1707             if (found_ssub) {
1708                 obj.controller.view.cmd_delete_ssub.setAttribute('disabled','false');
1709                 obj.controller.view.cmd_mark_subscription.setAttribute('disabled','false');
1710                 obj.controller.view.cmd_add_sdist.setAttribute('disabled','false');
1711                 obj.controller.view.cmd_add_siss.setAttribute('disabled','false');
1712                 obj.controller.view.cmd_add_scap.setAttribute('disabled','false');
1713                 obj.controller.view.cmd_transfer_subscription.setAttribute('disabled','false');
1714                 obj.controller.view.cmd_make_predictions.setAttribute('disabled','false');
1715             }
1716             if (found_sdist_group) {
1717                 obj.controller.view.cmd_add_sdist.setAttribute('disabled','false');
1718             }
1719             if (found_siss_group) {
1720                 obj.controller.view.cmd_add_siss.setAttribute('disabled','false');
1721             }
1722             if (found_scap_group) {
1723                 obj.controller.view.cmd_add_scap.setAttribute('disabled','false');
1724             }
1725             if (found_sdist) {
1726                 obj.controller.view.cmd_delete_sdist.setAttribute('disabled','false');
1727                 obj.controller.view.cmd_transfer_sdists.setAttribute('disabled','false');
1728             }
1729             if (found_siss) {
1730                 obj.controller.view.cmd_delete_siss.setAttribute('disabled','false');
1731             }
1732             if (found_scap) {
1733                 obj.controller.view.cmd_delete_scap.setAttribute('disabled','false');
1734             }
1735         } catch(E) {
1736             obj.error.standard_unexpected_error_alert(document.getElementById('catStrings').getString('staff.cat.copy_browser.actions.error'),E);
1737         }
1738     },
1739
1740     'refresh_list' : function() { 
1741         try {
1742             var obj = this;
1743             obj.list.clear();
1744             obj.map_tree = {};
1745             obj.map_ssub = {};
1746             obj.map_sdist = {};
1747             obj.map_siss = {};
1748             obj.map_scap = {};
1749             obj.org_ids = obj.network.simple_request('FM_SSUB_AOU_IDS_RETRIEVE_VIA_RECORD_ID.authoritative',[ obj.docid ]);
1750             if (typeof obj.org_ids.ilsevent != 'undefined') throw(obj.org_ids);
1751             JSAN.use('util.functional'); 
1752             obj.org_ids = util.functional.map_list( obj.org_ids, function (o) { return Number(o); });
1753             /*
1754             var org = obj.data.hash.aou[ obj.data.list.au[0].ws_ou() ];
1755             obj.show_libs( org );
1756             */
1757             obj.show_my_libs( document.getElementById('lib_menu').value );
1758         } catch(E) {
1759             this.error.standard_unexpected_error_alert(document.getElementById('catStrings').getString('staff.cat.copy_browser.refresh_list.error'),E);
1760         }
1761     },
1762 };
1763
1764 dump('exiting serial/manage_subs.js\n');