32d57f4f93278b98218771ceaab0bcc7ddce59f3
1 <?php
4 class addressbookgosa extends plugin{
6 static function plInfo()
7 {
8 /* Adapt addressbook settings and mofiy required settings.
9 */
10 $attrs = addressbook::plInfo();
11 $attrs['plShortName'] = _("Addressbook")." - "._("GOsa");
12 $attrs['plDescription'] = _("Addressbook")." - "._("GOsa related objects");
13 $attrs['plSelfModify'] = TRUE;
14 $attrs['plPriority'] = 2;
15 $attrs['plCategory'] = array("addressbook");
16 return($attrs);
17 }
18 }
20 class addressbook extends plugin
21 {
22 /* Definitions */
23 var $plHeadline = "Addressbook";
24 var $plDescription= "This does something";
26 /* Generic */
27 var $ui;
29 /* Phonelist attributes */
30 var $telephone_list = array();
31 var $new_dn = "";
32 var $orig_cn = "";
33 var $storage_base = "";
34 var $orig_storage_base= "";
36 /* Filter attributes */
37 var $start = 0;
38 var $search_for = "*";
39 var $search_base = "";
40 var $search_type = "";
41 var $range = 20;
43 /* Currently edited/added entry attributes */
44 var $sn = "";
45 var $cn = "";
46 var $givenName = "";
47 var $mail = "";
48 var $title = "";
49 var $personalTitle = "";
50 var $initials = "";
51 var $homePostalAddress = "";
52 var $homePhone = "";
53 var $mobile = "";
54 var $o = "";
55 var $postalAddress = "";
56 var $l = "";
57 var $postalCode = "";
58 var $st = "";
59 var $ou = "";
60 var $telephoneNumber = "";
61 var $facsimileTelephoneNumber = "";
62 var $pager = "";
63 var $view_logged = FALSE;
65 /* attribute list for save action */
66 var $attributes= array("sn", "givenName", "mail", "title",
67 "initials", "homePostalAddress", "displayName",
68 "homePhone", "mobile", "o", "postalAddress", "l",
69 "postalCode", "st", "ou", "telephoneNumber",
70 "facsimileTelephoneNumber", "pager");
72 var $objectclasses= array("top", "person", "organizationalPerson", "inetOrgPerson");
74 var $abobjectclass= "dc=addressbook";
75 var $acl_targets_objects = array();
77 function addressbook (&$config, $dn= NULL)
78 {
79 /* Include config object */
80 $this->config= &$config;
82 $this->base = $this->config->current['BASE'];
84 /* Check if there is a special ldap-sub-tree specified, instead of dc=addressbook, */
85 $aoc = $this->config->search("addressbook", "addressbookBaseDN",array('menu'));
86 if ($aoc != ""){
87 $this->abobjectclass = $aoc;
88 }
90 /* Get global filter config */
91 if (!session::is_set("phonefilter")){
92 $ui = get_userinfo();
93 $base = get_base_from_people($ui->dn);
94 $phonefilter= array(
95 "search_base" => $base,
96 "organizational" => "checked",
97 "global" => "checked",
98 "search_for" => "*",
99 "object_type" => "*");
100 session::set("phonefilter", $phonefilter);
101 }
103 $this->ui = get_userinfo();
104 $this->acl_targets_objects = $this->ui->get_acl_target_objects();
105 }
107 function execute()
108 {
109 /* Call parent execute */
110 plugin::execute();
112 $smarty= get_smarty();
114 /* Prevent empty variables for smarty */
115 foreach($this->attributes as $atr) {
116 $smarty->assign($atr,"");
117 }
119 /* Save formular information */
120 $phonefilter= session::get("phonefilter");
121 foreach( array("search_for", "search_base", "object_type") as $type){
122 if (isset($_POST[$type])){
123 $phonefilter[$type]= $_POST[$type];
124 }
125 $this->$type= $phonefilter[$type];
126 }
127 if (isset($_POST['search_base'])){
128 foreach( array("organizational", "global") as $type){
129 if (isset($_POST[$type])){
130 $phonefilter[$type]= "checked";
131 } else {
132 $phonefilter[$type]= "";
133 }
134 }
135 }
137 /* Search string */
138 $s= $phonefilter['search_for'];
139 if ($s == "") {
140 $s= "*";
141 }
142 if (isset($_GET['search'])){
143 $s= validate(mb_substr($_GET['search'], 0, 1, "UTF8"))."*";
144 if ($s == "**"){
145 $s= "*";
146 }
147 $this->search_for= $s;
148 $phonefilter['search_for']= $s;
149 }
150 session::set("phonefilter", $phonefilter);
152 /* Assign create acl */
153 $acl = $this->get_entry_acls($this->base);
154 $smarty->assign("internal_createable", preg_match("/c/",$acl));
156 $acl = $this->get_entry_acls($this->dn);
157 $smarty->assign("internal_removeable", preg_match("/d/",$acl));
158 $smarty->assign("internal_editable", preg_match("/w/",$acl));
160 /* Perform actions with CTI hook */
161 if (isset($_GET['target'])
162 && isset($_GET['dial'])
163 && $this->config->get_cfg_value("ctiHook") != "" ){
165 $dialmode= $_GET['dial'];
166 if ($dialmode == "telephoneNumber" ||
167 $dialmode == "mobile" ||
168 $dialmode == "homePhone"){
170 /* Get target */
171 $ldap= $this->config->get_ldap_link();
172 $ldap->cat(base64_decode($_GET['target']), array('telephoneNumber', 'mobile', 'homePhone'));
173 $attrs= $ldap->fetch();
174 if (isset($attrs["$dialmode"])){
175 $target= $attrs[$dialmode][0];
176 } else {
177 $target= "";
178 }
180 /* Get source */
181 $ui= get_userinfo();
182 $ldap->cat($ui->dn, array('telephoneNumber'));
183 $attrs= $ldap->fetch();
184 if (isset($attrs["telephoneNumber"])){
185 $source= $attrs['telephoneNumber'][0];
186 } else {
187 $source= "";
188 }
190 /* Save to session */
191 session::set('source',$source);
192 session::set('target',$target);
194 /* Perform call */
195 if ($target != "" && $source != ""){
196 $smarty->assign("phone_image", get_template_path('plugins/addressbook/images/phone.png'));
197 $smarty->assign("dial_info", sprintf(_("Dial from %s to %s now?"), "<b style='font-size:22px; color:red'>".$source."</b>", "<b style='font-size:22px;color:red'>".$target."</b>"));
198 return($smarty->fetch(get_template_path('dial.tpl', TRUE)));
199 return;
200 } else {
201 msg_dialog::display(_("Error"), _("You need to set your personal phone number in order to perform direct dials."), ERROR_DIALOG);
202 }
203 }
205 }
207 /* Finally dial */
208 if (isset($_POST['dial']) && session::is_set('source') && session::is_set('target')){
209 exec ($this->config->get_cfg_value("ctiHook")." ".
210 escapeshellarg(session::get('source'))." ".escapeshellarg(session::get('target')), $dummy, $retval);
211 session::un_set('source');
212 session::un_set('target');
213 }
216 /* Delete entry? */
217 if (isset($_POST['delete_entry_confirm'])){
219 /* Some nice guy may send this as POST, so we've to check
220 for the permissions again. */
222 $acl = $this->get_entry_acls($this->dn);
223 if(preg_match("/d/",$acl)){
225 /* Delete request is permitted, perform LDAP action */
226 $ldap= $this->config->get_ldap_link();
227 $ldap->rmdir ($this->dn);
228 new log("remove","addressbook/".get_class($this),$this->dn,array_keys($this->attrs),$ldap->get_error());
229 if (!$ldap->success()){
230 msg_dialog::display(_("LDAP error"), msgPool::ldaperror($ldap->get_error(), $this->dn, LDAP_DEL, get_class()));
231 }
232 new log("remove","addressbook/".get_class($this),$this->dn,array(),"Addressbook object'".$this->dn."' has been removed");
234 } else {
236 /* Normally this shouldn't be reached, send some extra
237 logs to notify the administrator */
238 msg_dialog::display(_("Permission"),permDelete($this->dn),ERROR_DIALOG);
239 new log("remove","addressbook/".get_class($this),$this->dn,array(),"Warning: '".$this->ui->uid."' tried to trick address book deletion.");
240 }
242 /* Remove lock file after successfull deletion */
243 del_lock ($this->dn);
245 /* Clean up */
246 if (session::is_set('saved_start')){
247 $_GET['start']= session::get('saved_start');
248 }
249 session::un_set('show_info');
250 session::un_set('saved_start');
251 }
254 /* Delete entry? */
255 if (isset($_POST['delete_cancel'])){
256 del_lock ($this->dn);
257 }
260 /* Save address entry? */
261 if (isset($_POST['save'])){
262 $this->save_object();
263 $this->storage_base= $_POST['storage_base'];
265 /* Perform checks */
266 $message= $this->check ();
268 /* No errors, save object */
269 if (count ($message) == 0){
270 $this->save();
272 /* Clean up */
273 if (session::is_set('saved_start')){
274 $_GET['start']= session::get('saved_start');
275 }
276 session::set('show_info',$this->dn);
277 session::un_set('saved_start');
278 } else {
279 /* Errors found, show message */
280 msg_dialog::displayChecks($message);
281 }
282 }
285 /* Close info window */
286 if (isset($_GET['close']) || isset($_POST['cancel'])){
287 if (session::is_set('saved_start')){
288 $_GET['start']= session::get('saved_start');
289 }
290 session::un_set('show_info');
291 session::un_set('saved_start');
292 }
295 /* Start address book edit mode? */
296 if (isset($_GET['global'])){
297 if (!session::is_set('saved_start') && isset($_GET['start'])){
298 session::set('saved_start',$_GET['start']);
299 }
300 switch ($_GET['global']){
301 case "add":
302 $this->dn= "new";
303 $this->orig_cn= "";
305 /* Clean values */
306 foreach ($this->attributes as $name){
307 $this->$name= "";
308 }
309 $this->saved_attributes= array();
310 $this->storage_base= $this->config->current["BASE"];
311 break;
313 case "edit":
314 /* Clean values */
315 foreach ($this->attributes as $name){
316 $this->$name= "";
317 }
318 $this->dn= session::get('show_info');
319 $this->load();
320 $this->orig_cn= $this->cn;
321 break;
322 case "remove":
323 $this->dn= session::get('show_info');
324 $this->load();
326 /* Load permissions for selected 'dn' and check if
327 we're allowed to remove this 'dn' */
328 $acl = $this->get_entry_acls($this->dn);
329 if(preg_match("/d/",$acl)){
331 /* Check locking, save current plugin in 'back_plugin', so
332 the dialog knows where to return. */
333 if (($user= get_lock($this->dn)) != ""){
334 return(gen_locked_message ($user, $this->dn));
335 }
337 /* Lock the current entry, so nobody will edit it during deletion */
338 $ui= get_userinfo();
339 add_lock ($this->dn, $ui->dn);
340 $smarty->assign("info", msgPool::deleteInfo($this->dn));
341 return($smarty->fetch(get_template_path('remove.tpl', TRUE)));
342 } else {
344 /* Obviously the user isn't allowed to delete. Show message and
345 clean session. */
346 msg_dialog::display(_("Permission"),permDelete($this->dn),ERROR_DIALOG);
347 }
348 }
349 session::set('show_info',"ADD");
350 }
353 /* Open info window */
354 if (isset($_GET['show'])){
355 if (!session::is_set('saved_start')){
356 session::set('saved_start',$_GET['start']);
357 }
358 $this->dn = base64_decode($_GET['show']);
359 $this->view_logged =FALSE;
360 if(!$this->view_logged){
361 $this->view_logged = TRUE;
362 new log("view","addressbook/".get_class($this),$this->dn);
363 }
364 session::set('show_info',base64_decode($_GET['show']));
365 }
368 /* Get ldap link / build filter */
369 $ldap= $this->config->get_ldap_link();
370 $this->telephone_list= array ();
373 /* Assemble bases
374 (Depending on checkboxes, we search for organisational entries or seperated
375 adressbook entries within dc=adressbook, ) */
376 $bases= array();
377 $filter= "";
378 if ($phonefilter['global'] == "checked"){
379 $bases[]= preg_replace("/".$this->config->current['BASE']."/", $this->abobjectclass.",".$this->config->current['BASE'], $this->search_base);
380 } else {
381 $filter= '(objectClass=gosaAccount)';
382 }
383 if ($phonefilter['organizational'] == "checked"){
384 $bases[]= $this->search_base;
385 }
388 /* Only display those entries that have at least on of this attributes set */
389 $must_have_this = array("telephoneNumber","facsimileTelephoneNumber","mobile","homePhone","mail");
391 /* Requested attributes in ldap search */
392 $attributes = array("sn", "givenName", "telephoneNumber", "facsimileTelephoneNumber", "mobile", "homePhone", "uid", "mail", "cn");
394 /* Create attribute filter part */
395 $attribute_filter = "";
396 foreach($attributes as $att){
397 $attribute_filter .= "(".$att."=".$s.")";
398 }
400 /* Walk through bases an check for usable entries */
401 foreach ($bases as $base){
403 $ldap->cd ($base);
405 if ($phonefilter['object_type'] == '*'){
406 $ldap->search (
407 "(&(objectClass=person)$filter(!(objectClass=gosaUserTemplate))". // Skip templates etc ..
408 "(!(uid=*$))". // Skip entries with ...$ as uid
409 "(|".$attribute_filter."))"
410 ,$attributes);
411 } else {
412 $ldap->search ("(&$filter(!(uid=*$))(!(objectClass=gosaUserTemplate))". //array
413 "(".$phonefilter['object_type']."=$s))", $attributes);
414 }
416 /* Walk through LDAP results */
417 while ($attrs= $ldap->fetch()){
419 /* prevent empty vaiables */
420 foreach($this->attributes as $atr) {
421 if(!isset($attrs[$atr][0])) {
422 $attrs[$atr][0] = "";
423 }
424 }
426 /* Check if page number was posted */
427 if(!isset($_GET['start'])) {
428 $_GET['start']="";
429 }
431 /* Check if at least one attribute is specified */
432 $skip = false;
434 foreach($must_have_this as $attr) {
435 if(isset($attrs[$attr][0]) && !empty($attrs[$attr][0])){
436 $skip =false;
437 break;
438 }
439 }
441 /* Skip all attributes that we are not allowed to read */
442 $any = false;
443 foreach($attributes as $attr){
445 $acls = $this->get_entry_acls($attrs['dn'],$attr);
446 if(!preg_match("/r/",$acls)){
447 $attrs[$attr][0] = "";
448 }else{
449 $any = true;
450 }
451 }
453 /* Only show lines that have set any mail or phone informations */
454 if(!$skip && $any){
456 $this->telephone_list[$attrs['sn'][0].$attrs['dn']]=
458 "<td class=\"phonelist\" title=\"".$attrs['sn'][0].", ".$attrs['givenName'][0].
459 "\"onClick='location.href=\"main.php?plug=".validate($_GET['plug']).
460 "&start=".validate($_GET['start']).
461 "&show=".urlencode(base64_encode($attrs['dn']))."\"'>
462 <a style='vertical-align:middle;' href=\"main.php?plug=".validate($_GET['plug']).
463 "&start=".validate($_GET['start']).
464 "&show=".urlencode(base64_encode($attrs['dn']))."\">".
465 $attrs['sn'][0].", ".$attrs['givenName'][0].
466 "</a>
467 </td>
468 <td class=\"phonelist\" title=\""._("Dial")." ".$attrs['telephoneNumber'][0]."\">
469 <a style='vertical-align:middle;' href=\"main.php?plug=".validate($_GET['plug'])."&dial=telephoneNumber&start=".validate($_GET['start'])."&target=".base64_encode($attrs['dn'])."\">".$attrs['telephoneNumber'][0]."
470 </a>
471 </td>
472 <td class=\"phonelist\" title=\"".$attrs['facsimileTelephoneNumber'][0]."\">
473 ".$attrs['facsimileTelephoneNumber'][0]."
474 </td>
475 <td class=\"phonelist\" title=\""._("Dial")." ".$attrs['mobile'][0]."\">
476 <a style='vertical-align:middle;' href=\"main.php?plug=".validate($_GET['plug'])."&dial=mobile&start=".validate($_GET['start'])."&target=".base64_encode($attrs['dn'])."\">".$attrs['mobile'][0]."
477 </a>
478 </td>
479 <td class=\"phonelist\" title=\""._("Dial")." ".$attrs['homePhone'][0]."\">
480 <a style='vertical-align:middle;' href=\"main.php?plug=".validate($_GET['plug'])."&dial=homePhone&start=".validate($_GET['start'])."&target=".base64_encode($attrs['dn'])."\">".$attrs['homePhone'][0]."
481 </a>
482 </td>
483 <td>
484 <a href=\"plugins/addressbook/getvcard.php?dn=".base64_encode($attrs['dn'])."\">
485 <img align=\"top\" border=0 src=\"images/save.png\" alt=\"vcf\" title=\"".sprintf(_("Save contact for %s as vcard"), $attrs['givenName'][0]." ".$attrs['sn'][0])."\">
486 </a>";
489 if(preg_match("/r/",$this->get_entry_acls($attrs['dn'],"mail"))){
490 if (isset($attrs['mail'][0]) && !empty($attrs['mail'][0])){
491 $dest= sprintf(_("Send mail to %s"), $attrs['mail'][0]);
492 $this->telephone_list[$attrs['sn'][0].$attrs['dn']].=
494 "<a href=\"mailto:".htmlentities($attrs['mail'][0])."\">".
495 "<img align=\"top\" border=0 src=\"images/mailto.png\" alt=\"vcf\" title=\"$dest\"></a>";
496 }
497 }
498 $this->telephone_list[$attrs['sn'][0].$attrs['dn']].= " </td>";
499 }
500 }
501 error_reporting(E_ALL | E_STRICT);
502 }
504 /* Sort up list */
505 ksort ($this->telephone_list);
506 reset ($this->telephone_list);
508 /* Fill template variables */
509 $smarty->assign("search_for", $this->search_for);
510 $smarty->assign("object_type", $this->object_type);
512 /* Create list of readable departments */
513 $deps = array();
514 foreach($this->config->idepartments as $dn => $name){
515 if( $this->acl_is_readable($dn) || $dn == $this->config->current['BASE']){
516 $deps[$dn] = $name;
517 }
518 }
520 $this->base = $phonefilter['search_base'];
521 $smarty->assign("deplist", $deps);
522 $smarty->assign("depselect", $this->search_base);
523 $smarty->assign("global", $phonefilter['global']);
524 $smarty->assign("organizational", $phonefilter['organizational']);
525 $smarty->assign("search_image", get_template_path('images/lists/search.png'));
526 $smarty->assign("obj_image", get_template_path('plugins/addressbook/images/objects.png'));
527 $smarty->assign("tree_image", get_template_path('images/lists/search-subtree.png'));
528 $smarty->assign("infoimage", get_template_path('images/info.png'));
529 $smarty->assign("actionimage", get_template_path('images/action.png'));
530 $smarty->assign("launchimage", get_template_path('images/launch.png'));
532 /* Generate alphabet */
533 $alphabet= generate_alphabet();
535 /* Build list output */
536 $output= "";
537 $mod= 0;
540 /* View detailed infos */
541 $smarty->assign("show_info", "");
542 if (session::is_set('show_info')){
544 $range= 4;
545 $smarty->assign("show_info", "1");
546 $smarty->assign("url", "main.php?plug=".validate($_GET['plug'])."&close=1");
548 $tmp = $this->plInfo();
550 if(isset($_POST['storage_base'])){
551 $this->storage_base = $_POST['storage_base'];
552 }
554 switch (session::get('show_info')){
556 case "ADD":
558 $a_bases = $this->get_allowed_bases();
560 if(!isset($a_bases[$this->storage_base])){
561 $base = key($this->get_allowed_bases());
562 $this->storage_base = $base;
563 }
565 $smarty->assign ('storage_base', $this->storage_base);
566 $smarty->assign ('address_info', get_template_path('address_edit.tpl', TRUE));
568 foreach($tmp['plProvidedAcls'] as $name => $translated){
569 $smarty->assign($name."ACL",$this->get_entry_acls($this->abobjectclass.",".$base,$name));
570 }
571 break;
573 default:
574 $smarty->assign ('address_info', get_template_path('address_info.tpl', TRUE));
575 foreach($tmp['plProvidedAcls'] as $name => $translated){
576 $smarty->assign($name."ACL",$this->get_entry_acls($this->dn,$name));
577 }
578 break;
579 }
581 /* Fill variables from LDAP */
582 if (session::get('show_info') != "ADD"){
583 $ldap->cat(session::get('show_info'), $this->attributes);
584 $info= $ldap->fetch();
585 }
586 foreach ($this->attributes as $name){
588 $dn = $this->dn;
589 if($dn == "new") $dn = $this->base;
591 /* Skip entries we are not allowed to read */
592 if(!preg_match("/r/",$this->get_entry_acls($dn,$name))){
593 $smarty->assign("info_$name", "");
594 }else
596 if (session::get('show_info') != "ADD" && isset($info["$name"][0])){
597 error_reporting(0);
598 /* Special treatment for phone attributes */
599 if ($name == "mobile" ||
600 $name == "homePhone" ||
601 $name == "telephoneNumber"){
602 $smarty->assign("info_$name",
603 "<a title=\""._("Dial")." ".$info["$name"][0]."\" href=\"main.php?plug=".validate($_GET['plug'])."&dial=$name&start=".validate($_GET['start'])."&target=".base64_encode(session::get('show_info'))."\">".$info["$name"][0]."</a>");
604 } else {
605 $smarty->assign("info_$name", preg_replace("/\n/", "<br>", $info["$name"][0]));
606 }
607 error_reporting(E_ALL | E_STRICT);
608 } elseif (session::get('show_info') == "ADD" && isset($this->$name)) {
609 $smarty->assign("info_$name", $this->$name);
610 } else {
611 $smarty->assign("info_$name", "-");
612 }
613 }
614 if (preg_match("/,".$this->abobjectclass.",/", session::get('show_info'))){
615 $storage= _("global addressbook");
616 $smarty->assign("internal", 0);
617 } else {
618 $storage= _("user database");
619 $smarty->assign("internal", 1);
620 }
621 if (session::get('show_info') != "ADD"){
622 $smarty->assign("storage_info", sprintf(_("Contact stored in '%s'"), $storage));
623 } else {
624 $smarty->assign("storage_info", _("Creating new entry in"));
625 }
626 } else {
629 if(isset($_POST['EntryPerPage'])){
630 $this->range = $_POST['EntryPerPage'];
631 }
632 $range = $this->range;
633 $smarty->assign("internal", 1);
634 }
635 if (isset($_GET['start'])){
636 $this->start= validate($_GET['start']);
637 }
638 foreach ($this->telephone_list as $val){
639 if ($mod < $this->start) {
640 $mod++;
641 continue;
642 }
643 if ($mod >= ($this->start + $range)){
644 $mod++;
645 break;
646 }
647 if ( ($mod++) & 1){
648 $col= "style=\"background-color: #FFFFFF;\"";
649 } else {
650 $col= "style=\"background-color: #F5F5F5;\"";
651 }
652 $output.= "<tr $col>\n$val</tr>\n";
653 }
655 $smarty->assign("search_result", $output);
656 $smarty->assign("apply", apply_filter());
657 $smarty->assign("alphabet", $alphabet);
658 if($range < 20){
659 $smarty->assign("range_selector", range_selector(count($this->telephone_list), $this->start, $range));
660 }else{
661 $smarty->assign("range_selector", range_selector(count($this->telephone_list), $this->start, $range, "EntryPerPage"));
662 }
663 $tmp= array("*" => _("All"), "sn" => _("Name"), "givenName" => _("Given name"),
664 "telephoneNumber" => _("Work phone"), "mobile" => _("Cell phone"),
665 "homePhone" => _("Home phone"), "uid" => _("User ID"));
666 natsort($tmp);
667 $smarty->assign("objlist", $tmp);
669 /* Show main page */
670 $smarty->assign ('personal_image', get_template_path('plugins/addressbook/images/addr_personal.png'));
671 $smarty->assign ('home_image', get_template_path('plugins/addressbook/images/addr_home.png'));
672 $smarty->assign ('company_image', get_template_path('plugins/addressbook/images/addr_company.png'));
673 $smarty->assign ('add_image', get_template_path('images/lists/paste.png'));
674 $smarty->assign ('edit_image', get_template_path('images/lists/edit.png'));
675 $smarty->assign ('delete_image', get_template_path('images/lists/delete.png'));
676 return($smarty->fetch(get_template_path('contents.tpl', TRUE)));
677 }
679 function save_object()
680 {
681 plugin::save_object();
682 foreach($this->attributes as $attr){
684 /* save attributes depending on acls */
685 $acl = $this->get_entry_acls($this->dn,$attr);
687 if(preg_match("/w/",$acl)){
688 if(isset($_POST[$attr])){
689 $this->$attr = $_POST[$attr];
690 }
691 }
693 }
694 }
696 function check()
697 {
698 /* Call common method to give check the hook */
699 $message= plugin::check();
701 /* must: sn, givenName */
702 if ($this->sn == ""){
703 $message[] = msgPool::required(_("Name"));
704 return ($message);
705 }
706 if ($this->givenName == ""){
707 $message[] = msgPool::required(_("Given name"));
708 return ($message);
709 }
711 /* Check for valid name definition */
712 if (preg_match ("/[\\\\]/", $this->sn)){
713 $message[] = msgPool::invalid(_("Name"),$this->sn,"/[\\\\]");
714 }
715 if (preg_match ("/[\\\\]/", $this->givenName)){
716 $message[] = msgPool::invalid(_("Given name"),$this->givenName,"/[\\\\]");
717 }
719 /* Check phone numbers */
720 if (!tests::is_phone_nr($this->homePhone)){
721 $message[] = msgPool::invalid(_("Phone"),$this->homePhone);
722 }
723 if (!tests::is_phone_nr($this->telephoneNumber)){
724 $message[] = msgPool::invalid(_("Telephone number"),$this->telephoneNumber);
725 }
726 if (!tests::is_phone_nr($this->facsimileTelephoneNumber)){
727 $message[] = msgPool::invalid(_("Fax"),$this->facsimileTelephoneNumber);
728 }
729 if (!tests::is_phone_nr($this->mobile)){
730 $message[] = msgPool::invalid(_("Mobile"),$this->mobile);
731 }
732 if (!tests::is_phone_nr($this->pager)){
733 $message[] = msgPool::invalid(_("Pager"),$this->pager);
734 }
735 /* Check for reserved characers */
736 if (preg_match ('/[,+"<>;]/', $this->givenName)){
737 $message[] = msgPool::invalid(_("Given name"),$this->givenName,'/[,+"<>;]/');
738 }
739 if (preg_match ('/[,+"<>;]/', $this->sn)){
740 $message[] = msgPool::invalid(_("Name"),$this->sn,'/[,+"<>;]/');
741 }
743 /* Check mail */
744 if (!tests::is_email($this->mail)){
745 $message[] = msgPool::invalid(_("Email"),"","","your-domain@your-domain.com");
746 }
748 /* Assemble cn/dn */
749 $this->cn= $this->givenName." ".$this->sn;
750 if ($this->orig_cn != $this->cn || $this->storage_base != $this->orig_storage_base){
751 $this->new_dn= $this->create_unique_dn("cn", preg_replace("/,*".$this->config->current['BASE']."$/", "", $this->storage_base).",".$this->abobjectclass.",".$this->config->current['BASE']);
752 if ($this->new_dn == "none"){
753 $message[]= _("Cannot create a unique DN for your entry. Please fill more formular fields.");
754 return ($message);
755 }
756 } else {
757 $this->new_dn= $this->dn;
758 }
760 return ($message);
761 }
764 function load()
765 {
766 /* Load base attributes */
767 plugin::plugin ($this->config, $this->dn);
768 $this->view_logged = FALSE;
769 $this->storage_base= preg_replace('/^[^,]+,/', '', preg_replace('/'.$this->abobjectclass.',/', '', $this->dn));
770 }
773 function save()
774 {
775 /* First use parents methods to do some basic fillup in $this->attrs */
776 plugin::save ();
778 $this->attrs['cn']= $this->cn;
779 $this->attrs['displayName']= $this->givenName." ".$this->sn;
781 /* Move entry if it got another name... */
782 if ($this->dn != "new" && $this->dn != $this->new_dn){
783 $this->move($this->dn, $this->new_dn);
784 }
785 $this->dn= $this->new_dn;
787 /* Save data. Using 'modify' implies that the entry is already present, use 'add' for
788 new entries. So do a check first... */
789 $ldap= $this->config->get_ldap_link();
790 $ldap->cat ($this->dn,array('dn'));
791 if ($ldap->fetch()){
792 $mode= "modify";
793 } else {
794 $mode= "add";
795 $ldap->cd($this->config->current['BASE']);
796 $ldap->create_missing_trees(preg_replace('/^[^,]+,/', '', $this->dn));
797 }
799 /* Finally write data with selected 'mode' */
800 $ldap->cd ($this->dn);
801 $this->cleanup();
802 $ldap->$mode ($this->attrs);
803 if (!$ldap->success()){
804 msg_dialog::display(_("LDAP error"), msgPool::ldaperror($ldap->get_error(), $this->dn, LDAP_DEL, get_class()));
805 return (1);
806 }
808 if($mode == "add"){
809 new log("create","addressbook/".get_class($this),$this->dn, array_keys($this->attrs),$ldap->get_error());
810 }else{
811 new log("modify","addressbook/".get_class($this),$this->dn, array_keys($this->attrs),$ldap->get_error());
812 }
813 }
816 /* Return entry acls */
817 function get_entry_acls($dn,$attr = "")
818 {
819 $acls = "";
820 $combineACLs = FALSE;
822 /* If combineACLs is set to false:
823 Differentiate between user and addressbook acls, thus leads into two object categories.
824 - real GOsa users
825 - and addressbook entries
826 To view addressbook entries (e.g. ou=addressbook,) you just require permissions on the ldap base for 'addressbook'.
827 To view real GOsa users you have to additionally add user permissions.
829 You can enable this option, to use only addressbook acls.
830 */
831 if($combineACLs){
832 $dn = preg_replace("/".preg_quote($this->abobjectclass, '/').",/","",$dn);
833 $acls = $this->ui->get_permissions($dn,"addressbook/addressbook",$attr);
834 }else{
836 /* Use addressbook acls */
837 if(preg_match("/".preg_quote($this->abobjectclass, '/')."/",$dn)) {
838 $acls = "";
839 foreach($this->acl_targets_objects as $path){
840 $acls .= $this->ui->get_permissions($path,"addressbook/addressbook",$attr);
841 }
842 }
844 /* Use Organizational Person acls */
845 else{
846 $acls = $this->ui->get_permissions($dn,"addressbook/addressbookgosa",$attr);
847 }
848 }
850 return($acls);
851 }
854 /* Return plugin informations for acl handling */
855 static function plInfo()
856 {
857 return (array(
858 "plShortName" => _("Addressbook")." - "._("Addressbook entries"),
859 "plDescription" => _("Addressbook")." - "._("Addressbook related objects"),
860 "plSelfModify" => FALSE,
861 "plDepends" => array(),
862 "plPriority" => 0,
863 "plSection" => array("addon" => _("Addons")),
864 "plCategory" => array("addressbook" => array("objectClass" => "inetOrgPerson", "description" => _("Addressbook"))),
866 "plProvidedAcls" => array(
867 "sn" => _("Surname"),
868 "givenName" => _("Given name"),
869 "telephoneNumber" => _("Telefon number"),
870 "facsimileTelephoneNumber" => _("Fax number"),
871 "mobile" => _("Mobile number"),
872 "homePhone" => _("Home phone number"),
873 "uid" => _("User identification"),
874 "mail" => _("Mail address"),
875 "pager" => _("Pager"),
876 "o" => _("Organization"),
877 "ou" => _("Department"),
878 "l" => _("Location"),
879 "postalAddress" => _("Postal address"),
880 "postalCode" => _("Postal address"),
881 "st" => _("State"),
882 "initials" => _("Initials"),
883 "title" => _("Title"),
884 "homePostalAddress" => _("Home postal address"),
885 "cn" => _("Common name"))
886 ));
887 }
888 }
889 // vim:tabstop=2:expandtab:shiftwidth=2:filetype=php:syntax:ruler:
890 ?>