d55a09f338b3a3221b0fd20b573b9b1aae0539c8
1 <?php
2 class appgroup extends plugin
3 {
4 var $config;
5 var $curbase;
7 /* Contains the menu structure in an array.
8 */
9 var $a_Structure= array();
10 var $a_Structure_on_load = array();
11 var $Releases;
12 var $FAIrelease = 0;
13 var $apps = array();
14 var $_cache = array();
16 var $app_parameter = array();
17 var $edit_entry = array();
18 var $enableReleaseManagement = FALSE;
21 public function __construct(&$config, $dn= NULL, $parent= NULL)
22 {
23 plugin::plugin($config,$dn,$parent);
24 $this->dn = $dn;
25 $this->_load_menu_structure();
26 $this->a_Structure_on_load = $this->a_Structure;
28 /* Check if we have relase mangement enabled and prepare group application for release management */
29 $tmp = $config->search("faiManagement", "CLASS",array('menu','tabs'));
30 if(!empty($tmp)){
31 $this->enableReleaseManagement = true;
32 }
34 $this->Releases = $this->getReleases();
35 $this->FAIrelease = "/";
36 $this->curbase = $this->config->current['BASE'];
37 $this->reload();
39 $this->is_account = FALSE;
40 if(count($this->_get_all_entries()) > 1){
41 $this->is_account= TRUE;
42 }
43 $this->initially_was_account = $this->is_account;
44 }
47 /*! \brief Reload the list of applications for the currently selected release
48 */
49 function reload()
50 {
51 $ret = array();
52 $release_info = $this->Releases[$this->FAIrelease];
54 if(!isset($this->_cache['ReleaseApps'][$release_info['suffix']])){
56 $ldap = $this->config->get_ldap_link();
57 $ldap->cd($this->config->current['BASE']);
58 $ldap->search("ou=apps",array("dn"));
59 $app_deps = array();
60 while($attrs = $ldap->fetch()){
61 $app_deps[] = $attrs['dn'];
62 }
64 foreach($app_deps as $dep){
65 $ldap->cd($dep);
66 $ldap->search("objectClass=FAIbranch",array("dn"));
67 while($attrs = $ldap->fetch()){
68 $app_deps[] = $attrs['dn'];
69 }
70 }
72 foreach($app_deps as $dep){
73 if(preg_match("/^".normalizePreg($release_info['suffix'])."/",$dep)){
74 $ret = array_merge($ret,get_list("(objectClass=gosaApplication)","application",$dep,array("*"),GL_NONE));
75 }
76 }
78 $tmp = array();
79 foreach($ret as $key => $app){
80 $tmp[$key] = $app['cn'][0];
81 }
82 natcasesort($tmp);
83 $res = array();
84 foreach($tmp as $key => $app){
85 $res[] = $ret[$key];
86 }
88 $this->_cache['ReleaseApps'][$release_info['suffix']] = $res;
89 }
90 $this->apps = $this->_cache['ReleaseApps'][$release_info['suffix']];
91 }
96 /*! \brief generate a list of available releases
97 @return return an array with all available releases.
98 */
99 function getReleases()
100 {
101 $ret =array("/" => array("name" => "/", "found" => TRUE , "parts" => array(),"suffix" => get_ou('applicationou')));
102 if($this->enableReleaseManagement){
104 /* Only display those releases that we are able to read */
105 $dn = $this->config->current['BASE'];
106 $filter = "(&(objectClass=organizationalUnit)(objectClass=FAIbranch))";
107 $res = get_sub_list($filter,array("application","fai"), array(get_ou("applicationou"),get_ou("faiou")),$dn, array("ou","FAIstate"), GL_SUBSEARCH);
110 foreach($res as $attrs){
111 if(preg_match("/".get_ou('applicationou')."/",$attrs['dn'])){
112 $bb = preg_replace("/".get_ou('applicationou').".*/","",$attrs['dn']);
113 $parts = array_reverse(split("ou=",$bb));
115 $str ="";
116 foreach($parts as $key => $part){
117 if(empty($part)) {
118 unset($parts[$key]);
119 continue;
120 }
121 $part = str_replace(",","",$part);
122 $str .= $part."/";
123 $parts[$key] = $part;
124 }
125 $name = preg_replace("/\/$/","",$str);
126 if(empty($name)) {
127 $name ="/";
128 }
129 $FAIstate = "";
130 if(isset($attrs['FAIstate'])){
131 $FAIstate = $attrs['FAIstate'][0];
132 }
134 $all = $this->_get_all_entries();
135 $found = FALSE;
136 foreach($all as $entry){
137 if(isset($entry['DN']) && preg_match("/^".normalizePreg($bb)."/",$entry['DN'])){
138 $found =TRUE;
139 break;
140 }
141 }
143 $cnt = 0;
144 $ret[$name] = array("name" => $name,
145 "found" => $found,
146 "FAIstate" => $FAIstate,
147 "dn" => $attrs['dn'],
148 "parts" => $parts,"suffix" => $bb.get_ou('applicationou'));
149 }
150 }
151 }
152 ksort($ret);
153 return($ret);
154 }
157 /*! \brief Load the menu structure from ldap and create a multi dimensional array
158 */
159 function _load_menu_structure()
160 {
161 $this->a_Structure = array();
162 $ldap = $this->config->get_ldap_link();
163 $ldap->cd($this->dn);
164 $ldap->search("(|(objectClass=gotoSubmenuEntry)(objectClass=FAIbranch)(objectClass=gotoMenuEntry))",array("*"));
166 $base = array();
167 $base['UNIQID'] = uniqid();
168 $base['PARENT'] = 0;
169 $base['NAME'] = "";
170 $base['TYPE'] = "BASE";
171 $base['ENTRIES']= array();
172 $base['STATUS'] = "LOADED";
174 $this->a_Structure[0] = $base;
176 while($attrs = $ldap->fetch()){
177 $cur = &$this->a_Structure[0]['ENTRIES'];
178 $parent_id = $base['UNIQID'];
179 $sub_dn = preg_replace("/,".normalizePreg($this->dn)."$/","",$attrs['dn']);
180 $sub_dn_array = split("\,",$sub_dn);
182 $found = true;
183 for($i = (count($sub_dn_array)-1) ; $i >= 0 ; $i--){
184 $name = preg_replace("/^[^=]*+=/","",$sub_dn_array[$i]);
186 if($i > 0){
187 $found =FALSE;
188 foreach($cur as $key => $entry){
189 if($entry['NAME'] == $name){
190 $cur = &$cur[$key]['ENTRIES'];
191 $parent_id = $entry['UNIQID'];
192 $found =true;
193 break;
194 }
195 }
196 }else{
198 if(!$found){
199 break;
200 }
201 $priority = 1;
202 if(isset($attrs['gosaApplicationPriority'])){
203 $priority= $attrs['gosaApplicationPriority'][0];
204 }
205 while(isset($cur[$priority])){
206 $priority ++;
207 }
209 $data = array();
210 if(in_array("gotoSubmenuEntry",$attrs['objectClass'])){
211 $type = "FOLDER";
213 $data['ICON'] = "";
214 if(isset($attrs['gosaApplicationIcon'])){
215 $data['ICON'] = $ldap->get_attribute($attrs['dn'],"gosaApplicationIcon");
216 }
218 }elseif(in_array("gotoMenuEntry",$attrs['objectClass'])){
220 $type = "ENTRY";
221 $data['INFO'] = "";
222 $data['PARAMETER'] = array();
223 if(isset($attrs['gosaApplicationParameter'])){
224 for($p = 0 ; $p < $attrs['gosaApplicationParameter']['count'] ; $p ++){
225 if(preg_match("/:/",$attrs['gosaApplicationParameter'][$p])){
226 $tmp = split(":",$attrs['gosaApplicationParameter'][$p]);
227 $data['PARAMETER'][$tmp[0]] = $tmp[1];
228 }elseif($attrs['gosaApplicationParameter'][$p] == "*separator*"){
229 $type = "SEPERATOR";
230 $data['PARAMETER'] = array();
231 break;
232 }
233 }
234 }
235 }elseif(in_array("FAIbranch",$attrs['objectClass'])){
237 $type = "RELEASE";
238 if(isset($attrs['FAIstate'][0])){
239 $data['FAIstate'] = $attrs['FAIstate'][0];
240 }else{
241 $data['FAIstate'] = "";
242 }
243 }
245 $data['DN'] = $attrs['dn'];
246 $data['NAME'] = $name;
247 $data['TYPE'] = $type;
248 $data['PRIORITY'] = $priority;
249 $data['ENTRIES'] = array();
250 $data['UNIQID'] = uniqid();
251 $data['PARENT'] = $parent_id;
252 $data['STATUS'] = "LOADED";
253 $cur[$priority] = $data;
254 ksort($cur);
255 }
256 }
257 }
258 }
261 function execute()
262 {
263 /* Call parent execute */
264 plugin::execute();
266 if(isset($_GET['r'])) $this->__construct($this->config,$this->dn);
268 if (isset($_POST['modify_state'])){
269 $this->is_account = !$this->is_account;
270 }
272 /* Do we represent a valid account? */
273 if (!$this->is_account){
274 $display= $this->show_enable_header(_("Add application extension"),
275 _("Application extension disabled. You can enable it by clicking below."));
276 return ($display);
277 }
279 $display = $this->show_enable_header(_("Remove application extension"),
280 _("Application extension enabled. You can disable it by clicking below."));
283 if(isset($_GET['send'])){
284 $id = $_GET['send'];
285 $all = $this->_get_all_entries();
286 if(isset($all[$id])){
287 send_binary_content($all[$id]['ICON'],$id.".jpg","image/jpeg");
288 exit;
289 }
290 }
292 if(isset($_GET['r']))
293 $this->__construct($this->config,$this->dn);
295 if(count($this->edit_entry)){
296 if($this->edit_entry['TYPE'] == "ENTRY"){
297 $smarty = get_smarty();
298 $smarty->assign("type", "ENTRY");
299 $smarty->assign("entry",$this->edit_entry);
300 $smarty->assign("paras",$this->app_parameter);
301 $display= $smarty->fetch (get_template_path('edit_entry.tpl', TRUE, dirname(__FILE__)));
302 return($display);
303 }
304 if($this->edit_entry['TYPE'] == "FOLDER"){
305 $smarty = get_smarty();
307 session::set("binarytype" , "image/jpeg");
308 session::set("binary" , $this->edit_entry['ICON']);
310 $smarty->assign("rand", microtime(TRUE));
311 $smarty->assign("image_set" , strlen($this->edit_entry['ICON']) > 0);
312 $smarty->assign("type", "FOLDER");
313 $smarty->assign("entry",$this->edit_entry);
314 $display= $smarty->fetch (get_template_path('edit_entry.tpl', TRUE, dirname(__FILE__)));
315 return($display);
316 }
317 }
319 $smarty = get_smarty();
320 $smarty->assign("plug_id" , $_GET['plug']);
322 /* Create application list */
323 $div = new divSelectBox("appgroup");
324 $div->SetHeight(300);
325 $departments = array();
326 $res = get_list("(objectClass=gosaDepartment)", "application", $this->curbase,array("description","cn","ou"),GL_SIZELIMIT);
327 foreach($res as $value){
328 $fdn = $value['dn'];
329 $fdn = preg_replace("/".normalizePreg($this->curbase)."/","",$fdn);
330 $fdn= @LDAP::fix($fdn);
331 if($value["description"][0]!=".."){
332 $departments[$value['dn']]= convert_department_dn($fdn)." - [".$value["description"][0]."]";
333 }else{
334 $departments[$value['dn']]=convert_department_dn($fdn)." ["._("Back")."]";
335 }
336 }
338 $linkopen = "<a href='?plug=".$_GET['plug']."&act=depopen&depid=%s'>%s</a>";
340 /* Create base back entry */
341 $base_back = preg_replace("/^[^,]+,/","",$this->curbase);
342 if((strlen($base_back)>= strlen($this->config->current['BASE']))&&($this->curbase!=$this->config->current['BASE'])){
343 $div->AddEntry(array(
344 array("string"=>sprintf($linkopen,base64_encode($base_back),".. ["._("back")."]"),
345 "attach"=>"style='border:0px;'")
346 ));
347 }
349 /* Append departments for current base */
350 foreach($departments as $key => $app){
351 $div->AddEntry(array(
352 array("string"=>"<img class='center' src='images/folder.png' alt='"._("department")."'> ".sprintf($linkopen,
353 base64_encode($key),$app),
354 "attach"=>"style='border:0px;'")
355 ));
356 }
359 /* Add applications found on this base */
360 $used_apps = $this->_get_used_entry_name();
361 foreach($this->apps as $key => $app){
362 if(in_array($app['cn'][0],$used_apps)){
363 continue;
364 }
365 if(!preg_match("/".get_ou('applicationou').normalizePreg($this->curbase)."$/",$app['dn'])){
366 continue;
367 }
369 $name = $app['cn'][0];
370 if(isset($app['description'])){
371 $name .= " [".$app['description'][0]."]";
372 }
373 $div->AddEntry(array(
374 array("string"=>sprintf("<input class='center' type='checkbox' value='1' name='AddApp_%s'>",$key).
375 "<img class='center' src='images/select_application.png' alt='"._("application")."'> ".$name,
376 "attach"=>"style='border:0px;'")
377 ));
378 }
381 $smarty->assign("enableReleaseManagement",$this->enableReleaseManagement);
382 $smarty->assign("FAIrelease",$this->FAIrelease);
383 $smarty->assign("app_list",$div->DrawList());
384 $smarty->assign("i",0);
385 $smarty->assign("releases",$this->Releases);
386 $smarty->assign("folders" , $this->_get_folder_names());
387 $entries = $this->_get_entries_for_release($this->FAIrelease);
388 $smarty->assign("entries",$entries);
389 $display.= $smarty->fetch (get_template_path('app_list.tpl', TRUE, dirname(__FILE__)));
390 return($display);
391 }
394 /*! \brief Returns all used folder names
395 @return Array All used folder names.
396 */
397 function _get_folder_names()
398 {
399 $data = $this->_get_entries_for_release($this->FAIrelease);
400 $all = $this->_get_all_entries();
401 $ret = array("BASE" => ".");
402 foreach($data as $entry){
404 if($entry['TYPE'] == "FOLDER"){
405 $str = $entry['NAME'];
406 $parent = $entry['PARENT'];
407 $i = 10;
408 while(isset($all[$parent]) && $i){
409 $i --;
410 $parent_o = $all[$parent];
411 $str = $parent_o['NAME']."/".$str;
412 $parent = $all[$parent_o['UNIQID']]['PARENT'];
413 }
414 $ret[$entry['UNIQID']] = $str;
415 }
416 }
417 return($ret);
418 }
421 /*! \brief return all used applications
422 @return Array All used applications.
423 */
424 function _get_used_entry_name()
425 {
426 $data = $this->_get_entries_for_release($this->FAIrelease);
427 $ret = array();
428 foreach($data as $entry){
429 if($entry['TYPE'] == "ENTRY"){
430 $ret[] = $entry['NAME'];
431 }
432 }
433 return($ret);
434 }
437 /*! \brief Returns all folder an entries for the selected release
438 @return Array Returns the complete menu structure for the given array.
439 */
440 function _get_entries_for_release($release,$cur = NULL)
441 {
442 $all = $this->_get_all_entries();
443 $key = $this->_get_release_key($release);
444 if(isset($all[$key]) && count($all[$key]['ENTRIES'])){
445 $res = $this->_get_all_entries(TRUE,TRUE,$all[$key]['ENTRIES']);
446 return($res);
447 }
448 return(array());
449 }
452 /*! \brief Save the currently edited entry */
453 function _save_entry_edit()
454 {
455 $all = $this->_get_all_entries();
456 $entry = $this->edit_entry;
457 $r_entry= &$all[$entry['UNIQID']];
459 if($entry['TYPE'] == "ENTRY"){
460 $r_entry['PARAMETER'] = $this->app_parameter;
461 $r_entry['STATUS'] = "EDITED";
462 }
463 if($entry['TYPE'] == "FOLDER"){
464 $r_entry['ICON'] = $this->edit_entry['ICON'];
465 $r_entry['STATUS'] = "EDITED";
466 }
467 $this->dialog = FALSE;
468 $this->edit_entry = array();
469 }
472 /*! \brief prepare the entry with the given ID, to be edited.
473 */
474 function _edit_entry_edit($id)
475 {
476 $all = $this->_get_all_entries();
477 $entry = $all[$id];
479 $this->app_parameter = array();
480 if($entry['TYPE'] == "ENTRY"){
481 $found = FALSE;
482 foreach($this->apps as $id => $app){
484 if($app['cn'][0] == $entry['NAME']){
485 $found = TRUE;
486 break;
487 }
488 }
489 if($found){
491 /* Create a list of editable parameter */
492 if(isset($app['gosaApplicationParameter'])){
493 for($i = 0 ; $i < $app['gosaApplicationParameter']['count'] ; $i++) {
494 $para = $app['gosaApplicationParameter'][$i];
495 $tmp = split(":",$para);
496 $this->app_parameter[$tmp[0]] = $tmp[1];
497 }
498 }
500 /* Overwrite parameters with entry parameters */
501 foreach($entry['PARAMETER'] as $name => $value){
502 $this->app_parameter[$name] = $value;
503 }
505 $this->dialog = TRUE;
506 $this->edit_entry = $entry;
507 }
508 }
510 if($entry['TYPE'] == "FOLDER"){
511 $this->dialog = TRUE;
512 $this->edit_entry = $entry;
513 }
514 }
517 function remove_from_parent()
518 {
519 $ldap = $this->config->get_ldap_link();
520 $ldap->cd($this->dn);
521 $ldap->ls("(|(objectClass=gotoSubmenuEntry)(objectClass=FAIbranch)(objectClass=gotoMenuEntry))",$this->dn,array("*"));
522 $a_remove = array();
523 while($attrs = $ldap->fetch()){
524 $a_remove[] = $attrs['dn'];
525 }
526 foreach($a_remove as $remove){
527 $ldap->rmdir_recursive($remove);
528 if (!$ldap->success()){
529 msg_dialog::display(_("LDAP error"), msgPool::ldaperror($ldap->get_error(), $this->dn, LDAP_DEL, get_class()));
530 }
531 }
532 $this->_load_menu_structure();
533 }
536 function check()
537 {
538 }
541 /*! \brief Create missing releases, if there is a release selected \
542 that is currently not part of the menu structure \
543 then create this entry
544 */
545 function _check_missing_release($release)
546 {
547 $release_info = $this->Releases[$release];
549 $parent_id = $this->a_Structure[0]['UNIQID'];
550 $cur = &$this->a_Structure[0]['ENTRIES'];
551 for($i = 0 ; $i < count($release_info['parts']) ; $i ++){
552 $part = $release_info['parts'][$i];
553 $found = FALSE;
554 foreach($cur as $key => $name){
555 if($name['NAME'] == $part){
556 $parent_id = $cur[$key]['UNIQID'];
557 $cur = &$cur[$key]['ENTRIES'];
559 $found =TRUE;
560 break;
561 }
562 }
563 if(!$found){
564 $release = array();
565 $release['UNIQID'] = uniqid();
566 $release['PARENT'] = $parent_id;
567 $release['NAME'] = $part;
568 $release['TYPE'] = "RELEASE";
569 $release['ENTRIES']= array();
570 $release['STATUS'] = "ADDED";
571 $release['FAIstate'] = $release_info['FAIstate'];
572 $cur[] = $release;
573 $i --;
574 }
575 }
576 }
580 function _move_entry($id,$dir)
581 {
582 $all = $this->_get_all_entries();
583 if($dir == "down"){
584 $to = $this->_get_next($id);
585 }
586 if($dir == "up"){
587 $to = $this->_get_last($id);
588 }
590 if(!$to){
591 return;
592 }
594 $o_to = $all[$to];
595 $o_from = $all[$id];
597 if($o_to['PARENT'] == $o_from['UNIQID'] && $dir == "down"){
598 $to = $this->_get_next($to,$o_from['PARENT']);
599 $o_to = $all[$to];
600 }
603 /* Target is ENTRY && same BASE, just switch */
604 if($o_to['PARENT'] == $o_from['PARENT'] ){
605 $parent = $all[$o_to['PARENT']];
606 $pos = 0;
607 foreach($parent['ENTRIES'] as $entry){
608 $pos ++;
609 if($entry['UNIQID'] == $to){
610 break;
611 }
612 }
613 if($dir == "up" && $pos > 0){
614 $pos --;
615 }
616 $this->_add_entry($parent['UNIQID'],$o_from,$pos);
617 $this->_remove_entry_id($id);
618 return(TRUE);
619 }
620 return(FALSE);
621 }
625 function _get_last($id)
626 {
627 $all_l = array_reverse($this->_get_entries_for_release($this->FAIrelease));
628 for($i = 0 ; $i < count($all_l) ; $i ++){
629 if(isset($all_l[$i]['UNIQID']) && $all_l[$i]['UNIQID'] == $id){
630 $i++;
631 break;
632 }
633 }
634 while(isset($all_l[$i]) && !in_array($all_l[$i]['TYPE'],array("ENTRY","FOLDER","CLOSE","OPEN")) && $i < count($all_l)){
635 $i++;
636 }
638 if(!isset($all_l[$i])){
639 return(FALSE);
640 }
642 if(in_array($all_l[$i]['TYPE'],array("CLOSE","OPEN"))){
643 return($all_l[$i]['PARENT']);
644 }
646 return($all_l[$i]['UNIQID']);
647 }
650 function _get_next($id,$parent = 0)
651 {
652 $all_l = $this->_get_entries_for_release($this->FAIrelease);
653 for($i = 0 ; $i < count($all_l) ; $i ++){
654 if(isset($all_l[$i]['UNIQID']) && $all_l[$i]['UNIQID'] == $id){
655 $i++;
656 break;
657 }
658 }
659 if($parent != 0){
660 while(isset($all_l[$i]) && $all_l[$i]['PARENT'] != $parent){
661 $i++;
662 }
663 }else{
664 while(isset($all_l[$i]) && !in_array($all_l[$i]['TYPE'],array("ENTRY","FOLDER")) && $i < count($all_l)){
665 $i++;
666 }
667 }
668 if(!isset($all_l[$i])){
669 return(FALSE);
670 }
671 if(in_array($all_l[$i]['TYPE'],array("CLOSE","OPEN"))){
672 return($all_l[$i]['PARENT']);
673 }
674 return($all_l[$i]['UNIQID']);
675 }
680 /* !\brief Handle ui POSTS, like sort up/down/delete
681 */
682 function save_object()
683 {
684 foreach($_POST as $name => $value){
685 if(preg_match("/del_/",$name)){
686 $id = preg_replace("/^del_/","",$name);
687 $id = preg_replace("/_(x|y)$/","",$id);
688 $this->_remove_entry_id($id);
689 break;
690 }
691 if(preg_match("/app_entry_edit/",$name)){
692 $id = preg_replace("/^app_entry_edit/","",$name);
693 $id = preg_replace("/_(x|y)$/","",$id);
694 $this->_edit_entry_edit($id);
695 break;
696 }
697 if(preg_match("/up_/",$name)){
698 $id = preg_replace("/^up_/","",$name);
699 $id = preg_replace("/_(x|y)$/","",$id);
700 $this->_move_entry($id,"up");
701 break;
702 }
703 if(preg_match("/down_/",$name)){
704 $id = preg_replace("/^down_/","",$name);
705 $id = preg_replace("/_(x|y)$/","",$id);
706 $this->_move_entry($id,"down");
707 break;
708 }
709 if(preg_match("/^parameter_/",$name) &&
710 count($this->edit_entry) && $this->edit_entry['TYPE'] == "ENTRY"){
711 $name = preg_replace("/^parameter_/","",$name);
712 $this->app_parameter[$name] = $value;
713 }
714 }
715 if(isset($_POST['FAIrelease'])){
716 $this->FAIrelease = $_POST['FAIrelease'];
717 $this->_check_missing_release($this->FAIrelease);
718 }
719 if(isset($_GET['act']) && $_GET['act'] == 'depopen'){
720 $this->curbase = base64_decode($_GET['depid']);
721 }
722 if(isset($_POST['add_to_folder']) && isset($_POST['folder'])){
723 $folder = $_POST['folder'];
724 foreach($_POST as $name => $value){
725 if(preg_match("/^AddApp_[0-9]*$/",$name)){
726 $this->_add_app_id($folder,preg_replace("/^AddApp_/","",$name));
727 }
728 }
729 }
731 /* Add seperator */
732 if(isset($_POST['add_seperator']) && isset($_POST['menu_folder'])){
733 $folder = $_POST['menu_folder'];
734 $this->_add_seperator($folder);
735 }
737 if(isset($_POST['add_menu_to_folder']) && isset($_POST['menu_folder'])){
738 $folder = $_POST['menu_folder'];
739 $name = $_POST['menu_folder_name'];
740 if(strlen($name) > 0 && preg_match("/[a-z ]/i",$name)){
741 $this->_add_sub_folder($folder,$name);
742 }
743 }
744 if(isset($_POST['app_entry_save'])){
745 $this->_save_entry_edit();
746 }
748 if(isset($_FILES['folder_image']) && isset($_POST['folder_image_upload'])){
749 if($_FILES['folder_image']['error'] == 0 && $_FILES['folder_image']['size'] > 0){
750 $this->edit_entry['ICON'] = file_get_contents($_FILES['folder_image']['tmp_name']);
751 }
752 }
754 if(isset($_POST['edit_reset_image'])){
755 $this->edit_entry['ICON'] = "";
756 }
758 if(isset($_POST['app_entry_cancel'])){
759 $this->edit_entry = array();
760 $this->dialog = FALSE;
761 }
762 $this->reload();
763 }
766 /*! \brief Returns the UNIQID of the currently selected release
767 */
768 function _get_release_key($release,$add_if_missing = FALSE)
769 {
770 $release_info = $this->Releases[$release];
772 if($release_info['name'] == "/"){
773 return($this->a_Structure['0']['UNIQID']);
774 }
776 $cur = &$this->a_Structure[0]['ENTRIES'];
777 $s_key = "";
778 $found = FALSE;
779 foreach($release_info['parts'] as $name){
780 foreach($cur as $key => $obj){
781 if($obj['TYPE'] == "RELEASE" && $obj['NAME'] == $name){
782 $s_key = $cur[$key]['UNIQID'];
783 $cur = &$cur[$key]['ENTRIES'];
784 $found = TRUE;
785 break;
786 }
787 $found = FALSE;
788 }
789 }
790 if($found){
791 return($s_key);
792 }
793 return(FALSE);
794 }
797 /*! \brief Add a new folder folder to the specified folder id
798 @param String $folder The folder id in where we want to add the new folder.
799 @param String $name The name of the new folder.
800 */
801 function _add_sub_folder($folder,$name)
802 {
803 $all = $this->_get_all_entries();
804 if($folder == "BASE"){
805 $folder = $this->_get_release_key($this->FAIrelease,TRUE);
806 }
808 if(isset($all[$folder])){
809 $a_folder = array();
810 $a_folder['STATUS'] = "ADDED";
811 $a_folder['NAME'] = $name;
812 $a_folder['UNIQID'] = uniqid();
813 $a_folder['ENTRIES']= array();
814 $a_folder['PARENT'] = $folder;
815 $a_folder['TYPE'] = "FOLDER";
816 $a_folder['ICON'] = "";
817 $all[$folder]['ENTRIES'][] = $a_folder;
818 }
819 }
822 /* !\brief Remove the given id from the menu structure.
823 @param String ID to of the entry we want to remove.
824 @return Boolean TRUE on success
825 */
826 function _remove_entry_id($id)
827 {
828 $all = $this->_get_all_entries();
829 if(isset($all[$id])){
830 $all[$id]['STATUS'] = "REMOVED";
831 $all[$id]['ENTRIES'] = array();
832 return(TRUE);
833 }
834 return(FALSE);
835 }
838 /* !\brief Remove the given id from the menu structure.
839 @param String ID to of the entry we want to remove.
840 @return Boolean TRUE on success
841 */
842 function _add_entry($folder_id,$entry,$pos = 0)
843 {
844 $all = $this->_get_all_entries();
846 /* Do not add removed */
847 if($entry['STATUS'] == "REMOVED"){
848 return;
849 }
851 if(isset($all[$folder_id])){
853 if(!isset($entry['ENTRIES'])){
854 $entries = array();
855 }else{
856 $entries = $entry['ENTRIES'];
857 }
859 $folder = &$all[$folder_id];
861 $entry['UNIQID'] = uniqid();
862 $entry['PARENT'] = $folder_id;
863 $entry['ENTRIES']= array();
864 $entry['STATUS'] = "ADDED";
866 $cnt = 0;
867 $new = array();
868 $added =FALSE;
869 foreach($folder['ENTRIES'] as $key => $obj){
870 if($obj['STATUS'] == "LOADED"){
871 $obj['STATUS'] = "EDITED";
872 }
873 if($pos == $cnt){
874 $new[] = $entry;
875 $added = TRUE;
876 }
877 $cnt ++;
878 $new[] = $obj;
879 }
880 if(!$added){
881 $new[] = $entry;
882 }
884 $all[$folder_id]['ENTRIES'] = $new;
885 foreach($entries as $sub){
886 $this->_add_entry($entry['UNIQID'],$sub,-1);
887 }
888 return(TRUE);
889 }
890 return(FALSE);
891 }
894 /*! \brief Add the application identified by $app_id to folder $folder_id
895 @param String folder_id The UNIQID of the folder where we want to add the new folder.
896 @param Integer app_id The ID of the application which should be added.
897 */
898 function _add_app_id($folder_id,$app_id)
899 {
900 $all = $this->_get_all_entries();
901 if($folder_id == "BASE"){
902 $folder_id = $this->_get_release_key($this->FAIrelease);
903 }
904 if(isset($all[$folder_id]) && isset($this->apps[$app_id])){
906 $new = array();
907 $new['TYPE'] = "ENTRY";
908 $new['NAME'] = $this->apps[$app_id]['cn'][0];
909 $new['UNIQID']= uniqid();
910 $new['PARENT']= $folder_id;
911 $new['PARAMETER']= array();
912 if(isset($this->apps[$app_id]['description'][0])){
913 $new['INFO'] = $this->apps[$app_id]['description'][0];
914 }else{
915 $new['INFO'] = "";
916 }
917 $new['STATUS']= "ADDED";
918 $all[$folder_id]['ENTRIES'][] = $new;
919 }
920 }
923 /*! \brief Add the application identified by $app_id to folder $folder_id
924 @param String folder_id The UNIQID of the folder where we want to add the new folder.
925 @param Integer app_id The ID of the application which should be added.
926 */
927 function _add_seperator($folder_id)
928 {
929 $all = $this->_get_all_entries();
930 if($folder_id == "BASE"){
931 $folder_id = $this->_get_release_key($this->FAIrelease);
932 }
934 if(isset($all[$folder_id])){
935 $new = array();
936 $new['TYPE'] = "SEPERATOR";
937 $new['NAME'] = "SEPERATOR";
938 $new['UNIQID']= uniqid();
939 $new['PARENT']= $folder_id;
940 $new['PARAMETER']= array();
941 $new['STATUS']= "ADDED";
942 $all[$folder_id]['ENTRIES'][] = $new;
943 }
944 }
947 /*! \brief Return all entries linear.
948 @param Boolean $add_tags If TRUE, OPEN/CLOSE Tags will be appended.
949 @param &Array Start here, Pointer to an array.
950 */
951 function _get_all_entries($add_tags = FALSE, $skip_release = FALSE, &$cur = NULL)
952 {
953 $ret = array();
954 if($cur == NULL){
955 $cur = &$this->a_Structure;
956 }
957 foreach($cur as $key => $entry){
959 if($skip_release && $entry['TYPE'] == "RELEASE"){
960 continue;
961 }
962 if($entry['TYPE'] == "ENTRY"){
963 $found = FALSE;
964 foreach($this->apps as $app){
965 if($app['cn'][0] == $entry['NAME']){
966 $found = TRUE;
967 if(isset($app['description'][0])){
968 $entry['INFO'] = "[".$app['description'][0]."]";
969 }
970 break;
971 }
972 }
973 if(!$found){
974 $entry['INFO'] = "<font color='red'>"._("Not available in release.")."</font>";
975 }
976 }
979 $tmp = $entry;
980 if(!$add_tags){
981 $ret[$tmp['UNIQID']] = &$cur[$key];
982 if(isset($entry['ENTRIES']) && count($entry['ENTRIES'])){
983 $ret = array_merge($ret,$this->_get_all_entries($add_tags,$skip_release,$cur[$key]['ENTRIES']));
984 }
985 }else{
987 if(isset($tmp['ENTRIES'])){
988 unset($tmp['ENTRIES']);
989 }
990 if($tmp['STATUS'] != "REMOVED"){
991 $ret[] = $tmp;
992 if(isset($entry['ENTRIES']) && count($entry['ENTRIES'])){
993 $add = false;
994 foreach($entry['ENTRIES'] as $entry){
995 if($entry['STATUS'] != "REMOVED"){
996 $add = TRUE;
997 break;
998 }
999 }
1001 if($add){
1002 $ret[] = array("TYPE" => "OPEN", "PARENT" => $entry['PARENT']);
1003 $ret = array_merge($ret,$this->_get_all_entries($add_tags,$skip_release,$cur[$key]['ENTRIES']));
1004 $ret[] = array("TYPE" => "CLOSE" , "PARENT" => $entry['PARENT']);
1005 }
1006 }
1007 }
1008 }
1009 }
1010 return($ret);
1011 }
1014 function save()
1015 {
1016 $ldap = $this->config->get_ldap_link();
1017 $all = $this->_get_all_entries();
1018 $prio = 0;
1019 $Actions = array("Remove" => array(),"Edit" => array() , "Add" => array());
1021 $sep_id = 0;
1022 foreach($all as $entry){
1023 $prio ++;
1024 $cur = $entry;
1025 $dn = "";
1027 do{
1028 if($cur['TYPE'] == "SEPERATOR"){
1029 $sep_id ++;
1030 $dn.= "cn=seperator_".$sep_id.",";
1031 }elseif($cur['TYPE'] == "ENTRY"){
1032 $dn.= "cn=".$cur['NAME'].",";
1033 }elseif($cur['TYPE'] == "FOLDER"){
1034 $dn.= "cn=".$cur['NAME'].",";
1035 }elseif($cur['TYPE'] == "RELEASE"){
1036 $dn.= "ou=".$cur['NAME'].",";
1037 }elseif($cur['TYPE'] == "BASE"){
1038 }
1039 if(!isset($all[$cur['PARENT']])){
1040 $cur = NULL;
1041 }else{
1042 $cur = $all[$cur['PARENT']];
1043 }
1044 }while(is_array($cur));
1046 $cur_dn = $dn.$this->dn;
1048 $attrs = array();
1049 switch($entry['TYPE']){
1050 case "SEPERATOR" :
1051 {
1052 $attrs['objectClass'] = "gotoMenuEntry";
1053 $attrs['cn'] = "seperator_".$sep_id;
1054 $attrs['gosaApplicationPriority'] = $prio;
1055 $attrs['gosaApplicationParameter'] = "*separator*";
1056 }
1057 break;
1058 case "ENTRY" :
1059 {
1060 $attrs['objectClass'] = "gotoMenuEntry";
1061 $attrs['cn'] = $entry['NAME'];
1062 $attrs['gosaApplicationPriority'] = $prio;
1063 $attrs['gosaApplicationParameter'] = array();
1066 foreach($entry['PARAMETER'] as $name => $value){
1067 $attrs['gosaApplicationParameter'][] = $name.":".$value;
1068 }
1069 if($entry['STATUS'] == "ADDED" && !count($attrs['gosaApplicationParameter'])){
1070 unset($attrs['gosaApplicationParameter']);
1071 }
1072 }
1073 break;
1074 case "FOLDER" :
1075 {
1076 $attrs['objectClass'] = "gotoSubmenuEntry";
1077 $attrs['cn'] = $entry['NAME'];
1078 $attrs['gosaApplicationPriority'] = $prio;
1079 if($entry['STATUS'] != "ADDED"){
1080 $attrs['gosaApplicationIcon'] = array();
1081 }
1083 if(!empty($entry['ICON'])){
1084 $attrs['gosaApplicationIcon'] = $entry['ICON'];
1085 }
1086 }
1087 break;
1088 case "RELEASE" :
1089 {
1090 $attrs['ou'] = $entry['NAME'];
1091 $attrs['objectClass'] = array();
1092 $attrs['objectClass'][] = "top";
1093 $attrs['objectClass'][] = "organizationalUnit";
1094 $attrs['objectClass'][] = "FAIbranch";
1095 if(!empty($entry['FAIstate'])){
1096 $attrs['FAIstate'] = $entry['FAIstate'];
1097 }
1098 }
1099 break;
1100 }
1102 if($entry['STATUS'] == "LOADED"){
1103 continue;
1104 }
1105 if($entry['STATUS'] == "REMOVED"){
1106 $Actions['Remove'][$entry['DN']] = $entry['DN'];
1107 }
1108 if($entry['STATUS'] == "EDITED"){
1109 $Actions['Edit'][$cur_dn] = $attrs;
1110 }
1111 if($entry['STATUS'] == "ADDED"){
1112 $Actions['Add'][$cur_dn] = $attrs;
1113 }
1114 }
1116 $ldap = $this->config->get_ldap_link();
1117 $ldap->cd($this->config->current['BASE']);
1118 foreach($Actions['Remove'] as $dn){
1119 $ldap->cd($dn);
1120 $ldap->cat($dn);
1121 if($ldap->count()){
1122 $ldap->rmdir_recursive($dn);
1123 if (!$ldap->success()){
1124 msg_dialog::display(_("LDAP error"), msgPool::ldaperror($ldap->get_error(), $dn, LDAP_DEL, get_class()));
1125 }
1126 }
1127 }
1128 foreach($Actions['Add'] as $dn => $data){
1129 $ldap->cd($dn);
1130 $ldap->cat($dn);
1131 if(!$ldap->count()){
1132 $ldap->add($data);
1133 if (!$ldap->success()){
1134 msg_dialog::display(_("LDAP error"), msgPool::ldaperror($ldap->get_error(), $dn, LDAP_DEL, get_class()));
1135 }
1136 }
1137 }
1138 foreach($Actions['Edit'] as $dn => $data){
1139 $ldap->cd($dn);
1140 $ldap->cat($dn);
1141 if($ldap->count()){
1142 $ldap->modify($data);
1143 if (!$ldap->success()){
1144 msg_dialog::display(_("LDAP error"), msgPool::ldaperror($ldap->get_error(), $dn, LDAP_DEL, get_class()));
1145 }
1146 }
1147 }
1149 $this->_load_menu_structure();
1150 }
1153 /* Return plugin informations for acl handling */
1154 static function plInfo()
1155 {
1156 return (array(
1157 "plShortName" => _("Applications"),
1158 "plDescription" => _("Group applications"),
1159 "plSelfModify" => FALSE,
1160 "plDepends" => array(),
1161 "plPriority" => 0,
1162 "plSection" => array("admin"),
1163 "plCategory" => array("groups"),
1164 "plProvidedAcls"=> array(
1165 "gosaMemberApplication" => _("Application"),
1166 "FAIrelease" => _("Release"),
1167 "gosaApplicationParameter" => _("Application parameter"))
1168 ));
1169 }
1172 function PrepareForCopyPaste($source)
1173 {
1174 }
1177 function multiple_save_object()
1178 {
1179 if(isset($_POST['group_apps_multi'])){
1180 $this->save_object();
1181 plugin::multiple_save_object();
1183 /* Get posts */
1184 foreach(array("apps") as $attr){
1185 if(isset($_POST['use_'.$attr])) {
1186 $this->multi_boxes[] = $attr;
1187 }
1188 }
1189 }
1190 }
1193 function get_multi_edit_values()
1194 {
1195 $ret = plugin::get_multi_edit_values();
1197 if(in_array("apps",$this->multi_boxes)){
1198 $ret['gosaApplicationParameter'] = $this->gosaApplicationParameter;
1199 $ret['Categories'] = $this->Categories;
1200 $ret['gosaMemberApplication'] = $this->gosaMemberApplication;
1201 $ret['FAIrelease'] = $this->FAIrelease;
1202 $ret['appoption'] = $this->appoption;
1203 }
1204 return($ret);
1205 }
1206 }
1207 // vim:tabstop=2:expandtab:shiftwidth=2:filetype=php:syntax:ruler:
1208 ?>