前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >SpringBoot整合自定义FTP文件连接池

SpringBoot整合自定义FTP文件连接池

作者头像
庞小明
发布2019-05-25 17:59:28
3.3K0
发布2019-05-25 17:59:28
举报
文章被收录于专栏:pangguoming

说明:通过GenericObjectPool实现的FTP连接池,记录一下以供以后使用 环境: JDK版本1.8 框架 :springboot2.1 文件服务器: Serv-U 1.引入依赖

<!--ftp文件上传--> <dependency> <groupId>commons-net</groupId> <artifactId>commons-net</artifactId> <version>3.3</version> </dependency> <!--自定义连接池--> <dependency> <groupId>org.apache.commons</groupId> <artifactId>commons-pool2</artifactId> <version>2.4.2</version> </dependency> 2.创建ftp.properties

ftp.Host=192.168.xx.xx 本机ip ftp.Port=21 ftp.UserName=root ftp.PassWord=root ftp.workDir=/images ftp.encoding=utf-8 ftp.root=/ ftp.MaxTotal=100 ftp.MinIdel=2 ftp.MaxIdle=5 ftp.MaxWaitMillis=3000 3.创建配置类FtpConfig

package com.hcq.demo.util;

import org.springframework.boot.context.properties.ConfigurationProperties; import org.springframework.context.annotation.PropertySource; import org.springframework.stereotype.Component;

import java.util.HashMap; import java.util.Map; import java.util.Set;

/** * fileName:FtpConfig * description: * author:hcq * createTime:2019-03-15 15:04 */

@Component @ConfigurationProperties(prefix="ftp") @PropertySource("classpath:ftp.properties") public class FtpConfig { private String Host; private int Port; private String UserName; private String PassWord; private String workDir; private String encoding; private String root; private int MaxTotal; private int MinIdel; private int MaxIdle; private int MaxWaitMillis; .......省略get set } 4.创建FtpClientFactory工厂类

package com.hcq.demo.util;

import org.apache.commons.net.ftp.FTP; import org.apache.commons.net.ftp.FTPClient; import org.apache.commons.pool2.PooledObject; import org.apache.commons.pool2.impl.DefaultPooledObject; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.stereotype.Component; import org.apache.commons.pool2.PooledObjectFactory;

import java.io.IOException;

