conn = ldap_connect($host,$port); ldap_set_option($this->conn, LDAP_OPT_PROTOCOL_VERSION, 3); $this->bind_status = ldap_bind($this->conn, $user, $pass); } function get_bind_status(){ return $this->bind_status; } function bind($host, $port, $user, $pass){ $conn = ldap_connect($host,$port); ldap_set_option($conn, LDAP_OPT_PROTOCOL_VERSION, 3); return ldap_bind($conn, $user, $pass); } function get_ldap_attr($dn, $attr){ # $search = ldap_search($this->conn, $dn, "$attr=*", array($attr)); $dn_array=ldap_explode_dn($dn, 0); $new_dn=array(); for ($i=1; $i<$dn_array['count']; $i++){ $new_dn[]=$dn_array[$i]; } $search=ldap_search($this->conn, implode(',', $new_dn), $dn_array[0]); if (ldap_count_entries($this->conn, $search)==0){ return Null; } $entry = ldap_first_entry($this->conn, $search); return ldap_get_values ($this->conn, $entry, $attr); } function get_ldap_attr_max($dn, $attr){ $search = ldap_search($this->conn, $dn, "$attr=*", array($attr)); $entry = ldap_first_entry($this->conn, $search); $max=0; while( $entry){ $tmp=ldap_get_values ($this->conn, $entry, $attr)[0]; if ($tmp>$max){ $max=$tmp; } $entry = ldap_next_entry($this->conn, $search); } return $max; } function add_ldap_obj($dn, $obj){ return ldap_add($this->conn, $dn, $obj); } function exist_ldap_obj($dn){ $dn_array=ldap_explode_dn($dn, 0); $new_dn=array(); for ($i=1; $i<$dn_array['count']; $i++){ $new_dn[]=$dn_array[$i]; } $search=ldap_search($this->conn, implode(',', $new_dn), $dn_array[0]); if (ldap_count_entries($this->conn, $search)==0){ return False; } return True; } function set_ldap_attr($dn, $attr, $value){ return ldap_modify($this->conn, $dn , array($attr=>$value)); } } abstract class Adapter{ function __construct($dn){ $this->dn = $dn; $this->setters = array(); $this->getters = array(); } function add_getter($attr, $fn = Null){ if (array_key_exists($attr, $this->getters)){ $this->getters[$attr][]= $fn; }else{ $this->getters[$attr] = array($fn); } } function add_setter($attr, $fn = Null){ if (array_key_exists($attr, $this->setters)){ $this->setters[$attr][]= $fn; }else{ $this->setters[$attr] = array($fn); } } function get_attr($la, $username, $attr){ if (array_key_exists($attr, $this->getters)){ foreach ($this->getters[$attr] as $getter){ $result=$la->get_ldap_attr(sprintf($this->dn, $username), $attr); if ($getter != Null) return $getter($result); return $result; } } return Null; } function set_attr($la, $username, $attr, $value){ $done=False; if (array_key_exists($attr, $this->setters)){ $done=True; foreach ($this->setters[$attr] as $setter){ if ($setter != Null) $value=$setter($value); $la->set_ldap_attr(sprintf($this->dn, $username), $attr, $value); } } return $done; } function get_attributes(){ $attributes=array(); foreach ($this->setters as $setter => $value) $attributes[]=$setter; return $attributes; } function exist($la, $username){ if ($la->exist_ldap_obj(sprintf($this->dn, $username))){ return True; } return False; } function bind($username, $password){ global $HOST, $PORT, $LOGIN_DN; return LdapAdapter::bind($HOST, $PORT, sprintf($this->dn,$username), $password); } } class MailAdapter extends Adapter{ function __construct($dn){ global $ssha; parent::__construct($dn); $this->add_getter('mail', function($x){return $x[0];}); # function($x){return substr($x, strlen("@lilik.it")*-1);} $this->add_setter('mail'); # function($x){return $x[0]."@lilik.it";} $this->add_getter('cn', function($x){return $x[0];}); $this->add_setter('cn'); $this->add_getter('userPassword', function($x){return $x[0];}); $this->add_setter('userPassword', $ssha); $this->add_getter('accountActive', function($x){return $x[0];}); $this->add_setter('accountActive'); } function create($la, $id, $name, $surname, $password){ global $ssha; $new_mail_obj=['cn'=> [sprintf('%s %s',$name,$surname)], 'accountActive'=> ['FALSE'], 'objectClass'=> ['top', 'VirtualMailAccount', 'Vacation', 'VirtualForward', 'amavisAccount'], 'smtpAuth'=> ['FALSE'], 'mailAutoreply'=> [sprintf('%s@lilik.it.autoreply',$id)], 'uid'=> [sprintf('%s.lilik.it',$id)], 'vacationEnd'=> ['200701010000'], 'userPassword'=> [$ssha($password)], 'amavisBypassSpamChecks'=> ['FALSE'], 'amavisSpamTagLevel'=> ['3.0'], 'otherTransport'=> ['phamm=>'], 'vacationInfo'=> ['vacation'], 'mail'=> [sprintf('%s@lilik.it',$id)], 'vacationStart'=> ['200701010000'], 'vacationActive'=> ['FALSE'], 'amavisSpamTag2Level'=> ['5.5'], 'vdHome'=> [sprintf('/home/mail_deliver/lilik.it/%s',$id)], 'quota'=> ['1024000'], 'mailbox'=> [sprintf('lilik.it/%s/',$id)], 'forwardActive'=> ['FALSE'], 'amavisBypassVirusChecks'=> ['FALSE'], 'sn'=> [sprintf('%s',$surname)], 'amavisSpamKillLevel'=> ['6.0'], 'givenName'=> [sprintf('%s',$name)], 'delete'=> ['FALSE'], 'lastChange'=> [sprintf('%d',time())] ]; return $la->add_ldap_obj(sprintf($this->dn,$id),$new_mail_obj); } } class PosixAdapter extends Adapter{ function __construct($dn){ global $ssha; parent::__construct($dn); $this->add_getter('cn', function($x){return $x[0];}); $this->add_setter('cn'); $this->add_getter('host'); $this->add_setter('host'); $this->add_getter('userPassword', function($x){return $x[0];}); $this->add_setter('userPassword', $ssha); $this->add_getter('memberOf'); $this->add_setter('memberOf'); } function create($la, $id, $name, $surname, $password){ global $ssha; $new_posix_obj=['uid'=> [sprintf('%s',$id)], 'objectClass'=> ['top', 'shadowAccount', 'posixAccount', 'account'], 'loginShell'=> ['/bin/bash'], 'userPassword'=> [$ssha($password)], 'uidNumber'=> [$la->get_ldap_attr_max('o=People,dc=lilik,dc=it', 'uidNumber')], 'host'=> ['*'], 'gidNumber'=> ['9000'], #stdusers 'homeDirectory'=> [sprintf('/home/%s',$id)], 'cn'=> [sprintf('%s %s',$name,$surname)], ]; return $la->add_ldap_obj(sprintf($this->dn,$id),$new_posix_obj); } } class GroupAdapter extends Adapter{ function __construct($dn){ parent::__construct($dn); $this->add_getter('member'); $this->add_setter('member'); $this->add_getter('memberUid'); $this->add_setter('memberUid'); } } abstract class pippo{ function __construct($id){ global $HOST, $PORT, $LOGIN_DN, $LOGIN_PASS; $this->id=$id; $this->la=new LdapAdapter($HOST, $PORT, $LOGIN_DN, $LOGIN_PASS); } function get_bind_status(){ return $this->la->get_bind_status(); } function get_attr($attr){ foreach($this->adapters as $adapter){ $result=$adapter->get_attr($this->la, $this->id, $attr); if ($result!=Null) return $result; } return Null; } function set_attr($attr, $value){ $result=False; foreach($this->adapters as $adapter){ if ($adapter->set_attr($this->la, $this->id, $attr, $value)){ $result=True; } } return $result; } function add_in_list($attr, $value){ $tmp=$this->get_attr($attr); if (in_array($value, $tmp)){ return True; } $tmp[]=$value; unset($tmp['count']); if ($this->set_attr($attr, $tmp)){ return True; } return False; } function del_in_list($attr, $value){ $tmp=$this->get_attr($attr); if (!in_array($value, $tmp)){ return True; } if(($key = array_search($value, $tmp)) !== false) { unset($tmp[$key]); } unset($tmp['count']); $tmp=array_values($tmp); if ($this->set_attr($attr, $tmp)){ return True; } return False; } function exist(){ foreach ($this->adapters as $adapter){ if ($adapter->exist($this->la, $this->id)){ return True; } } return False; } function check_password($password){ foreach ($this->adapters as $adapter) if ($adapter->bind($this->id, $password)) return True; return False; } } class LilikGroup extends pippo{ function __construct($id, $is_posix=False){ global $HOST, $PORT, $LOGIN_DN; parent::__construct($id); $this->adapters=[new GroupAdapter("cn=%s,o=Group,dc=lilik,dc=it")]; $this->is_posix=$is_posix; if ($is_posix){ $this->member_attr="memberUid"; }else{ $this->member_attr="member"; } } function get_id($user){ if ($this->is_posix){ return $user->id; }else{ return sprintf($user->adapters[1]->dn,$user->id); } } function add_user($user){ return $this->add_in_list($this->member_attr, $this->get_id($user)); } function del_user($user){ return $this->del_in_list($this->member_attr, $this->get_id($user)); } function is_user($user){ if (in_array($this->get_id($user), $this->get_attr($this->member_attr))){ return True; } return False; } } class LilikUser extends pippo{ function __construct($id){ parent::__construct($id); $this->adapters=array(new MailAdapter("mail=%s@lilik.it,vd=lilik.it,o=hosting,dc=lilik,dc=it"), new PosixAdapter("uid=%s,o=People,dc=lilik,dc=it")); $this->_flag=array('mail'=>'accountActive'); $this->_host=array('ltsp'=>'ltsp', 'users'=>'users'); $this->_member=array('admin'=>'admin', 'wiki'=>'wiki', 'lilik.it'=>'lilik.it', 'cloud'=>'cloud', 'projects'=>'projects', 'teambox'=>'teambox', 'im'=>'im' ); $this->_posix_member=array('users_sites'=>'users_sites'); if ($this->exist()){ $this->sanitize(); } } function is_admin(){ return $this->status('admin'); } function is_binded(){ } function enable($service){ if (array_key_exists($service, $this->_flag)){ return $this->set_attr($this->_flag[$service], 'TRUE'); }elseif (array_key_exists($service, $this->_host)){ return $this->add_in_list('host', $this->_host[$service]); }elseif (array_key_exists($service, $this->_member)){ $l=new LilikGroup($this->_member[$service]); return $l->add_user($this); }elseif (array_key_exists($service, $this->_posix_member)){ $l=new LilikGroup($this->_posix_member[$service], True); return $l->add_user($this); }else{ throw new Exception("Service not found"); } } function disable($service){ if (array_key_exists($service, $this->_flag)){ return $this->set_attr($this->_flag[$service], 'FALSE'); }elseif (array_key_exists($service, $this->_host)){ return $this->del_in_list('host', $this->_host[$service]); }elseif (array_key_exists($service, $this->_member)){ $l=new LilikGroup($this->_member[$service]); return $l->del_user($this); }elseif (array_key_exists($service, $this->_posix_member)){ $l=new LilikGroup($this->_posix_member[$service], True); return $l->del_user($this); }else{ throw new Exception("Service not found"); } } function status($service){ if (array_key_exists($service, $this->_flag)){ if ($this->get_attr($this->_flag[$service])=='TRUE'){ return True; } return False; }elseif (array_key_exists($service, $this->_host)){ if (in_array($this->_host[$service], $this->get_attr("host"))){ return True; } return False; }elseif (array_key_exists($service, $this->_member)){ $l=new LilikGroup($this->_member[$service]); return $l->is_user($this); }elseif (array_key_exists($service, $this->_posix_member)){ $l=new LilikGroup($this->_posix_member[$service], True); return $l->is_user($this); }else{ throw new Exception("Service not found"); } } function get_attributes(){ $attributes=array(); foreach ($this->adapters as $adapter) $attributes+= $adapter->get_attributes(); return $attributes; } function get_services(){ $services=array(); foreach (array($this->_flag, $this->_host, $this->_member, $this->_posix_member) as $k) foreach ($k as $x => $value) $services[]= $x; return $services; } function get_enabled_services(){ $enabled_services=array(); foreach ($this->get_services() as $service){ if ($this->status($service)){ $enabled_services[]=$service; } } return $enabled_services; } function sanitize(){ $tmp=explode(' ', $this->get_attr('cn'), 2); if (count($tmp) > 1){ $name=$tmp[0]; $surname=$tmp[1]; }else{ $name=$this->get_attr('cn'); $surname=''; } return $this->create($name, $surname, $this->get_attr('userPassword')); } function create($name, $surname, $password){ $result=True; foreach ($this->adapters as $adapter){ if (!$adapter->exist($this->la, $this->id)){ if (!$adapter->create($this->la, $this->id, $name, $surname, $password)){ $result=False; } } } return $result; } }