zoukankan      html  css  js  c++  java
  • springboot2.1.3配置sftp,自定义sftp连接池(转)

    原文: https://blog.csdn.net/qq_35433926/article/details/91880345

    springboot2.1.3配置sftp,自定义sftp连接池

    项目地址

    项目地址:https://gitee.com/xuelingkang/spring-boot-demo
    完整配置参考com.example.ftp包

    maven: 

    <!-- sftp -->
    <dependency>
        <groupId>com.jcraft</groupId>
        <artifactId>jsch</artifactId>
        <version>0.1.56</version>
    </dependency>
    <!-- commons-pool2 -->
    <dependency>
        <groupId>org.apache.commons</groupId>
        <artifactId>commons-pool2</artifactId>
        <version>2.11.1</version>
    </dependency>
    commons-pool2 配置详解: https://www.jianshu.com/p/e9194bd84e38

    application.yml配置

    sftp:
      host: server02 # 服务器ip
      port: 22 # ssh端口
      username: demofile # 用户名
      password: demo # 密码
      # 连接池参数
      pool:
        max-total: 10
        max-idle: 10
        min-idle: 5

    or application.properties

    sftp.username = bxfc
    sftp.password = root
    sftp.host = 192.168.180.51
    sftp.port = 2222
    sftp.pool.max-total = 10
    sftp.pool.max-idle = 10
    sftp.pool.min-idle = 3
    sftp.poll.maxWaitMillis = 60000

    SftpProperties

    package com.example.ftp;
    
    import com.jcraft.jsch.ChannelSftp;
    import lombok.Data;
    import org.apache.commons.pool2.impl.GenericObjectPoolConfig;
    import org.springframework.boot.context.properties.ConfigurationProperties;
    
    @Data
    @ConfigurationProperties(prefix = "sftp")
    public class SftpProperties {
    
        private String host;
        private int port = 22;
        private String username = "root";
        private String password = "root";
        private Pool pool = new Pool();
    
        public static class Pool extends GenericObjectPoolConfig<ChannelSftp> {
    
            private int maxTotal = DEFAULT_MAX_TOTAL;
            private int maxIdle = DEFAULT_MAX_IDLE;
            private int minIdle = DEFAULT_MIN_IDLE;
    
            public Pool() {
                super();
            }
            @Override
            public int getMaxTotal() {
                return maxTotal;
            }
            @Override
            public void setMaxTotal(int maxTotal) {
                this.maxTotal = maxTotal;
            }
            @Override
            public int getMaxIdle() {
                return maxIdle;
            }
            @Override
            public void setMaxIdle(int maxIdle) {
                this.maxIdle = maxIdle;
            }
            @Override
            public int getMinIdle() {
                return minIdle;
            }
            @Override
            public void setMinIdle(int minIdle) {
                this.minIdle = minIdle;
            }
    
        }
    
    }

    sftp连接工厂

    package com.example.ftp;
    import com.example.exception.ProjectException;
    import com.jcraft.jsch.ChannelSftp;
    import com.jcraft.jsch.JSch;
    import com.jcraft.jsch.JSchException;
    import com.jcraft.jsch.Session;
    import lombok.Data;
    import lombok.extern.slf4j.Slf4j;
    import org.apache.commons.pool2.BasePooledObjectFactory;
    import org.apache.commons.pool2.PooledObject;
    import org.apache.commons.pool2.impl.DefaultPooledObject;
    
    import java.util.Properties;
    
    @Data
    @Slf4j
    public class SftpFactory extends BasePooledObjectFactory<ChannelSftp> {
    
        private SftpProperties properties;
    
        public SftpFactory(SftpProperties properties) {
            this.properties = properties;
        }
    
        @Override
        public ChannelSftp create() {
            try {
                JSch jsch = new JSch();
                Session sshSession = jsch.getSession(properties.getUsername(), properties.getHost(), properties.getPort());
                sshSession.setPassword(properties.getPassword());
                Properties sshConfig = new Properties();
                sshConfig.put("StrictHostKeyChecking", "no");
                sshSession.setConfig(sshConfig);
                sshSession.connect();
                ChannelSftp channel = (ChannelSftp) sshSession.openChannel("sftp");
                channel.connect();
                return channel;
            } catch (JSchException e) {
                throw new ProjectException("连接sfpt失败", e);
            }
        }
    
        @Override
        public PooledObject<ChannelSftp> wrap(ChannelSftp channelSftp) {
            return new DefaultPooledObject<>(channelSftp);
        }
    
        // 销毁对象
        @Override
        public void destroyObject(PooledObject<ChannelSftp> p) {
            ChannelSftp channelSftp = p.getObject();
            channelSftp.disconnect();
        }
    
    }

    sftp连接池

    package com.example.ftp;
    
    import com.example.exception.ProjectException;
    import com.jcraft.jsch.ChannelSftp;
    import lombok.Data;
    import org.apache.commons.pool2.impl.GenericObjectPool;
    
    @Data
    public class SftpPool {
    
        private GenericObjectPool<ChannelSftp> pool;
    
        public SftpPool(SftpFactory factory) {
            this.pool = new GenericObjectPool<>(factory, factory.getProperties().getPool());
        }
    
        /**
         * 获取一个sftp连接对象
         * @return sftp连接对象
         */
        public ChannelSftp borrowObject() {
            try {
                return pool.borrowObject();
            } catch (Exception e) {
                throw new ProjectException("获取ftp连接失败", e);
            }
        }
    
        /**
         * 归还一个sftp连接对象
         * @param channelSftp sftp连接对象
         */
        public void returnObject(ChannelSftp channelSftp) {
            if (channelSftp!=null) {
                pool.returnObject(channelSftp);
            }
        }
    
    }

    sftptemplate 辅助类

    import com.icil.bx.common.config.SftpPool;
    import com.jcraft.jsch.ChannelSftp;
    import com.jcraft.jsch.SftpException;
    import org.apache.commons.io.IOUtils;
    import org.slf4j.Logger;
    import org.slf4j.LoggerFactory;
    import java.io.File;
    import java.io.FileOutputStream;
    import java.io.InputStream;
    import java.util.Vector;
    
    /**
     * @PACKAGE : com.icil.bx.common.utils
     * @Author :  Sea
     * @Date : 8/23/21 9:31 AM
     * @Desc :
     **/
    public class SFTPTemplate {
        private transient Logger log = LoggerFactory.getLogger(this.getClass());
        //结合springboot
        private SftpPool pool;
    
        public SFTPTemplate(SftpPool pool) {
            this.pool = pool;
        }
    
        /**
         * 将输入流的数据上传到sftp作为文件。文件完整路径=basePath+directory
         * @param basePath  服务器的基础路径 eg: /upload
         * @param directory  上传到该目录 eg:  img/  or img/cc/   一定要带上最后的URL,否则返回的url无效
         * @param sftpFileName  sftp端文件名   eg : xx.png
         * @param input   输入流
         */
        public String upload(String basePath,String directory, String sftpFileName, InputStream input) throws Exception {
            ChannelSftp sftp = pool.borrowObject();
            try{
                  log.info("start upload file {}",sftpFileName);
                   mkdir(basePath,directory,sftp);
                   sftp.put(input, sftpFileName);  //上传文件
                   log.info("end upload file {}",sftpFileName);
               } catch (Exception e)
               {
                   throw new Exception(e.getMessage());
               }finally
               {
                   pool.returnObject(sftp);
               }
              return directory+sftpFileName;
        }
    
    
        private void mkdir(String basePath,String directory,ChannelSftp sftp) throws SftpException {
            try
            {
                sftp.cd(basePath);
                sftp.cd(directory);
            }
            catch (SftpException e)
            {
                log.info("目录不存在,创建文件夹");
                //目录不存在,则创建文件夹
                String [] dirs=directory.split("/");
                String tempPath=basePath;
                for(String dir:dirs)
                {
                    if(null== dir || "".equals(dir)) continue;
                    tempPath+="/"+dir;
                    try{
                        sftp.cd(tempPath);
                    }catch(SftpException ex){
                        sftp.mkdir(tempPath);
                        sftp.cd(tempPath);
                    }
                }
            }
        }
    
    
    
        /**
         * 下载文件。
         * @param directory 下载目录
         * @param downloadFile 下载的文件
         * @param saveFile 存在本地的路径
         */
        public void download(String directory, String downloadFile, String saveFile) throws Exception{
            ChannelSftp sftp = pool.borrowObject();
            try{
                if (directory != null && !"".equals(directory)) {
                    sftp.cd(directory);
                }
                File file = new File(saveFile);
                sftp.get(downloadFile, new FileOutputStream(file));
               } catch (Exception e)
               {
                 throw  new Exception(e.getMessage());
               } finally
              {
                  pool.returnObject(sftp);
              }
        }
    
        /**
         * 下载文件
         * @param directory 下载目录
         * @param downloadFile 下载的文件名
         * @return 字节数组
         */
        public byte[] download(String directory, String downloadFile) throws Exception{
            ChannelSftp sftp = pool.borrowObject();
            try
            {
                if (directory != null && !"".equals(directory)) {
                    sftp.cd(directory);
                }
                InputStream is = sftp.get(downloadFile);
                return IOUtils.toByteArray(is);
            } catch (Exception e)
            {
                throw new Exception(e.getMessage());
            }finally
            {
                pool.returnObject(sftp);
            }
        }
    
    
        /**
         * 删除文件
         * @param directory 要删除文件所在目录
         * @param deleteFile 要删除的文件
         */
        public void delete(String directory, String deleteFile) throws Exception{
            ChannelSftp sftp = pool.borrowObject();
            try
            {
                sftp.cd(directory);
                sftp.rm(deleteFile);
            } catch (Exception e)
            {
                throw new Exception(e.getMessage());
            }finally
            {
                pool.returnObject(sftp);
            }
        }
    
    
        /**
         * 列出目录下的文件
         * @param directory 要列出的目录
         */
        public Vector<?> listFiles(String directory) throws Exception {
            ChannelSftp sftp = pool.borrowObject();
            try
            {
                return sftp.ls(directory);
            } catch (Exception e)
            {
                throw new Exception(e.getMessage());
            }finally
            {
                pool.returnObject(sftp);
            }
        }
    }

    主配置类

    package com.example.config;
    
    import com.example.ftp.SftpFactory;
    import com.example.ftp.SftpHelper;
    import com.example.ftp.SftpPool;
    import com.example.ftp.SftpProperties;
    import org.springframework.boot.context.properties.EnableConfigurationProperties;
    import org.springframework.context.annotation.Bean;
    import org.springframework.context.annotation.Configuration;
    
    // ftp配置
    @Configuration
    @EnableConfigurationProperties(SftpProperties.class)
    public class SftpConfig {
    
        // 工厂
        @Bean
        public SftpFactory sftpFactory(SftpProperties properties) {
            return new SftpFactory(properties);
        }
    
        // 连接池
        @Bean
        public SftpPool sftpPool(SftpFactory sftpFactory) {
            return new SftpPool(sftpFactory);
        }
    
        // 辅助类
    
       @Bean
      public SFTPTemplate sftpTemplate(SftpPool sftpPool) {
      return new SFTPTemplate(sftpPool);
      }
     }

    使用方法

    @Autowired
    private SftpTemplate sftpTemplate;
    

      注入辅助类,直接调用方法即可。

    
    
    
  • 相关阅读:
    自然语言交流系统 phxnet团队 创新实训 项目博客 (十一)
    install ubuntu on Android mobile phone
    Mac OS, Mac OSX 与Darwin
    About darwin OS
    自然语言交流系统 phxnet团队 创新实训 项目博客 (十)
    Linux下编译安装qemu和libvirt
    libvirt(virsh命令总结)
    深入浅出 kvm qemu libvirt
    自然语言交流系统 phxnet团队 创新实训 项目博客 (九)
    自然语言交流系统 phxnet团队 创新实训 项目博客 (八)
  • 原文地址:https://www.cnblogs.com/lshan/p/15180336.html
Copyright © 2011-2022 走看看