/** * fileName:FtpClientFactory * description: * author:hcq * createTime:2019-03-18 19:49 */ @Component public class FtpClientFactory implements PooledObjectFactory<FTPClient> { @Autowired FtpConfig config; //创建连接到池中 @Override public PooledObject<FTPClient> makeObject() { FTPClient ftpClient = new FTPClient();//创建客户端实例 return new DefaultPooledObject<>(ftpClient); } //销毁连接,当连接池空闲数量达到上限时,调用此方法销毁连接 @Override public void destroyObject(PooledObject<FTPClient> pooledObject) { FTPClient ftpClient = pooledObject.getObject(); try { ftpClient.logout(); if (ftpClient.isConnected()) { ftpClient.disconnect(); } } catch (IOException e) { throw new RuntimeException("Could not disconnect from server.", e); } } //链接状态检查 @Override public boolean validateObject(PooledObject<FTPClient> pooledObject) { FTPClient ftpClient = pooledObject.getObject(); try { return ftpClient.sendNoOp(); } catch (IOException e) { return false; } } //初始化连接 @Override public void activateObject(PooledObject<FTPClient> pooledObject) throws Exception { FTPClient ftpClient = pooledObject.getObject(); ftpClient.connect(config.getHost(),config.getPort()); ftpClient.login(config.getUserName(), config.getPassWord()); ftpClient.setControlEncoding(config.getEncoding()); ftpClient.changeWorkingDirectory(config.getWorkDir()); ftpClient.setFileType(FTP.BINARY_FILE_TYPE);//设置上传文件类型为二进制,否则将无法打开文件 } //钝化连接,使链接变为可用状态 @Override public void passivateObject(PooledObject<FTPClient> pooledObject) throws Exception { FTPClient ftpClient = pooledObject.getObject(); try { ftpClient.changeWorkingDirectory(config.getRoot()); ftpClient.logout(); if (ftpClient.isConnected()) { ftpClient.disconnect(); } } catch (IOException e) { throw new RuntimeException("Could not disconnect from server.", e); } } //用于连接池中获取pool属性 public FtpConfig getConfig() { return config; } } 5.创建FtpPool连接池

package com.hcq.demo.util;

import org.apache.commons.net.ftp.FTPClient; import org.apache.commons.pool2.impl.GenericObjectPool; import org.apache.commons.pool2.impl.GenericObjectPoolConfig; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.stereotype.Component;

/** * fileName:ftpPool * description:FTP连接池 * 1.可以获取池中空闲链接 * 2.可以将链接归还到池中 * 3.当池中空闲链接不足时,可以创建链接 * author:hcq * createTime:2019-03-16 9:59 */ @Component public class FtpPool { FtpClientFactory factory; private final GenericObjectPool<FTPClient> internalPool; //初始化连接池 public FtpPool(@Autowired FtpClientFactory factory){ this.factory=factory; FtpConfig config = factory.getConfig(); GenericObjectPoolConfig poolConfig = new GenericObjectPoolConfig(); poolConfig.setMaxTotal(config.getMaxTotal()); poolConfig.setMinIdle(config.getMinIdel()); poolConfig.setMaxIdle(config.getMaxIdle()); poolConfig.setMaxWaitMillis(config.getMaxWaitMillis()); this.internalPool = new GenericObjectPool<FTPClient>(factory,poolConfig); } //从连接池中取连接 public FTPClient getFTPClient() { try { return internalPool.borrowObject(); } catch (Exception e) { e.printStackTrace(); return null; } } //将链接归还到连接池 public void returnFTPClient(FTPClient ftpClient) { try { internalPool.returnObject(ftpClient); } catch (Exception e) { e.printStackTrace(); } } /** * 销毁池子 */ public void destroy() { try { internalPool.close(); } catch (Exception e) { e.printStackTrace(); } } }

6.创建FtpUtil类

package com.hcq.demo.util;

import org.apache.commons.net.ftp.FTPClient; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.core.io.ResourceLoader; import org.springframework.http.ResponseEntity; import org.springframework.stereotype.Component; import org.springframework.web.multipart.MultipartFile;

import javax.servlet.http.HttpServletResponse; import java.io.*; import java.util.UUID;

/** * fileName:FTP工具类 * description:提供文件上传和下载 * author:hcq * createTime:2019-03-16 8:55 */ @Component public class FtpUtil { @Autowired FtpConfig config; @Autowired private ResourceLoader resourceLoader; @Autowired FtpPool pool; /** * Description: 向FTP服务器上传文件 * * @Version2.0 * @param file * 上传到FTP服务器上的文件 * @return * 成功返回文件名,否则返回null */ public String upload(MultipartFile file) throws Exception { FTPClient ftpClient = pool.getFTPClient(); //开始进行文件上传 String fileName=UUID.randomUUID()+file.getOriginalFilename().substring(file.getOriginalFilename().lastIndexOf(".")); InputStream input=file.getInputStream(); try { boolean result=ftpClient.storeFile(fileName,input);//执行文件传输 if(!result){//上传失败 throw new RuntimeException("上传失败"); } }catch(Exception e){ e.printStackTrace(); return null; }finally {//关闭资源 input.close(); System.out.println("开始归还连接"); pool.returnFTPClient(ftpClient);//归还资源 } return fileName; } /** * Description: 从FTP服务器下载文件 * * @Version1.0 * @param fileName * FTP服务器中的文件名 * @param resp * 响应客户的响应体 */ public void downLoad(String fileName,HttpServletResponse resp) throws IOException { FTPClient ftpClient = pool.getFTPClient(); resp.setContentType("application/force-download");// 设置强制下载不打开 MIME resp.addHeader("Content-Disposition", "attachment;fileName="+fileName);// 设置文件名 //将文件直接读取到响应体中 OutputStream out = resp.getOutputStream(); ftpClient.retrieveFile(config.getWorkDir()+"/"+fileName, out); out.flush(); out.close(); pool.returnFTPClient(ftpClient); } /** * Description: 从FTP服务器读取图片 * * @Version1.0 * @param fileName * 需要读取的文件名 * @return * 返回文件对应的Entity */ public ResponseEntity show(String fileName){ String username=config.getUserName(); String password=config.getPassWord(); String host=config.getHost(); String work=config.getWorkDir(); //ftp://root:root@192.168.xx.xx/+fileName return ResponseEntity.ok(resourceLoader.getResource("ftp://"+username+":"+password+"@"+host+work+"/"+fileName)); }

}

本文参与 腾讯云自媒体同步曝光计划,分享自作者个人站点/博客。
原始发表:2019-05-23 ,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档