Code

Added member info to group mail
[gosa.git] / gosa-plugins / mail / admin / groups / mail / class_groupMail.inc
1 <?php
3 class mailgroup extends plugin
4 {
5   /* Multiple edit */
6   var $gosaMailForwardingAddress_Some  = array();  // Used in multiple edit 
8   /* Default values */
9   var $mail                       = "";           // Default mail address 
10   var $gosaMailAlternateAddress   = array();  // Set default Alternate Mail Adresses to empty array
11   var $gosaMailForwardingAddress  = array();  // Forwarding also empty
12   var $gosaMailServer             = "";       // Selected mailserver 
13   var $gosaMailQuota              = "";       // Defined Quota 
14   var $gosaVacationMessage        = "";       // Vocation message 
15   var $gosaSpamSortLevel          = "";     
16   var $gosaSpamMailbox            = "";
17   var $gosaSharedFolderTarget     ;
18   var $gosaMailDeliveryMode       = "[L        ]";   // 
19   var $gosaMailMaxSize            = "";       // 
20   var $FolderType                 = array("CAT" => '', "SUB_CAT" => '');
22   var $quotaUsage                 = -1;        // -1 Means undefined
24   /* Internal */
25   var $AclTypes                   = array();
26   var $members                    = array();  // Group members
27   var $mailusers                  = array();  // Group member with mail account
28   var $folder_acls                = array();
29   var $MailMethod = NULL; 
30   var $forward_dialog             = FALSE;    
31   var $remove_folder_from_imap    = true;
32   var $view_logged                = FALSE;
33   var $mailDomainPart             = "";
35   /* attribute list for save action */
36   var $attributes= array( "mail",   "gosaMailServer", "gosaMailQuota", "gosaMailMaxSize",
37       "gosaMailAlternateAddress", "gosaMailForwardingAddress",
38       "gosaMailDeliveryMode", "gosaSpamSortLevel", "gosaSpamMailbox",
39       "acl","gosaSharedFolderTarget", "gosaVacationMessage");
41   var $objectclasses= array("gosaMailAccount");
42   var $multiple_support = FALSE; // Not tested yet
44   var $uid = "";
45   var $cn ="";
46   var $orig_cn = "";
47   var $show_effective_memeber = FALSE;
49   function __construct (&$config, $dn= NULL, $ui= NULL)
50   {
51     plugin::plugin($config, $dn);
53     /* Get attributes from parent object
54      */
55     foreach(array("uid","cn") as $attr){
56       if(isset($this->parent->by_object['group']) && isset($this->parent->by_object['group']->$attr)){
57         $this->$attr = &$this->parent->by_object['group']->$attr;
58       }elseif(isset($this->attrs[$attr])){
59         $this->$attr = $this->attrs[$attr][0];
60       }
61     }
62     $this->orig_cn = $this->cn;
64     /* Intialize the used mailMethod
65      */
66     $tmp = new mailMethod($config,$this,"group");
67     $this->mailMethod           = $tmp->get_method();
68     $this->mailMethod->fixAttributesOnLoad();
69     $this->mailDomainParts      = $this->mailMethod->getMailDomains();
70     $this->AvailableFolderTypes = $this->mailMethod->getAvailableFolderTypes();
71     $this->MailBoxes = array();
73     /* Remember account status
74      */
75     $this->initially_was_account = $this->is_account;
77     /* Load folder_acls with defaults.
78       anyone -- The default acl, will be written to ldap.
79       member -- The ACL used for the members.
80      */ 
81     $this->folder_acls = $this->mailMethod->getDefaultACLs();
83     /* Load acls
84        The most used acl will be used as member acl, this
85         shortens the listed acls.        
86        This may be merged/overwritten by the mail methods.
87      */
88     $ldap = $this->config->get_ldap_link();
89     if(isset($this->attrs['acl'])){
90       for($i = 0; $i < $this->attrs['acl']['count'] ; $i++){
91         $str = trim($this->attrs['acl'][$i]);
93         /* Be carefull here, since kolab22 uses spaces in the acls (herbert read anon/post)
94          */
95         $name = trim(preg_replace("/^([^\s]*).*$/","\\1",$str));
96         $acl  = trim(preg_replace("/^[^\s]*+\s/","",$str));
97         if($name == "anyone") $name = "__anyone__";
98         $this->folder_acls[$name] = $acl;
99       }
100     }
102     /* Initialize configured values
103      */
104     if($this->is_account){
105       if($this->mailMethod->connect() && $this->mailMethod->account_exists()){
107         /* Read quota */
108         $this->gosaMailQuota = $this->mailMethod->getQuota($this->gosaMailQuota);
109         $this->quotaUsage = $this->mailMethod->getQuotaUsage($this->quotaUsage);
110         if($this->mailMethod->is_error()){
111           msg_dialog::display(_("Mail error"), sprintf(_("Cannot read quota settings: %s"),
112                 $this->mailMethod->get_error()), ERROR_DIALOG);
113         }
115         /* Read mailboxes */
116         $this->MailBoxes = $this->mailMethod->getMailboxList($this->MailBoxes);
117         if($this->mailMethod->is_error()){
118           msg_dialog::display(_("Mail error"), sprintf(_("Cannot get list of mailboxes: %s"),
119                 $this->mailMethod->get_error()), ERROR_DIALOG);
120         }
122         /* Receive folder types */
123         $this->FolderType = $this->mailMethod->getFolderType($this->FolderType);
124         if($this->mailMethod->is_error()){
125           msg_dialog::display(_("Mail error"), sprintf(_("Cannot receive folder types: %s"),
126                 $this->mailMethod->get_error()), ERROR_DIALOG);
127         }
129         /* Receive permissions */  
130         $this->folder_acls = $this->mailMethod->getFolderACLs($this->folder_acls);
131         if($this->mailMethod->is_error()){
132           msg_dialog::display(_("Mail error"), sprintf(_("Cannot receive folder permissions: %s"),
133                 $this->mailMethod->get_error()), ERROR_DIALOG);
134         }
136       }elseif(!$this->mailMethod->is_connected()){
137         msg_dialog::display(_("Mail error"), sprintf(_("Mail method cannot connect: %s"),
138               $this->mailMethod->get_error()), ERROR_DIALOG);
139       }elseif(!$this->mailMethod->account_exists()){
140         msg_dialog::display(_("Mail error"), sprintf(_("Mailbox '%s' doesn't exists on mail server: %s"),
141               $this->mailMethod->get_account_id(),$this->gosaMailServer), ERROR_DIALOG);
142       }
144       /* If the doamin part is selectable, we have to split the mail address
145        */
146       if(!(!$this->mailMethod->isModifyableMail() && $this->is_account)){
147         if($this->mailMethod->domainSelectionEnabled() || $this->mailMethod->mailEqualsCN()){
148           $this->mailDomainPart = preg_replace("/^[^@]*+@/","",$this->mail);
149           $this->mail = preg_replace("/@.*$/","\\1",$this->mail);
150           if(!in_array($this->mailDomainPart,$this->mailDomainParts)){
151             $this->mailDomainParts[] = $this->mailDomainPart;
152           }
153         }
154       }
156       /* Load attributes containing arrays */
157       foreach (array("gosaMailAlternateAddress", "gosaMailForwardingAddress") as $val){
158         $this->$val= array();
159         if (isset($this->attrs["$val"]["count"])){
160           for ($i= 0; $i<$this->attrs["$val"]["count"]; $i++){
161             array_push($this->$val, $this->attrs["$val"][$i]);
162           }
163         }
164       }
165     }
167     /* Disconnect mailMethod. Connect on demand later.
168      */
169     $this->mailMethod->disconnect();
170     $this->AclTypes = $this->mailMethod->getAclTypes();
172     /* Summarize most used ACLs as member acl 
173      */
174     if(count($this->folder_acls) > 2){
175       $acl_usage = array();
176       $most_acl = $this->folder_acls['__member__'];
177       $most_cnt = 0;
178       $member = $this->get_member();
179       foreach($this->folder_acls as $user => $acl){
180         if(preg_match("/^__/",$user)) continue;
181         if(!in_array($user,$member['mail'])) continue; 
182         if(!isset($acl_usage[$acl])) $acl_usage[$acl]=0;
183         $acl_usage[$acl] ++;
184         if($acl_usage[$acl] > $most_cnt){
185           $most_cnt = $acl_usage[$acl];
186           $most_acl = $acl;
187         }
188       }
189       $this->folder_acls['__member__'] = $most_acl;  
190       foreach($this->folder_acls as $name => $acl){
191         if(preg_match("/^__/",$name)) continue;
192         if($acl == $most_acl && in_array($name,$member['mail'])){
193           unset($this->folder_acls[$name]);
194         }
195       }
196     }
198     /* Get global filter config */
199     if (!session::is_set("gmailfilter")){
200       $ui= get_userinfo();
201       $base= get_base_from_people($ui->dn);
202       $gmailfilter= array( "depselect"       => $base,
203           "muser"            => "",
204           "regex"           => "*");
205       session::set("gmailfilter", $gmailfilter);
206     }
207   }
209  
210   /*! \brief  Returns all group members once with 'dn' and once with 'mail'.
211               This function is used to summarize ACLs by member acls.
212       @return Array   Containing all members, with mail and dn
213    */ 
214   function get_member()
215   {
216     $member = array('all' => array(), 'mail' => array());
217     $ldap = $this->config->get_ldap_link();
218     $ldap->cd($this->config->current['BASE']);
219     if(isset($this->parent->by_object['group'])){
220       foreach($this->parent->by_object['group']->memberUid as $uid){
221         $dn = $this->parent->by_object['group']->dnMapping[$uid];
222         $member['all'][$uid] = $uid;
223         if($ldap->object_match_filter($dn,"(&(objectClass=gosaMailAccount)(".$this->mailMethod->getUAttrib()."=*))")){
224           $ldap->cat($dn);
225           $attrs = $ldap->fetch();
226           $member['mail'][$uid] = $attrs[$this->mailMethod->getUAttrib()][0]; 
227         }
228       }
229     }else{
230       if(!isset($this->attrs['memberUid'])) return($member);
231       $uattrib = $this->mailMethod->getUAttrib();
232       $users = get_list("(&(objectClass=person)(objectClass=gosaAccount)(uid=*))",
233               "users",$this->config->current['BASE'],
234               array("uid","objectClass",$uattrib),GL_SUBSEARCH | GL_NO_ACL_CHECK);
235       foreach($users as $user){
236         $member['all'][$user['uid'][0]] = $user['dn'];
237         if(isset($user[$uattrib]) 
238             && in_array("gosaMailAccount",$user['objectClass']) 
239             && (in_array($user['uid'][0], $this->attrs['memberUid']))){
240           $member['mail'][$user['uid'][0]] = $user[$uattrib][0];
241         }
242       }
243     }
244     return($member);
245   }
248   function execute()
249   {
250     /* Call parent execute */
251     plugin::execute();
253     /* Log view */
254     if($this->is_account && !$this->view_logged){
255       $this->view_logged = TRUE;
256       new log("view","groups/".get_class($this),$this->dn);
257     }
258  
259     /****************
260       Account status
261      ****************/
263     if(!$this->multiple_support_active){
265       if(isset($_POST['modify_state'])){
266         if($this->is_account && $this->acl_is_removeable() && $this->mailMethod->accountRemoveAble()){
267           $this->is_account= FALSE;
268         }elseif(!$this->is_account && $this->acl_is_createable() && $this->mailMethod->accountCreateable()){
269           $this->is_account= TRUE;
270         }
271       }
273       if ($this->is_account){
274         $reason = "";
275         if(!$this->mailMethod->accountRemoveable($reason)){
276           $display= $this->show_disable_header(msgPool::removeFeaturesButton(_("Mail")),$reason ,TRUE,TRUE);
277         }else{
278           $display= $this->show_disable_header(msgPool::removeFeaturesButton(_("Mail")),msgPool::
279               featuresEnabled(_("Mail")));
280         }
281       } else {
282         $reason = "";
283         if(!$this->mailMethod->accountCreateable($reason)){
284           $display= $this->show_disable_header(msgPool::addFeaturesButton(_("Mail")),$reason ,TRUE,TRUE);
285         }else{
286           $display= $this->show_disable_header(msgPool::addFeaturesButton(_("Mail")),msgPool::
287               featuresDisabled(_("Mail")));
289           /* Show checkbox that allows us to remove imap entry too*/
290           if($this->initially_was_account){
291             $c = "";
292             if($this->remove_folder_from_imap){
293               $c= " checked ";
294             }
295             $display .= "<h2>Shared folder delete options</h2>
296               <input class='center' type='checkbox' name='remove_folder_from_imap' value='1' ".$c."
297               title='"._("Remove shared folder from mail server database when entry gets removed in LDAP")."'>";
298             $display .= _("Remove the shared folder and all its contents after saving this account");
299           }
300         }
301         return ($display);
302       }
303     }
305     
306     /****************
307       Preset mail attribute
308      ****************/
309     if(empty($this->mail) && $this->mailMethod->mailEqualsCN() && !$this->initially_was_account){
310       if($this->mailMethod->domainSelectionEnabled()){
311         $this->mail = &$this->parent->by_object['group']->cn;
312       }
313     }
316     /****************
317       Forward addresses
318      ****************/
319     if (isset($_POST['add_local_forwarder'])){
320       $this->forward_dialog= TRUE;
321       $this->dialog= TRUE;
322     }
323     if (isset($_POST['add_locals_cancel'])){
324       $this->forward_dialog= FALSE;
325       $this->dialog= FALSE;
326     }
327     if (isset($_POST['add_locals_finish'])){
328       if (isset($_POST['local_list'])){
329         if($this->acl_is_writeable("gosaMailForwardingAddress")){
330           foreach ($_POST['local_list'] as $val){
331             if (!in_array ($val, $this->gosaMailAlternateAddress) &&
332                 $val != $this->mail){
333               $this->addForwarder($val);
334               $this->is_modified= TRUE;
335             }
336           }
337         }
338         $this->forward_dialog= FALSE;
339         $this->dialog= FALSE;
340       } else {
341         msg_dialog::display(_("Error"), _("Please select an entry!"), ERROR_DIALOG);
342       }
343     }
345     if (isset($_POST['add_forwarder'])){
346       if ($_POST['forward_address'] != ""){
347         $address= $_POST['forward_address'];
348         $valid= FALSE;
349         if (!tests::is_email($address)){
350           if (!tests::is_email($address, TRUE)){
351             if ($this->is_template){
352               $valid= TRUE;
353             } else {
354               msg_dialog::display(_("Error"), msgPool::invalid(_("Mail address"),
355                     "","","your-address@your-domain.com"),ERROR_DIALOG);
356             }
357           }
358         } elseif ($address == $this->mail
359             || in_array($address, $this->gosaMailAlternateAddress)) {
360           msg_dialog::display(_("Error"),_("Cannot add primary address to the list of forwarders!") , ERROR_DIALOG);
361         } else {
362           $valid= TRUE;
363         }
364         if ($valid){
365           if($this->acl_is_writeable("gosaMailForwardingAddress")){
366             $this->addForwarder ($address);
367             $this->is_modified= TRUE;
368           }
369         }
370       }
371     }
372     if (isset($_POST['delete_forwarder'])){
373       $this->delForwarder ($_POST['forwarder_list']);
374     }
375     if ($this->forward_dialog){
376       return($this->display_forward_dialog());
377     } 
379  
380     /****************
381       Alternate addresses
382      ****************/
384     if (isset($_POST['add_alternate'])){
385       $valid= FALSE;
386       if (!tests::is_email($_POST['alternate_address'])){
387         if ($this->is_template){
388           if (!(tests::is_email($_POST['alternate_address'], TRUE))){
389             msg_dialog::display(_("Error"),msgPool::invalid(_("Mail address"),
390                   "","","your-domain@your-domain.com"),     ERROR_DIALOG);
391           } else {
392             $valid= TRUE;
393           }
394         } else {
395           msg_dialog::display(_("Error"),msgPool::invalid(_("Mail address"),
396                 "","","your-domain@your-domain.com"),       ERROR_DIALOG);
397         }
398       } else {
399         $valid= TRUE;
400       }
401       if ($valid && ($user= $this->addAlternate ($_POST['alternate_address'])) != ""){
402         $ui= get_userinfo();
403         if ($user != $ui->username){
404           msg_dialog::display(_("Error"), msgPool::duplicated(_("Mail address"))."&nbsp;".
405               sprintf(_("Address is already in use by user '%s'."), $user), ERROR_DIALOG);
406         }
407       }
408     }
409     if (isset($_POST['delete_alternate']) && isset($_POST['alternates_list'])){
410       $this->delAlternate ($_POST['alternates_list']);
411     }
414     /****************
415       SMARTY- Assign smarty variables
416      ****************/
418     /* Load templating engine */
419     $smarty= get_smarty();
420     $smarty->assign("initially_was_account", $this->initially_was_account);
421     $smarty->assign("isModifyableMail", $this->mailMethod->isModifyableMail());
422     $smarty->assign("isModifyableServer", $this->mailMethod->isModifyableServer());
423     $smarty->assign("mailEqualsCN", $this->mailMethod->mailEqualsCN());
424     $smarty->assign("folder_acls" , $this->postable_acls());
425     $smarty->assign("AclTypes" ,    $this->AclTypes);
426     $smarty->assign("Effective",    $this->get_effective_member_acls());
427     $smarty->assign("show_effective_memeber",    $this->show_effective_memeber);
428   
429     $smarty->assign("quotaEnabled", $this->mailMethod->quotaEnabled());
430     if($this->mailMethod->quotaEnabled()){
431       $smarty->assign("gosaMailQuota",$this->gosaMailQuota);
432       $smarty->assign("quotaUsage",   mailMethod::quota_to_image($this->quotaUsage,$this->gosaMailQuota)); 
433     }
435     $smarty->assign("MailDomains", $this->mailDomainParts);
436     $smarty->assign("MailDomain" , $this->mailDomainPart);
437     $smarty->assign("MailServers", $this->mailMethod->getMailServers());
438     $smarty->assign("allowSieveManagement", $this->mailMethod->allowSieveManagement());
440     $smarty->assign("domainSelectionEnabled", $this->mailMethod->domainSelectionEnabled());
441     $smarty->assign("folderTypesEnabled",$this->mailMethod->folderTypesEnabled());
442     $smarty->assign("AvailableFolderTypes", $this->AvailableFolderTypes);
443     $smarty->assign("FolderType", $this->FolderType);
444  
445     if (is_numeric($this->gosaMailQuota) && $this->gosaMailQuota != 0){
446       if($this->acl_is_readable("gosaMailQuota")){
447         $smarty->assign("quotausage", progressbar(round(($this->quotaUsage * 100)/ $this->gosaMailQuota),100,15,true));
448         $smarty->assign("quotadefined", "true");
449       }else{
450         $smarty->assign("quotadefined", "true");
451         $smarty->assign("quotausage", "-");
452       }
453     } else {
454       $smarty->assign("quotadefined", "false");
455     }
457     /* Assign acls */
458     $tmp = $this->plInfo();
459     foreach($tmp['plProvidedAcls'] as $name => $translation) {
460       $smarty->assign($name."ACL",$this->getacl($name));
461     }
462     foreach($this->attributes as $name){
463       $smarty->assign($name,$this->$name);
464     }
468     $smarty->assign("mailServers", $this->mailMethod->getMailServers());
469     if (preg_match("/I/", $this->gosaMailDeliveryMode)) {
470       $smarty->assign("only_local", "checked");
471     }else{
472       $smarty->assign("only_local", "");
473     }
476     /******
477       Multi edit support 
478      ******/
479     foreach($this->attributes as $attr){
480       if(in_array($attr,$this->multi_boxes)){
481         $smarty->assign("use_".$attr,TRUE);
482       }else{
483         $smarty->assign("use_".$attr,FALSE);
484       }
485     }
487     /* Multiple support handling */
488     foreach(array("kolabFolderType") as $attr){
489       if(in_array($attr,$this->multi_boxes)){
490         $smarty->assign("use_".$attr,TRUE);
491       }else{
492         $smarty->assign("use_".$attr,FALSE);
493       }
494     }
496     $smarty->assign("Forward_all",$this->gosaMailForwardingAddress);
497     $smarty->assign("Forward_some",$this->gosaMailForwardingAddress_Some);
498     $smarty->assign("multiple_support",$this->multiple_support_active);
500     $display.= $smarty->fetch (get_template_path('mail.tpl', TRUE, dirname(__FILE__)));
501     return ($display);
502   }
505   /* remove object from parent */
506   function remove_from_parent()
507   {
508     if(!$this->initially_was_account){
509       return;
510     }
511  
512     /* If domain part was selectable, contruct mail address */
513     if($this->mailMethod->domainSelectionEnabled() || $this->mailMethod->mailEqualsCN()){
514       $this->mail = $this->mail."@".$this->mailDomainPart;
515     }
517     /* Remove GOsa attributes */
518     plugin::remove_from_parent();
520     /* Zero arrays */
521     $this->attrs['gosaMailAlternateAddress'] = array();
522     $this->attrs['gosaMailForwardingAddress']= array();
523     $this->attrs['gosaSharedFolderTarget']= array();
525     $this->mailMethod->fixAttributesOnRemove();
526     $this->cleanup();
527     $ldap = $this->config->get_ldap_link();
528     $ldap->cd($this->dn);
529     $ldap->modify ($this->attrs); 
530     if (!$ldap->success()){
531       msg_dialog::display(_("LDAP error"), msgPool::ldaperror($ldap->get_error(), $this->dn, LDAP_MOD, get_class()));
532     }
534     new log("remove","groups/".get_class($this),$this->dn,array_keys($this->attrs),$ldap->get_error());
537     /* Let the mailMethod remove this mailbox, e.g. from imap and
538        update shared folder membership, ACL may need to be updated.
539      */
540     if (!$this->is_template && $this->remove_folder_from_imap){
542       if(!$this->mailMethod->connect()){
543         msg_dialog::display(_("Mail error"), sprintf(_("Mail method cannot connect: %s"),
544               $this->mailMethod->get_error()), ERROR_DIALOG);
545       }else{
546         if(!$this->mailMethod->deleteMailbox()){
547           msg_dialog::display(_("Mail error"), sprintf(_("Cannot remove mailbox: %s"),
548                 $this->mailMethod->get_error()), ERROR_DIALOG);
549         }
550         if(!$this->mailMethod->updateSharedFolder()){
551           msg_dialog::display(_("Mail error"), sprintf(_("Cannot update shared folder permissions: %s"),
552                 $this->mailMethod->get_error()), ERROR_DIALOG);
553         }
554       }
555     }
556     $this->mailMethod->disconnect();
559     /* Optionally execute a command after we're done */
560     $this->handle_post_events("remove");
561   }
564   /* Save data to object */
565   function save_object()
566   {
567     /* Check if user wants to remove the shared folder from imap too 
568      */
569     if($this->initially_was_account && !$this->is_account){
570       if(isset($_POST['remove_folder_from_imap'])){
571         $this->remove_folder_from_imap = true;
572       }else{
573         $this->remove_folder_from_imap = false;
574       }
575     }
576     if (isset($_POST['mailedit'])){
578       if(isset($_POST['show_effective_memeber'])){
579         $this->show_effective_memeber = !$this->show_effective_memeber;
580       }
582       $mail = $this->mail;
583       $server = $this->gosaMailServer;
584       plugin::save_object();
586       if(!$this->mailMethod->isModifyableServer() && $this->initially_was_account){
587         $this->gosaMailServer = $server;
588       }
589       if(!$this->mailMethod->isModifyableMail() && $this->initially_was_account){
590         $this->mail = $mail;
591       }else{
593         if($this->mailMethod->mailEqualsCN()){
594           $this->mail = &$this->parent->by_object['group']->cn;
595           if(isset($_POST['MailDomain'])){
596             $this->mailDomainPart = get_post('MailDomain');
597           }
598         }
600       /* Get posted mail domain part, if necessary
601        */
602       if($this->mailMethod->domainSelectionEnabled() && isset($_POST['MailDomain'])){
603         if(in_array(get_post('MailDomain'), $this->mailDomainParts)){
604           $this->mailDomainPart = get_post('MailDomain');
605         }
606       }
607     }
609       /* Get folder type 
610        */
611       if($this->mailMethod->folderTypesEnabled()){
612         if(isset($_POST['FolderTypeCAT'])){
613         $this->FolderType['CAT']     = get_post('FolderTypeCAT');
614         }
615         if(isset($_POST['FolderTypeSUB_CAT'])){
616           $this->FolderType['SUB_CAT'] = get_post('FolderTypeSUB_CAT');
617         }
618       }
620       /* Handle posted ACL changes. 
621          Add/del member acls.
622        */
623       if(isset($_POST['mail_acls_posted'])){
624         $new_acls = array();
625         foreach(array("__anyone__","__member__") as $attr){
626           $pname = base64_encode($attr);
627           if(get_post('acl_value_'.$pname)){ 
628             $new_acls[$attr] = get_post('acl_value_'.$pname);
629           }else{
630             $new_acls[$attr] = $this->folder_acls[$attr];
631           }
632         }
634         foreach($this->folder_acls as $user => $acl){
635           $pname = base64_encode($user);
636           if($user == "__member__" || $user == "__anyone__") continue;
637           if(isset($_POST['remove_acl_user_'.$pname])){
638           }elseif(isset($_POST['acl_user_'.$pname])){
639             if($user != get_post('acl_user_'.$pname)){
640               $new_acls[get_post('acl_user_'.$pname)] = get_post('acl_value_'.$pname);
641             }else{
642               $new_acls[$user] = get_post('acl_value_'.$pname);
643             }
644           }else{
645             $new_acls[$user] = $acl;
646           }
647         }
648         if(isset($_POST['add_acl_user'])){
649           $new_acls[_('New')] = $this->folder_acls['__anyone__'];
650         }
651         $this->folder_acls = $new_acls;
652       }
654       /* Handle GOsa mail delivery flags.
655        */
657     /* Assemble mail delivery mode
658        The mode field in ldap consists of values between braces, this must
659        be called when 'mail' is set, because checkboxes may not be set when
660        we're in some other dialog.
662        Example for gosaMailDeliveryMode [LR        ]
663        L - Local delivery
664        R - Reject when exceeding mailsize limit
665        S - Use spam filter
666        V - Use vacation message
667        C - Use custom sieve script
668        I - Only insider delivery */
669       $tmp= preg_replace("/[^a-z]/i","",$this->gosaMailDeliveryMode);
670       if($this->acl_is_writeable("gosaMailDeliveryModeL")){
671         if(!preg_match("/L/",$tmp) && !isset($_POST['drop_own_mails'])){
672           $tmp.="L";
673         }elseif(preg_match("/L/",$tmp) && isset($_POST['drop_own_mails'])){
674           $tmp = preg_replace("/L/","",$tmp);
675         }
676       }
678       $opts = array(
679           "R"   => "use_mailsize_limit",
680           "S"   => "use_spam_filter",
681           "V"   => "use_vacation",
682           "C"   => "own_script",
683           "I"   => "only_local");
685       foreach($opts as $flag => $post){
686         if($this->acl_is_writeable("gosaMailDeliveryMode".$flag)){
687           if(!preg_match("/".$flag."/",$tmp) && isset($_POST[$post])){
688             $tmp.= $flag;
689           }elseif(preg_match("/".$flag."/",$tmp) && !isset($_POST[$post])){
690             $tmp = preg_replace("/".$flag."/","",$tmp);
691           }
692         }
693       }
695       $tmp= "[$tmp]";
696       if ($this->gosaMailDeliveryMode != $tmp){
697         $this->is_modified= TRUE;
698       }
699       $this->gosaMailDeliveryMode= $tmp;
700     }
701   }
704   /* Save data to LDAP, depending on is_account we save or delete */
705   function save()
706   {
707     $ldap= $this->config->get_ldap_link();
709     /* If domain part was selectable, contruct mail address */
710     if(!(!$this->mailMethod->isModifyableMail() && $this->initially_was_account)){
712       if($this->mailMethod->domainSelectionEnabled() || $this->mailMethod->mailEqualsCN()){
713         $this->mail = $this->mail."@".$this->mailDomainPart;
714       }
715     }
717     /* Enforce lowercase mail address and trim whitespaces
718      */
719     $this->mail = trim(strtolower($this->mail));
720     
722     /* Create acls 
723      */
724     $this->acl = array("anyone ".$this->folder_acls['__anyone__']);
725     $member = $this->get_member();
726     $new_folder_acls = array("anyone" => $this->folder_acls['__anyone__']);
727     foreach($member['mail'] as $uid => $mail){
729       /* Do not save overridden acls */
730       if(isset($this->folder_acls[$mail])){
731         continue;
732       }
734       $this->acl[] = $mail." ".$this->folder_acls['__member__'];
735       $new_folder_acls[$mail]=$this->folder_acls['__member__'];
736     }
737     foreach($this->folder_acls as $user => $acls){
738       if(preg_match("/^__/",$user)) continue;
739       $this->acl[] = $user." ".$acls;
740       $new_folder_acls[$user]=$acls;
741     }
742     $this->folder_acls = $new_folder_acls;
743     $this->acl = array_unique($this->acl);
744      
745     /* Call parents save to prepare $this->attrs */
746     plugin::save();
748     /* Save arrays */
749     $this->attrs['gosaMailAlternateAddress'] = $this->gosaMailAlternateAddress;
750     $this->attrs['gosaMailForwardingAddress']= $this->gosaMailForwardingAddress;
752     /* Map method attributes */
753     $this->mailMethod->fixAttributesOnStore();
755     /* Save data to LDAP */
756     $ldap->cd($this->dn);
757     $this->cleanup();
758     $ldap->modify ($this->attrs); 
759     if (!$ldap->success()){
760       msg_dialog::display(_("LDAP error"), msgPool::ldaperror($ldap->get_error(), $this->dn, LDAP_MOD, get_class()));
761     }
762     
763     if($this->initially_was_account){
764       new log("modify","groups/".get_class($this),$this->dn,array_keys($this->attrs),$ldap->get_error());
765     }else{
766       new log("create","groups/".get_class($this),$this->dn,array_keys($this->attrs),$ldap->get_error());  
767     }
768     
769     /* Do imap/sieve actions,
770      */
771     $this->mailMethod->connect();
772     if(!$this->mailMethod->is_connected()){
773       msg_dialog::display(_("Mail error"), sprintf(_("Mail method cannot connect: %s"),
774             $this->mailMethod->get_error()), ERROR_DIALOG);
775     }else{
776       if(!$this->mailMethod->updateMailbox()){
777         msg_dialog::display(_("Mail error"), sprintf(_("Cannot update mailbox: %s"),
778               $this->mailMethod->get_error()), ERROR_DIALOG);
779       }
780       if(!$this->mailMethod->setQuota($this->gosaMailQuota)){
781         msg_dialog::display(_("Mail error"), sprintf(_("Cannot write quota settings: %s"),
782               $this->mailMethod->get_error()), ERROR_DIALOG);
783       }
784       /* Save Folder Types, if available 
785        */
786       if($this->mailMethod->folderTypesEnabled()){
787         $this->mailMethod->setFolderType($this->FolderType);
788       }
789       if(!$this->mailMethod->setFolderACLs($this->folder_acls)){
790         msg_dialog::display(_("Mail error"), sprintf(_("Cannot update shared folder permissions: %s"),
791               $this->mailMethod->get_error()), ERROR_DIALOG);
792       }
793     }
794     $this->mailMethod->disconnect();
796     /* Optionally execute a command after we're done */
797     if ($this->initially_was_account == $this->is_account){
798       if ($this->is_modified){
799         $this->handle_post_events("modify");
800       }
801     } else {
802       $this->handle_post_events("add");
803     }
804   }
808   /* Check formular input */
809   function check()
810   {
811     if(!$this->is_account) return array();
812     $ldap= $this->config->get_ldap_link();
815     /* Call common method to give check the hook */
816     $message= plugin::check();
818     /* Ensure that this group isn't renamed if the mailMethod enforces cn mailAttributes 
819      */
820     if($this->mailMethod->mailEqualsCN() && $this->initially_was_account){
821       if($this->cn != $this->orig_cn){
822         $message[] = sprintf(_("The groups 'cn' has changed!  The cn attribute can't be changed due to the fact that this mail method '%s' relies on it.")
823             ,get_class($this->mailMethod));
824       }
825     }
827     if(empty($this->gosaMailServer)){
828       $message[]= msgPool::noserver(_("Mail"));
829     }
831     /* Mail address checks */
832     if(!(!$this->mailMethod->isModifyableMail() && $this->initially_was_account)){
833       $mail = $this->mail;
834       if($this->mailMethod->domainSelectionEnabled() || $this->mailMethod->mailEqualsCN()){
835         $mail.= "@".$this->mailDomainPart;
836       }
837       if (empty($mail)){
838         $message[]= msgPool::required(_("Primary address"));
839       }elseif (!tests::is_email($mail)){
840         $message[]= msgPool::invalid(_("Mail address"),"","","your-address@your-domain.com");
841       }
842     }
843     
844     /* Check quota */
845     if ($this->gosaMailQuota != '' && $this->acl_is_writeable("gosaMailQuota")){
846       if (!is_numeric($this->gosaMailQuota)) {
847         $message[]= msgPool::invalid(_("Quota size"),$this->gosaMailQuota,"/[0-9]/");
848       } else {
849         $this->gosaMailQuota= (int) $this->gosaMailQuota;
850       }
851     }
853     /* Check rejectsize for integer */
854     if ($this->gosaMailMaxSize != '' && $this->acl_is_writeable("gosaMailQuota")){
855       if (!is_numeric($this->gosaMailMaxSize)){
856         $message[]= msgPool::invalid(_("Mail max size"));
857       } else {
858         $this->gosaMailMaxSize= (int) $this->gosaMailMaxSize;
859       }
860     }
862     /* Need gosaMailMaxSize if use_mailsize_limit is checked */
863     if (is_integer(strpos($this->gosaMailDeliveryMode, "reject")) && $this->gosaMailMaxSize == ""){
864       $message[]= _("You need to set the maximum mail size in order to reject anything.");
865     }
867     if(empty($this->gosaMailServer)){
868       $message[] = msgPool::required(_("Mail server"));
869     }
871     return ($message);
872   }
874   /* Adapt from template, using 'dn' */
875   function adapt_from_template($dn, $skip= array())
876   {
877     plugin::adapt_from_template($dn, $skip);
879     foreach (array("gosaMailAlternateAddress", "gosaMailForwardingAddress") as $val){
880  
881       if (in_array($val, $skip)){
882         continue;
883       }
885       $this->$val= array();
886       if (isset($this->attrs["$val"]["count"])){
887         for ($i= 0; $i<$this->attrs["$val"]["count"]; $i++){
888           $value= $this->attrs["$val"][$i];
889           foreach (array("sn", "givenName", "uid") as $repl){
890             if (preg_match("/%$repl/i", $value)){
891               $value= preg_replace ("/%$repl/i", $this->parent->$repl, $value);
892             }
893           }
894           array_push($this->$val, $value);
895         }
896       }
897     }
898   }
902   function make_name($attrs)
903   {
904     $name= "";
905     if (isset($attrs['sn'][0])){
906       $name= $attrs['sn'][0];
907     }
908     if (isset($attrs['givenName'][0])){
909       if ($name != ""){
910         $name.= ", ".$attrs['givenName'][0];
911       } else {
912         $name.= $attrs['givenName'][0];
913       }
914     }
915     if ($name != ""){
916       $name.= " ";
917     }
919     return ($name);
920   }
922   function getCopyDialog()
923   {
924     if(!$this->is_account) return("");
926     $smarty = get_smarty();
927     $smarty->assign("gosaMailAlternateAddress",$this->gosaMailAlternateAddress);
928     $smarty->assign("gosaMailForwardingAddress",$this->gosaMailForwardingAddress);
929     $smarty->assign("mail",$this->mail);
930     $display= $smarty->fetch (get_template_path('paste_mail.tpl', TRUE, dirname(__FILE__)));
931     $ret = array();
932     $ret['string'] = $display;
933     $ret['status'] = "";
934     return($ret);
935   }
937   function saveCopyDialog()
938   {
939     if(!$this->is_account) return;
941     /* Perform ADD / REMOVE ... for mail alternate / mail forwarding addresses 
942     */
943     $this->execute();
944     if(isset($_POST['mail'])){
945       $this->mail = $_POST['mail'];
946     }
947   }
950   function PrepareForCopyPaste($source)
951   {
952     plugin::PrepareForCopyPaste($source);
953  
954     /* Reset alternate mail addresses */
955     $this->gosaMailAlternateAddress = array();
956   }
959   /* Return plugin informations for acl handling  */
960   static function plInfo()
961   {
962     return (array(
963           "plShortName"   => _("Mail"),
964           "plDescription" => _("Group mail"),
965           "plSelfModify"  => FALSE,
966           "plDepends"     => array(),
967           "plPriority"    => 10,
968           "plSection"     => array("administration"),
969           "plCategory"    => array("groups"), 
970           "plProvidedAcls"=> array(
971             "mail"                      => _("Mail address"),
972             "gosaMailQuota"             => _("Quota size"),
973             "gosaMailServer"            => _("Mail server"),
974             "kolabFolderType"           => _("Folder type")." ("._("Kolab").")",
975             "gosaMailAlternateAddress"  => _("Alternate addresses"),
976             "gosaMailForwardingAddress" => _("Forwarding addresses"),
977             "gosaMailDeliveryModeI"     => _("Only local"),
978             "acl"                       => _("Permissions"))
979           ));
980   }
982   
983   /* Remove given ACL for given member (uid,mail) ..
984    */
985   function removeUserAcl($index )
986   {
987     if(isset($this->imapacl[$index])){
988       unset($this->imapacl[$index]);
989     }
990   }
992   function multiple_execute()
993   {
994     return($this->execute());
995   }
998   function init_multiple_support($attrs,$all)
999   {
1000     plugin::init_multiple_support($attrs,$all);
1002     $this->gosaMailForwardingAddress = array();
1003     if(isset($attrs['gosaMailForwardingAddress'])){
1004       for($i = 0 ; $i < $attrs['gosaMailForwardingAddress']['count'] ; $i++){
1005         $this->gosaMailForwardingAddress[] = $attrs['gosaMailForwardingAddress'][$i];
1006       }
1007     }
1009     $this->gosaMailForwardingAddress_Some = array();
1010     if(isset($all['gosaMailForwardingAddress'])){
1011       for($i = 0 ; $i < $all['gosaMailForwardingAddress']['count'] ; $i++){
1012         if(!in_array($all['gosaMailForwardingAddress'][$i],$this->gosaMailForwardingAddress)){
1013           $this->gosaMailForwardingAddress_Some[] = $all['gosaMailForwardingAddress'][$i];
1014         }
1015       }
1016     }
1017   }
1019   function multiple_save_object()
1020   {
1021     if(isset($_POST['multiple_mail_group_posted'])){
1022       plugin::multiple_save_object();
1023       
1024       foreach(array("kolabFolderType") as $attr){
1025         if(isset($_POST['use_'.$attr])){
1026           $this->multi_boxes[] = $attr;
1027         }
1028       }
1030       /* Add special kolab attributes */
1031       if(preg_match("/olab/i",$this->config->get_cfg_value("mailmethod"))){
1032         if(isset($_POST['kolabFolderTypeType']) && $this->acl_is_writeable("kolabFolderType")){
1033           $this->kolabFolderTypeType = get_post("kolabFolderTypeType");
1034           $this->kolabFolderTypeSubType = get_post("kolabFolderTypeSubType");
1035         }
1036       }
1038       /* Collect data and re-assign it to the imapacl array */
1039       if ($this->acl_is_writeable("acl")){
1040         $this->imapacl= array();
1041         $this->imapacl['%members%']= $_POST['member_permissions'];
1042         $this->imapacl['anyone']= $_POST['default_permissions'];
1043         foreach ($this->indexed_user as $nr => $user){
1044           if (!isset($_POST["user_$nr"])){
1045             continue;
1046           }
1047           if ($_POST["user_$nr"] != $user ||
1048               $_POST["perm_$nr"] != $this->indexed_acl[$nr]){
1049             $this->is_modified= TRUE;
1050           }
1051           $this->imapacl[$_POST["user_$nr"]]= $_POST["perm_$nr"];
1052         }
1053       }
1054     }
1055   }
1056   
1057   
1058   /* Return selected values for multiple edit */
1059   function get_multi_edit_values()
1060   {
1061     $ret = plugin::get_multi_edit_values();
1062     $ret['Forward_some'] = $this->gosaMailForwardingAddress_Some;    
1063     $ret['Forward_all'] = $this->gosaMailForwardingAddress;    
1064     if(in_array('kolabFolderType',$this->multi_boxes)){
1065       $ret['kolabFolderTypeType'] = $this->kolabFolderTypeType;
1066       $ret['kolabFolderTypeSubType'] = $this->kolabFolderTypeSubType;
1067     }
1068     if(in_array("acl",$this->multi_boxes)){
1069       $ret['imapacl'] = $this->imapacl;
1070     }
1071     return($ret);
1072   }
1074   function set_multi_edit_values($attrs)
1075   {
1076     $forward = array();
1077     foreach($attrs['Forward_some'] as $addr){
1078       if(in_array($addr,$this->gosaMailForwardingAddress)){
1079         $forward[] = $addr;
1080       }
1081     }
1082     foreach($attrs['Forward_all'] as $addr){
1083       $forward[] = $addr;
1084     }
1085     plugin::set_multi_edit_values($attrs);
1086     $this->gosaMailForwardingAddress = $forward;
1087   }
1090   /*! \brief  Displays a dialog that allows mail address selection.
1091    */
1092   function display_forward_dialog()
1093   {
1094     restore_error_handler();
1096     $smarty = get_smarty();
1097     $ldap= $this->config->get_ldap_link();
1099     /* Save data */
1100     $mailfilter= session::get("mailfilter");
1101     foreach( array("depselect", "muser", "regex") as $type){
1102       if (isset($_POST[$type])){
1103         $mailfilter[$type]= $_POST[$type];
1104       }
1105     }
1106     if (isset($_GET['search'])){
1107       $s= mb_substr($_GET['search'], 0, 1, "UTF8")."*";
1108       if ($s == "**"){
1109         $s= "*";
1110       }
1111       $mailfilter['regex']= $s;
1112     }
1113     session::set("mailfilter", $mailfilter);
1115     /* Get actual list */
1116     $mailusers= array ();
1117     if ($mailfilter['regex'] != '*' && $mailfilter['regex'] != ""){
1118       $regex= $mailfilter['regex'];
1119       $filter= "(|(mail=$regex)(gosaMailAlternateAddress=$regex))";
1120     } else {
1121       $filter= "";
1122     }
1123     if ($mailfilter['muser'] != ""){
1124       $user= $mailfilter['muser'];
1125       $filter= "$filter(|(uid=$user)(cn=$user)(givenName=$user)(sn=$user))";
1126     }
1128     /* Add already present people to the filter */
1129     $exclude= "";
1130     foreach ($this->gosaMailForwardingAddress as $mail){
1131       $exclude.= "(mail=$mail)";
1132     }
1133     if ($exclude != ""){
1134       $filter.= "(!(|$exclude))";
1135     }
1136     $res= get_list("(&(objectClass=gosaMailAccount)$filter)", "users", $mailfilter['depselect'],
1137         array("sn", "mail", "givenName"), GL_SIZELIMIT | GL_SUBSEARCH);
1138     $ldap->cd($mailfilter['depselect']);
1139     $ldap->search ("(&(objectClass=gosaMailAccount)$filter)", array("sn", "mail", "givenName"));
1140     while ($attrs= $ldap->fetch()){
1141       if(preg_match('/%/', $attrs['mail'][0])){
1142         continue;
1143       }
1144       $name= $this->make_name($attrs);
1145       $mailusers[$attrs['mail'][0]]= $name."&lt;".
1146         $attrs['mail'][0]."&gt;";
1147     }
1148     natcasesort ($mailusers);
1149     reset ($mailusers);
1151     /* Show dialog */
1152     $smarty->assign("search_image", get_template_path('images/lists/search.png'));
1153     $smarty->assign("usearch_image", get_template_path('images/lists/search-user.png'));
1154     $smarty->assign("tree_image", get_template_path('images/lists/search-subtree.png'));
1155     $smarty->assign("infoimage", get_template_path('images/info.png'));
1156     $smarty->assign("launchimage", get_template_path('images/lists/action.png'));
1157     $smarty->assign("mailusers", $mailusers);
1158     if (isset($_POST['depselect'])){
1159       $smarty->assign("depselect", $_POST['depselect']);
1160     }
1161     $smarty->assign("deplist", $this->config->idepartments);
1162     $smarty->assign("apply", apply_filter());
1163     $smarty->assign("alphabet", generate_alphabet());
1164     $smarty->assign("hint", print_sizelimit_warning());
1165     foreach( array("depselect", "muser", "regex") as $type){
1166       $smarty->assign("$type", $mailfilter[$type]);
1167     }
1168     $smarty->assign("hint", print_sizelimit_warning());
1169     $display= $smarty->fetch (get_template_path('mail_locals.tpl', TRUE, dirname(__FILE__)));
1170     return ($display);
1171   }
1174   /*! \brief  Add given mail address to the list of forwarders.
1175    */
1176   function addForwarder($address)
1177   {
1178     if(empty($address)) continue;
1179     $this->gosaMailForwardingAddress[]= $address;
1180     $this->gosaMailForwardingAddress= array_unique($this->gosaMailForwardingAddress);
1182     /* Update multiple edit values too */
1183     if($this->multiple_support_active){
1184       $this->gosaMailForwardingAddress_Some= 
1185         array_remove_entries (array($address),$this->gosaMailForwardingAddress_Some);
1186     }
1188     sort ($this->gosaMailForwardingAddress);
1189     reset ($this->gosaMailForwardingAddress);
1190     $this->is_modified= TRUE;
1191   }
1194   /*! \brief  Removes the given mail address from the forwarders 
1195    */
1196   function delForwarder($addresses)
1197   {
1198     if(empty($address)) continue;
1199     $this->gosaMailForwardingAddress= array_remove_entries ($addresses,
1200         $this->gosaMailForwardingAddress);
1202     /* Update multiple edit values too */
1203     if($this->multiple_support_active){
1204       $this->gosaMailForwardingAddress_Some = array_remove_entries ($addresses,
1205           $this->gosaMailForwardingAddress_Some);
1206     }
1207     $this->is_modified= TRUE;
1208   }
1211   /*! \brief  Add given mail address to the list of alternate adresses ,
1212     .          check if this mal address is used, skip adding in this case
1213    */
1214   function addAlternate($address)
1215   {
1216     if(empty($address)) continue;
1217     $ldap= $this->config->get_ldap_link();
1219     $address= strtolower($address);
1221     /* Is this address already assigned in LDAP? */
1222     $ldap->cd ($this->config->current['BASE']);
1223     $ldap->search ("(&(objectClass=gosaMailAccount)(|(mail=$address)".
1224         "(gosaMailAlternateAddress=$address)))");
1226     if ($ldap->count() > 0){
1227       $attrs= $ldap->fetch ();
1228       return ($attrs["uid"][0]);
1229     }
1231     /* Add to list of alternates */
1232     if (!in_array($address, $this->gosaMailAlternateAddress)){
1233       $this->gosaMailAlternateAddress[]= $address;
1234     }
1236     sort ($this->gosaMailAlternateAddress);
1237     reset ($this->gosaMailAlternateAddress);
1238     $this->is_modified= TRUE;
1240     return ("");
1241   }
1244   /*! \brief  Removes the given mail address from the alternate addresses  
1245    */
1246   function delAlternate($addresses)
1247   {
1248     if(empty($address)) continue;
1249     $this->gosaMailAlternateAddress= array_remove_entries ($addresses,
1250         $this->gosaMailAlternateAddress);
1251     $this->is_modified= TRUE;
1252   }
1255   function postable_acls()
1256   {
1257     $ret = array();
1258     foreach($this->folder_acls as $name => $acl){
1259       $ret[$name] = array("name" => $name,"acl" => $acl,"post_name" => base64_encode($name));
1260     }
1261     return($ret);
1262   }
1265   function get_effective_member_acls()
1266   {
1267     $tmp = array();
1268     $member = $this->get_member();
1269     foreach($member['mail'] as $uid => $mail){
1271       /* Do not save overridden acls */
1272       if(isset($this->folder_acls[$mail])){
1273         continue;
1274       }
1276       
1277       $tmp[$mail]  = $this->folder_acls['__member__'];
1278     }
1279     return($tmp);
1280   }
1283   function allow_remove()
1284   {
1285     $resason = "";
1286     if(!$this->mailMethod->allow_remove($reason)){
1287       return($reason);
1288     }
1289     return("");
1290   }
1293   // vim:tabstop=2:expandtab:shiftwidth=2:filetype=php:syntax:ruler:
1294 ?>