2012-01-31 49 views
0

我試圖從Activiti使用Apache目錄的LDAP API連接到Active Directory。我想我已經設法驗證了我的用戶,但後來對用戶的查詢什麼都沒有發現。使用Apache目錄的LDAP API調用Active Directory

這裏是我的Java代碼:

package com.abc.activiti.ldap; 

import org.activiti.engine.ActivitiException; 
import org.activiti.engine.identity.User; 
import org.activiti.engine.impl.Page; 
import org.activiti.engine.impl.UserQueryImpl; 
import org.activiti.engine.impl.persistence.entity.UserEntity; 
import org.activiti.engine.impl.persistence.entity.UserManager; 
import org.apache.directory.ldap.client.api.LdapConnection; 
import org.apache.directory.ldap.client.api.exception.LdapException; 
import org.apache.directory.ldap.client.api.message.BindResponse; 
import org.apache.directory.ldap.client.api.message.SearchResponse; 
import org.apache.directory.ldap.client.api.message.SearchResultEntry; 
import org.apache.directory.shared.ldap.cursor.Cursor; 
import org.apache.directory.shared.ldap.entry.EntryAttribute; 
import org.apache.directory.shared.ldap.filter.SearchScope; 
import org.apache.directory.shared.ldap.message.ResultCodeEnum; 
import org.apache.mina.core.session.IoSession; 
import org.slf4j.LoggerFactory; 
import org.slf4j.Logger; 

import java.io.IOException; 
import java.util.ArrayList; 
import java.util.List; 

public class LDAPUserManager extends UserManager { 
    private final static Logger logger = LoggerFactory.getLogger(LDAPUserManager.class); 

    private LDAPConnectionParams ldapConnectionParams; 

    public LDAPUserManager(LDAPConnectionParams ldapConnectionParams) { 
     this.ldapConnectionParams = ldapConnectionParams; 
    } 

    public Boolean checkPassword(String userId, String password) { 
     Boolean result; 
     LdapConnection connection; 

     String userDN = ldapConnectionParams.getUserPrefix() + "=" + 
       userId + "," + ldapConnectionParams.getUserGroup(); 
     logger.debug("Checking password, using connection string: '" + userDN + "'"); 
     try { 
      connection = openConnection(); 
      BindResponse bindResponse = connection.bind(userDN, password); 
      result = bindResponse.getLdapResult().getResultCode() == ResultCodeEnum.SUCCESS; 
     } catch (LdapException e) { 
      throw new ActivitiException("LDAP exception while binding", e); 
     } catch (IOException e) { 
      throw new ActivitiException("IO exception while binding", e); 
     } 
     // TODO: move this into a finally clause above 
     closeConnection(connection); 

     return result; 
    } 

    public List<User> findUserByQueryCriteria(Object o, Page page) { 
     List<User> result = new ArrayList<User>(); 

     UserQueryImpl userQuery = (UserQueryImpl)o; 
     StringBuilder queryString = new StringBuilder(); 
     queryString.append("(").append(ldapConnectionParams.getUserPrefix()).append("=") 
       .append(userQuery.getId()).append(")"); 

     logger.debug("Looking for users: '" + queryString + "'"); 
     LdapConnection connection; 

     try { 
      connection = openConnection(); 
      Cursor<SearchResponse> responseCursor = connection.search(
        ldapConnectionParams.getUserGroup(), queryString.toString(), 
        SearchScope.ONELEVEL, 
        "cn", "sAMAccountName", "sn"); 

      logger.debug("Got cursor: " + responseCursor); 

      for (SearchResponse response : responseCursor) { 
       logger.debug("It's a rsponse: " + response); 
      } 

      int maxUsers = 10; 
      while (responseCursor.next() && maxUsers-- > 0) { 
       User user = new UserEntity(); 
       SearchResultEntry searchResponse = (SearchResultEntry)responseCursor.get(); 
       logger.debug("Got item: " + searchResponse); 
       result.add(user); 
      } 
      responseCursor.close(); 
     } catch (LdapException e) { 
      throw new ActivitiException("While searching for user in LDAP", e); 
     } catch (Exception e) { 
      throw new ActivitiException("While searching for user in LDAP", e); 
     } 
     // TODO: move this into a finally clause above 
     closeConnection(connection); 
     logger.debug("Returning users: " + result); 
     return result; 
    } 

    private void closeConnection(LdapConnection connection) { 
     try { 
      connection.unBind(); 
     } catch (Exception e) { 
      e.printStackTrace(); 
     } 
     try { 
      connection.close(); 
     } catch (IOException e) { 
      e.printStackTrace(); 
     } 
    } 

    private LdapConnection openConnection() throws LdapException, IOException { 
     LdapConnection connection = new LdapConnection(
       ldapConnectionParams.getLdapServer(), 
       ldapConnectionParams.getLdapPort()) { 

      public void exceptionCaught(IoSession ioSession, Throwable throwable) throws Exception { 
       logger.error("Exception thrown in " + ioSession, throwable); 
      } 
     }; 
     connection.connect(); 
     return connection; 
    } 

} 

我讀的Spring bean定義的一些東西:

<property name="ldapServer" value="secret"/> 
<property name="ldapPort" value="389"/> 
<property name="ldapUser" value="CN=Stefan Blixt,OU=x,OU=x,OU=x,DC=x,DC=x"/> 
<property name="ldapPassword" value="secret"/> 
<property name="userGroup" value="OU=x,OU=x,OU=x,DC=x,DC=x"/> 
<property name="userPrefix" value="CN"/> 

的Activiti將首先運行checkPassword()所在,它返回true,那麼它將運行findUserByQueryCriteria( ),其輸出如下:

DEBUG: com.abc.activiti.ldap.LDAPUserManager - Looking for users: '(CN=Stefan Blixt)' 
DEBUG: com.abc.activiti.ldap.LDAPUserManager - Got cursor: [email protected] 
DEBUG: com.abc.activiti.ldap.LDAPUserManager - Returning users: [] 

我已經設法連接並執行此操作第二查詢在Apache目錄工作室:

Active Directory Studio search snapshot

那一個能給我與斯特凡Blixt條目的結果。

我已經編輯了一些上面的隱私路徑。

任何想法?在進行LDAP用戶搜索時,是否有可能導致零結果的經典罪魁禍首?我嘗試使用uid,sAMAccountName等搜索時 - 總是相同的結果。

回答

4

看起來findUserByQueryCriteria正在創建一個新的LdapConnection,而不是在其上執行bind()。也許你的AD服務器不允許匿名查詢。

+0

D'oh!就是這樣!我在查找有關解決其他問題時尋找綁定的建議,但這次我沒有建立連接。謝謝! – 2012-02-01 09:16:07

相關問題