Using connection pool with JSCH

后端 未结 3 1589
南笙
南笙 2020-12-19 06:22

I\'m using JSCH for file upload ever sftp. In it\'s current state each thread opens and closes connection when needed.

If it possible to use connection pooling with

相关标签:
3条回答
  • 2020-12-19 06:59

    I wold like to share with you our implementation, We have used Session Manager of jsch-extension library

    First of all you need to implement pool object factory that is responsible for lifecycle of pooled objects:

    public class ChannelSftpConnectionsFactory extends BasePooledObjectFactory<ChannelSftp> {
        private SessionManager sessionManager;
    
        public ChannelSftpConnectionsFactory(final SessionManager sessionManager) {
            this.sessionManager = sessionManager;
        }
    
        //Create and open channel
        @Override
        public ChannelSftp create() throws JSchException {
            ChannelSftp channelSftp = (ChannelSftp) sessionManager.getSession().openChannel("sftp");
            channelSftp.connect();
    
            return channelSftp;
        }
    
        //wrapping
        @Override
        public PooledObject<ChannelSftp> wrap(final ChannelSftp channelSftp) {
            return new DefaultPooledObject<>(channelSftp);
        }
    
        @Override
        //disconnect channel on destroy
        public void destroyObject(final PooledObject<ChannelSftp> pooledObject) {
            ChannelSftp sftp = pooledObject.getObject();
            disconnectChannel(sftp);
        }
    
        void disconnectChannel(final ChannelSftp sftp) {
            if (sftp.isConnected()) {
                sftp.disconnect();
            }
        }
    
        @Override
        //reset channel current folder to home if someone was walking on another folders
        public void passivateObject(final PooledObject<ChannelSftp> p) {
            ChannelSftp sftp = p.getObject();
            try {
                sftp.cd(sftp.getHome());
            } catch (SftpException ex) {
                log.error("Could not reset channel to home folder, closing it");
                disconnectChannel(sftp);
            }
        }
    
        @Override
        //validate object before it is borrowed from pool. If false object will be removed from pool
        public boolean validateObject(final PooledObject<ChannelSftp> p) {
            ChannelSftp sftp = p.getObject();
            return sftp.isConnected() && !sftp.isClosed();
        }
    }
    

    Now you could create pool using configured factory:

    ObjectPool<ChannelSftp> createPool(final SessionManager sessionManager, final GenericObjectPoolConfig<ChannelSftp> poolConfig) {
        return PoolUtils.synchronizedPool(new GenericObjectPool<>(buildFactory(sessionManager), poolConfig));
    }
    
    
    PooledObjectFactory<ChannelSftp> buildFactory(final SessionManager sessionManager) {
        return PoolUtils.synchronizedPooledFactory(new ChannelSftpConnectionsFactory(sessionManager));
    }
    

    This java doc would help you to configure pool properly : https://commons.apache.org/proper/commons-pool/api-2.6.0/org/apache/commons/pool2/impl/BaseGenericObjectPool.html

    Do not forget about correct borrowing and returning of object into pool: https://commons.apache.org/proper/commons-pool/api-2.6.0/org/apache/commons/pool2/ObjectPool.html

     Object obj = null;
    
     try {
         obj = pool.borrowObject();
         try {
             //...use the object...
         } catch(Exception e) {
             // invalidate the object
             pool.invalidateObject(obj);
             // do not return the object to the pool twice
             obj = null;
         } finally {
             // make sure the object is returned to the pool
             if(null != obj) {
                 pool.returnObject(obj);
            }
         }
     } catch(Exception e) {
           // failed to borrow an object
     }
    
    0 讨论(0)
  • 2020-12-19 07:00

    Here's an implementation of Ssh Connection pool http://www.javacodegeeks.com/2013/02/pool-of-ssh-connections-using-apache-keyedobjectpool.html

    you can use grep4j to use this pool https://code.google.com/p/grep4j/source/browse/trunk/src/main/java/org/grep4j/core/command/linux/SessionFactory.java?r=354

    Also make sure you can access the server from the execution machine. For instance if the target server is not in your reach. It'll throw connection timeout.

    0 讨论(0)
  • 2020-12-19 07:13

    For that I would prefer commons-pool. ;)

    0 讨论(0)
提交回复
热议问题