JCA Outbond MessageEndpoint size

105 views Asked by At

I want to send multiple outbound message with my own custom JCA outbound adapter on Liberty application server .

this is my resource adapter :

@Connector(description = "Example Resource Adapter", displayName = "Example Resource Adapter", eisType = "Example Resource Adapter", version = "1.0")
public class ExampleResourceAdapter implements ResourceAdapter {

    private EndpointTarget endpointTarget;
    private MessageEndpointFactory messageEndpointFactory;

    public void start(BootstrapContext bootstrapContext) {
    }

    public void stop() {
    }

    public void endpointActivation(final MessageEndpointFactory messageEndpointFactory, final ActivationSpec activationSpec) {
        this.messageEndpointFactory = messageEndpointFactory;
    }

    public void endpointDeactivation(MessageEndpointFactory messageEndpointFactory, ActivationSpec activationSpec) {
        if (endpointTarget != null) {
            endpointTarget.getMessageEndpoint().release();
        }
    }

    public XAResource[] getXAResources(ActivationSpec[] activationSpecs) {
        return new XAResource[0];
    }

    public void executeRequest(String iid) {
        endpointTarget = new EndpointTarget(messageEndpointFactory, iid);
        endpointTarget.start();
    }      

and this is jca managed connection :

public class ExampleManagedConnection implements ManagedConnection {

    private static Logger log = Logger.getLogger(ExampleManagedConnection.class.getName());

    private PrintWriter logwriter;

    private ExampleManagedConnectionFactory mcf;

    private List<ConnectionEventListener> listeners;

    private ExampleConnectionImpl connection;

    public ExampleManagedConnection(ExampleManagedConnectionFactory mcf) {
        this.mcf = mcf;
        this.logwriter = null;
        this.listeners = Collections.synchronizedList(new ArrayList<>(1));
        this.connection = null;
    }

    public Object getConnection(Subject subject,
                                ConnectionRequestInfo cxRequestInfo) throws ResourceException {
        log.finest("getConnection()");
        connection = new ExampleConnectionImpl(this, mcf);
        return connection;
    }

    public void associateConnection(Object connection) throws ResourceException {
        log.finest("associateConnection()");

        if (connection == null)
            throw new ResourceException("Null connection handle");

        if (!(connection instanceof ExampleConnectionImpl))
            throw new ResourceException("Wrong connection handle");

        this.connection = (ExampleConnectionImpl) connection;
    }

    public void cleanup() throws ResourceException {
        log.finest("cleanup()");
    }

    public void destroy() throws ResourceException {
        log.finest("destroy()");
    }

    public void addConnectionEventListener(ConnectionEventListener listener) {
        log.finest("addConnectionEventListener()");

        if (listener == null) {
            throw new IllegalArgumentException("Listener is null");
        }

        listeners.add(listener);
    }

    public void removeConnectionEventListener(ConnectionEventListener listener) {
        log.finest("removeConnectionEventListener()");
        if (listener == null)
            throw new IllegalArgumentException("Listener is null");
        listeners.remove(listener);
    }

    public PrintWriter getLogWriter() throws ResourceException {
        log.finest("getLogWriter()");
        return logwriter;
    }

    public void setLogWriter(PrintWriter out) throws ResourceException {
        log.finest("setLogWriter()");
        logwriter = out;
    }

    public LocalTransaction getLocalTransaction() throws ResourceException {
        throw new NotSupportedException("getLocalTransaction() not supported");
    }

    public XAResource getXAResource() throws ResourceException {
        throw new NotSupportedException("getXAResource() not supported");
    }

    public ManagedConnectionMetaData getMetaData() throws ResourceException {
        log.finest("getMetaData()");
        return new ExampleManagedConnectionMetaData();
    }

    public void getPreTimeMarketOrders(String iid) {
        ExampleResourceAdapter ExampleResourceAdapter = (ExampleResourceAdapter) mcf.getResourceAdapter();
        ExampleResourceAdapter.executeRequest(iid);
    }
}     

i receive this exception when send more than 500 requests :

javax.resource.spi.RetryableUnavailableException: limit for number of MessageEndpoint proxies reached.  Limit = 500
at com.ibm.ws.ejbcontainer.mdb.BaseMessageEndpointFactory.createEndpoint(BaseMessageEndpointFactory.java:349)
at com.ibm.ws.ejbcontainer.mdb.internal.MessageEndpointFactoryImpl.createEndpoint(MessageEndpointFactoryImpl.java:385)   

How can change JCA adapter Thread Pool in Liberty/OpenLiberty Application Server ?

1

There are 1 answers

1
njr On

Looking at the OpenLiberty source, 500 is a default value that is used absent other configuration.

It looks like you can configure a different max pool size for a bean type. Refer to the section covering com.ibm.websphere.ejbcontainer.poolSize in this document.

That said, your approach seems a bit unconventional in that MessageEndpointFactory is intended for inbound, not outbound communication. Inbound communication involves a Message Driven Bean to receive the inbound messages (which could have a com.ibm.websphere.ejbcontainer.poolSize configured for it).

Your approach of overwriting endpointTarget within executeRequest is also suspicious. @Connector/ResourceAdapter class ExampleResourceAdapter is a singleton, so if you have overlapping executeRequest it will overwrite endpointTarget and only one of them will be released in endpointDeactivation.