0
votes

I am using apache commons httpclient 4.3.x along with spring3. I am trying to wire up a connectionpool with it's associated socketconfig instance.

http://hc.apache.org/httpcomponents-client-ga/httpclient/apidocs/org/apache/http/impl/conn/PoolingHttpClientConnectionManager.html

http://hc.apache.org/httpcomponents-core-ga/httpcore/apidocs/org/apache/http/config/SocketConfig.html?is-external=true

My code looks like this:

<bean id="socketConfig" class="org.apache.http.config.SocketConfig" factory-method="custom" init-method="build">
        <property name="soTimeout" value="60000"/>
        <property name="soLinger" value="5" />
</bean>

<bean name="poolingHttpConnectionManager" class="org.apache.http.impl.conn.PoolingHttpClientConnectionManager" depends-on="socketConfig">
        <property name="maxTotal" value="20" />
        <property name="defaultMaxPerRoute" value="20" />
        <property name="defaultSocketConfig" ref="socketConfig" />
</bean>

However, this is not working. The instance type that is used to setDefaultSocketConfig() on PoolingHttpClientConnectionManager is of type SocketConfig.Builder instead of SocketConfig.

What I want to have happen is as follows:

SocketConfig config = SocketConfig.custom()
 .setSoTimeout(60000)
 .setSoLinger(5)
 .build()

So, I expect that the socketConfig bean type should be a SocketConfig instance, not a SocketConfig.Builder instance.

As per spring docs, I thought this should work.

http://docs.spring.io/spring/docs/3.0.x/spring-framework-reference/htmlsingle/spring-framework-reference.html#beans-factory-class-static-factory-method

is there anything I am doing wrong? Or is this just not supported in spring?

2

2 Answers

0
votes

It turns out that the socketconfig builder instance is not designed to work with spring very well.

I had to use a spring beanfactory implementation to create the instance.

The bean class:

import org.apache.http.config.SocketConfig;
import org.springframework.beans.factory.FactoryBean;

public class SocketConfigFactoryBean implements FactoryBean<SocketConfig> {
    int soLinger;
    int soTimeout;

    public SocketConfig getObject() throws Exception {
        return SocketConfig.custom()
                .setSoLinger(soLinger)
                .setSoTimeout(soTimeout)
                .build();
    }

    public Class<?> getObjectType() {
        return SocketConfig.class;
    }

    public boolean isSingleton() {
        return true;
    }

    public int getSoLinger() {
        return soLinger;
    }

    public void setSoLinger(int soLinger) {
        this.soLinger = soLinger;
    }

    public int getSoTimeout() {
        return soTimeout;
    }

    public void setSoTimeout(int soTimeout) {
        this.soTimeout = soTimeout;
    }
}

The bean definition

<bean name="poolingHttpConnectionManager" class="org.apache.http.impl.conn.PoolingHttpClientConnectionManager">
    <property name="maxTotal" value="20" />
    <property name="defaultMaxPerRoute" value="20" />
    <property name="defaultSocketConfig">
        <bean class="org.apache.http.config.SocketConfig" factory-method="custom" init-method="build">
        <bean class="com.ex.spring.beans.factory.SocketConfigFactoryBean">
            <property name="soTimeout" value="60000"/>
            <property name="soLinger" value="5" />
        </bean>
    </property>
</bean>
0
votes

I was able to achieve it by doing the next configuration in spring:

<bean id="socketConfig" class="org.apache.http.config.SocketConfig" factory-method="custom">
    <property name="soTimeout" value="1000" />
    <property name="soLinger" value="5" />
</bean>

<bean name="poolingHttpConnectionManager" class="org.apache.http.impl.conn.PoolingHttpClientConnectionManager">
    <property name="maxTotal" value="20" />
    <property name="defaultMaxPerRoute" value="20" />
    <property name="defaultSocketConfig">
        <bean factory-bean="socketConfig" factory-method="build" />
    </property>
</bean>