7

我正在使用 Spring LdapTemplate 类来访问 ldap。我正在使用一个 ldap 连接池(PoolingContextSource 类)来避免在运行时一直创建连接。但是,有时在我的应用程序中会遇到此异常:

javax.servlet.ServletException: org.springframework.ldap.CommunicationException: Connection reset; 
nested exception is javax.naming.CommunicationException: Connection reset [Root exception is java.net.SocketException: Connection reset]; 
Remaining name: 'ou=memberlist,ou=mygroups,o=mycompany.com'

(...)

我的 ldap 类在以下 xml 中定义

<bean id="contextSource" class="com.ibm.tp4.spring.ldap.CustomPoolingContextSource">
  <property name="contextSource" ref="contextSourceTarget" />
  <property name="testWhileIdle" value="true" />
  <property name="minEvictableIdleTimeMillis" value="300000" />
  <property name="timeBetweenEvictionRunsMillis" value="10000"/>
  <property name="dirContextValidator">
    <bean class="org.springframework.ldap.pool.validation.DefaultDirContextValidator" />
  </property>
</bean>

<bean id="contextSourceTarget" class="org.springframework.ldap.core.support.LdapContextSource">
  <property name="url" value="${ldap.url}" />
  <property name="pooled" value="false" />
  <property name="anonymousReadOnly" value="true" />
</bean>

<bean id="ldapTemplate" class="org.springframework.ldap.core.LdapTemplate">
  <constructor-arg ref="contextSource" />
</bean>

<bean id="myLdapResolver" class="com.ibm.tp4.model.service.user.MyLdapResolver">
  <constructor-arg ref="ldapTemplate" />
  <property name="ldapUserSearchBase" value="${ldap.user.search_base}" />
  <property name="ldapUserEmailAddressField" value="${ldap.user.email_address}" />
  <property name="ldapAttributes" value="${ldap.user.attributes}" />
</bean>

有没有人遇到过这个问题并可以提出解决方案?

我考虑过在池属性中使用 testOnReturn 参数,而不是现在使用的连接驱逐器。当我这样做时,当我在浏览器中运行我的 Web 应用程序时收到以下警告:

WARN [org.springframework.ldap.pool.validation.DefaultDirContextValidator] - 
DirContext 'javax.naming.ldap.InitialLdapContext@d150d15' failed validation with an 
exception.javax.naming.OperationNotSupportedException: [LDAP: error code 53 - Unwilling To Perform]; 
Remaining name: ''

不久之后,我得到了这个例外:

org.springframework.dao.DataAccessResourceFailureException: Failed to borrow DirContext from pool.; nested exception is java.util.NoSuchElementException: Could not create a validated object, cause: ValidateObject failed  
org.springframework.ldap.pool.factory.PoolingContextSource.getContext(PoolingContextSource.java:425)

提前致谢。

4

1 回答 1

2

看起来超时定义太低了。Oracle 有一个官方站点,可以让您找出问题的根源,很可能不是“Spring”,而是 Sun Ldap 连接器或您的 Ldap 服务器。很多人反对提供链接,但我根本无法复制此页面,也许您可​​以尝试他们网站上的“原始”声明,看看它是否也会发生。它将使您更接近您的解决方案。(可能是 ldap 超时配置)

http://docs.oracle.com/javase/tutorial/jndi/newstuff/readtimeout.html

env.put(Context.INITIAL_CONTEXT_FACTORY,
    "com.sun.jndi.ldap.LdapCtxFactory");
env.put("com.sun.jndi.ldap.read.timeout", "1000");
env.put(Context.PROVIDER_URL, "ldap://localhost:2001");

Server s = new Server();

try {

    // start the server
    s.start();

   // Create initial context
   DirContext ctx = new InitialDirContext(env);
   System.out.println("LDAP Client: Connected to the Server");
        :
        :
} catch (NamingException e) {
   e.printStackTrace();
}
于 2012-09-18T04:54:36.093 回答