`
gogo1217
  • 浏览: 149998 次
  • 性别: Icon_minigender_1
  • 来自: 上海
社区版块
存档分类
最新评论

2款 wordpress LDAP插件 链接服务器的BUG修复

阅读更多

版权所有,转载请注明来源http://gogo1217.iteye.com,违者必究!

       今天安装了下wordpress,主要用于团队内部技术交流和分享。它的安装倒是非常简单,修改下数据库配置文件就可以了。但由于团队的账号全部采用LDAP进行管理,因此希望wordpress能与ldap进行集成。

       好在wordpress比较成熟,有多种LDAP插件可以使用,在尝试了Simple LDAP Login和Active Directory Integration均告知失败的情况下,只好潜心去看下它的代码,代码倒简单,加上之前写过一个简单的PHP修改LDAP密码的页面,很快就定位问题并圆满解决了。

 

  1、现将问题的修改过程和大家分享,先说下我们LDAP的组织情况,我们在LDAP创建了2个组,一个用户组,一个角色分组,用户分组按照组织架构进行区分,如下图所示:

+dc=foo,dc=bar,dc=com
-+ou=roles
-+ou=users
--+ou=dev
---+ou=dev09
----+uid=zhangsan

   因此我们base_dn为 dc=foo,dc=bar,dc=com

 

 2、Simple LDAP Login插件修改:

      a).下载并启用Simple LDAP Login

      b).在设置项中找到Simple LDAP Login的配置页面,填写Simple选项卡中配置baseDN、LDAP的服务器IP地址,并在Advance配置LDAP Login Attribute为uid。

      c).保存后,发现输入正确的用户名和密码后,无法登陆。

      d).翻了翻插件的源码才发现在Simple-LDAP-Login.php中ldap_auth方法存在问题。他将我们配置的uid、输入的用户名和配置baseDN链接在一起,即得到的是“uid=zhangsan,dc=foo,dc=bar,dc=com”作为用户的dn查找,而该正确的查找应该为“uid=zhangsan,ou=dev1,ou=dev1,ou=dev,ou=users,dc=foo,dc=bar,dc=com”,因此总是提示我们无法登陆。

function ldap_auth( $username, $password, $directory ) {
		$result = false;

		if ( $directory == "ad" ) {
			$result = $this->adldap->authenticate( $username, $password );
		} elseif ( $directory == "ol" ) {
			$this->ldap = ldap_connect( join(' ', (array)$this->get_setting('domain_controllers')), (int)$this->get_setting('ldap_port') );
			ldap_set_option($this->ldap, LDAP_OPT_PROTOCOL_VERSION, (int)$this->get_setting('ldap_version'));
			if ( str_true($this->get_setting('use_tls')) ) {
				ldap_start_tls($this->ldap);
			}
			$ldapbind = @ldap_bind($this->ldap, $this->get_setting('ol_login') .'=' . $username . ',' . $this->get_setting('base_dn'), $password);
			$result = $ldapbind;
		}

		return apply_filters($this->prefix . 'ldap_auth', $result);
	}

         e).修改查找部分,先用uid去查找正确的dn,然后用正确的dn和password去绑定,红色部分为修改。

         f).最终代码如下:

	function ldap_auth( $username, $password, $directory ) {
		$result = false;

		if ( $directory == "ad" ) {
			$result = $this->adldap->authenticate( $username, $password );
		} elseif ( $directory == "ol" ) {
			$this->ldap = ldap_connect( join(' ', (array)$this->get_setting('domain_controllers')), (int)$this->get_setting('ldap_port') );
			ldap_set_option($this->ldap, LDAP_OPT_PROTOCOL_VERSION, (int)$this->get_setting('ldap_version'));
			if ( str_true($this->get_setting('use_tls')) ) {
				ldap_start_tls($this->ldap);
			}
			
			//add by gogo1217
	        $search=@ldap_search($this->ldap,$this->get_setting('base_dn'),$this->get_setting('ol_login') .'=' .$username);
	        $dn=@ldap_get_entries($this->ldap,$search);
	        //从获取到的数组取出用户dn,没有用户dn修改不了密码。
	        for ($i=0; $i<$dn["count"]; $i++){
	            $user_dn= $dn[$i]["dn"];
	        }
            $ldapbind = @ldap_bind($this->ldap, $user_dn, $password);
	        //end by gogo1217

			//$ldapbind = @ldap_bind($this->ldap, $this->get_setting('ol_login') .'=' . $username . ',' . $this->get_setting('base_dn'), $password);
			$result = $ldapbind;
		}

		return apply_filters($this->prefix . 'ldap_auth', $result);
	}

      g).LDAP中姓名中文乱码问题:

这是因为插件中对中文进行了转码,去掉转码即可,删除红颜色部分中的sanitize_title函数包裹:

 

 

 3、Active Directory Integration插件修改:

      a).下载并启用Active Directory Integration;

      b).在配置模块中找到Active Directory Integration Settings,填写Server选项卡中的LDAP的服务器IP地址和baseDN。

      c).保存后,发现输入正确的用户名和密码后,无法登陆。

      d).翻了翻插件的源码,发现使用ad_ldap/adLDAP.php来链接LDAP,他将输入的用户名和我们在User配置页面中用户后缀链接在一起,由于我没有配置后缀即得到的是“zhangsan”作为用户的dn查找,而该正确的查找应该为“uid=zhangsan,ou=dev1,ou=dev1,ou=dev,ou=users,dc=foo,dc=bar,dc=com”,因此总是提示我们无法登陆。

 /**
    * Validate a user's login credentials
    * 
    * @param string $username A user's AD username
    * @param string $password A user's AD password
    * @param bool optional $prevent_rebind
    * @return bool
    */
    public function authenticate($username, $password, $prevent_rebind = false) {
        // Prevent null binding
        if ($username === NULL || $password === NULL) { return false; } 
        if (empty($username) || empty($password)) { return false; }
        
        // Bind as the user        
        $ret = true;
        $this->_bind = @ldap_bind($this->_conn, $username . $this->_account_suffix, $password);
        if (!$this->_bind){ $ret = false; }

      e).修改查找部分,先用uid去查找正确的dn,然后用正确的dn和password去绑定,红色部分为修改。

      f).最终代码如下:

    /**
    * Validate a user's login credentials
    * 
    * @param string $username A user's AD username
    * @param string $password A user's AD password
    * @param bool optional $prevent_rebind
    * @return bool
    */
    public function authenticate($username, $password, $prevent_rebind = false) {
        // Prevent null binding
        if ($username === NULL || $password === NULL) { return false; } 
        if (empty($username) || empty($password)) { return false; }
        
        // Bind as the user        
        $ret = true;
        
        //add by liushimin
        $search=@ldap_search($this->_conn,$this->_base_dn,"uid=".$username);
        $dn=@ldap_get_entries($this->_conn,$search);
        //从获取到的数组取出用户dn,没有用户dn修改不了密码。
        for ($i=0; $i<$dn["count"]; $i++){
            $user_dn= $dn[$i]["dn"];
        }
        //end by liushimin
        $this->_bind = @ldap_bind($this->_conn, $user_dn, $password);

        //$this->_bind = @ldap_bind($this->_conn, $username . $this->_account_suffix, $password);

        if (!$this->_bind){ $ret = false; }

 

 

4、对比2个插件,都是在用户登陆的时候去LDAP检索,并且发现本地没有用户,则创建一个新的用户并赋予指定的角色。

  • 描述: Simple-LDAP-Login.php修改
  • 大小: 116.3 KB
  • 大小: 102.6 KB
  • 大小: 145.1 KB
分享到:
评论
1 楼 gogo1217 2013-10-01  
发现Simple LDAP Login插件的LDAP中文乱码问题,已经更新。

相关推荐

Global site tag (gtag.js) - Google Analytics