FTP服务器打包下载文件的步骤

发布时间:2021-09-04 18:26:24 作者:chen
来源:亿速云 阅读:343

这篇文章主要讲解了“FTP服务器打包下载文件的步骤”,文中的讲解内容简单清晰,易于学习与理解,下面请大家跟着小编的思路慢慢深入,一起来研究和学习“FTP服务器打包下载文件的步骤”吧!

需求:从ftp服务器打包下载文件

解决步骤:1.从ftp服务器把各个文件下载到本地服务器(一般是安装tomcat的服务器,项目自己电脑跑的本地服务器就是自己电脑)指定目录中

2.在本地服务器打包下载好的文件夹打包,返回打包好的File zip

3.zip文件用流写入reponse,达到用户下载效果

准备文件:

// 封装所有需要打包下载的文件地址请求类
public class DownloadPackageReq implements Serializable {// 本地服务器临时存放目录名(尽量唯一.eg:"menutree20200904112125")    private String localTempDirName; // 打包下载本地服务器文件夹名字private List<DownloadPackageListReq> downloadPackageListReqList; // 需要下载所有文件路径和名称
}
// FTPClientUtils:ftp工具类
public static FTPClientUtils init() {   FTPClientUtils ftp = new FTPClientUtils();   ftp.setHost(host);   ftp.setPort(port);   ftp.setUsername(username);   ftp.setPassword(password);   ftp.setBinaryTransfer(true);   ftp.setPassiveMode(false);   ftp.setEncoding("utf-8");   return ftp;
}
/** * 下载一个远程文件到本地的指定文件 * 
 * @param remoteAbsoluteFile *            远程文件名(包括完整路径,eg:/MTL/test/menutree_attachment/file.xlsx) * @param localAbsoluteFile *            本地文件名(包括完整路径) * @param autoClose *            是否自动关闭当前连接 * 
 * @return 成功时,返回true,失败返回false * @throws Exception */public boolean get(String remoteAbsoluteFile, String localAbsoluteFile, boolean autoClose) throws Exception {   OutputStream output = null;   try {
      output = new FileOutputStream(localAbsoluteFile);      return get(remoteAbsoluteFile, output, autoClose);
   } catch (FileNotFoundException e) {      throw new Exception("local file not found.", e);
   } finally {      try {         if (output != null) {
            output.close();
         }
      } catch (IOException e) {         throw new Exception("Couldn't close FileOutputStream.", e);
      }
   }
}
/** * 下载一个远程文件到指定的流 处理完后记得关闭流 * 
 * @param remoteAbsoluteFile * @param output * @param autoClose * @return * @throws Exception */public boolean get(String remoteAbsoluteFile, OutputStream output, boolean autoClose) throws Exception {   try {      FTPClient ftpClient = getFTPClient();      // 处理传输      return ftpClient.retrieveFile(remoteAbsoluteFile, output);
   } catch (IOException e) {      throw new Exception("Couldn't get file from server.", e);
   } finally {      if (autoClose) {
         disconnect(); // 关闭链接      }
   }
}

第一步:

public File downloadMenuTreeAttachment(Integer menutreeId) throws Exception {
    // 从数据库拿到menutreeId对应的所有文件地址List<ResourcesMenutreeListVo> resourcesMenutreeLists = resourcesMenutreeListMapper.selExistingAttachment(menutreeId);DownloadPackageReq req = new DownloadPackageReq();if (CollectionUtils.isNotEmpty(resourcesMenutreeLists)) {req.setLocalTempDirName(resourcesMenutreeLists.get(0).getMenutreeName() + DateUtils.dateTimeNow());List<DownloadPackageListReq> dpList = new ArrayList<>();for(ResourcesMenutreeListVo temp : resourcesMenutreeLists) {DownloadPackageListReq dpReq = new DownloadPackageListReq();
            // 文件名称,用来下载ftp服务器文件修改文件名(因为ftp文件都是uuid名称)String fileName = temp.getModuleName() + "_" + temp.getEngineerName();dpReq.setFileName(fileName);dpReq.setFileFtpUrl(temp.getMenutreeAttachment());dpList.add(dpReq);
        }req.setDownloadPackageListReqList(dpList);
    } else {req.setLocalTempDirName("空菜单树" + DateUtils.dateTimeNow());
    }return ftpService.zipFiles(req);
}
public File zipFiles(DownloadPackageReq req) throws Exception {HttpServletRequest request = ((ServletRequestAttributes) RequestContextHolder.getRequestAttributes()).getRequest();// 本地服务器暂存路径    String localTempDir = request.getSession().getServletContext().getRealPath("/") + req.getLocalTempDirName() + File.separator;logger.info("本地服务器暂存路径:" + localTempDir);File dir = new File(localTempDir);if ( ! dir.exists()) {dir.mkdir();
    }if (CollectionUtils.isNotEmpty(req.getDownloadPackageListReqList())) {List<DownloadPackageListReq> downloadList = req.getDownloadPackageListReqList();FTPClientUtils ftp = FTPClientUtils.init();for(int i=0; i<downloadList.size(); i++) {// 是否关闭传输流(最后一份文件传输完毕关闭)            boolean isCloseStream = false;if (i == downloadList.size() - 1) {
                isCloseStream = true;
            }DownloadPackageListReq temp = downloadList.get(i);String fileFtpUrl = temp.getFileFtpUrl();String suffix = "";if (fileFtpUrl.contains(".") && !fileFtpUrl.endsWith(".")) {// 文件后缀名                suffix = fileFtpUrl.substring(fileFtpUrl.lastIndexOf("."));
            }// 本地服务器存放完整路径(包含文件名)            String localUrl = localTempDir + temp.getFileName() + suffix;// 下载的第一个参数远程路径如果是FTP服务器,就采用服务器完整文件路径(eg:/MTL/test/menutree_attachment/file.xlsx),因为初始化ftp服务器就带了ip端口            boolean result = ftp.get(temp.getFileFtpUrl(), localUrl, isCloseStream);
        }
    }
    // 打包下载好的文件File zipFile = ZipUtil.zip(localTempDir, localTempDir + req.getLocalTempDirName() + ".zip");return zipFile;
}

第二步:

public class ZipUtil {private static Logger logger = Logger.getLogger(ZipUtil.class);/**     * 缓冲器大小     */    private static final int BUFFER = 512;/**     * 压缩方法 (可以压缩空的子目录)     *     * @param srcPath     压缩源路径     * @param zipFileName 目标压缩文件     * @return     */    public static File zip(String srcPath, String zipFileName) {ZipOutputStream zipOutputStream = null;InputStream inputStream = null;File outputZipFile = null;try {// 检查文件是否存在,是的话先删除            outputZipFile = new File(zipFileName);if (outputZipFile.exists()) {
                outputZipFile.delete();
            }File srcFile = new File(srcPath);List<File> fileList = FileUtil.getAllFiles(srcFile);// 所有要压缩的文件            byte[] buffer = new byte[BUFFER];// 缓冲器            ZipEntry zipEntry = null;int readLength = 0;// 每次读出来的长度            zipOutputStream = new ZipOutputStream(new FileOutputStream(zipFileName));for (File file : fileList) {if (file.isFile()) {// 若是文件,则压缩这个文件                    zipEntry = new ZipEntry(getRelativePath(srcPath, file));
                    zipEntry.setSize(file.length());
                    zipEntry.setTime(file.lastModified());
                    zipOutputStream.putNextEntry(zipEntry);

                    inputStream = new BufferedInputStream(new FileInputStream(file));while ((readLength = inputStream.read(buffer, 0, BUFFER)) != -1) {
                        zipOutputStream.write(buffer, 0, readLength);
                    }
                } else {// 若是目录(即空目录)则将这个目录写入zip条目                    zipEntry = new ZipEntry(getRelativePath(srcPath, file) + File.separator);
                    zipOutputStream.putNextEntry(zipEntry);
                }
            } // end for        } catch (FileNotFoundException e) {logger.error("zip fail!", e);
        } catch (IOException e) {logger.error("zip fail!", e);
        } finally {close(inputStream);close(zipOutputStream);
        }// 返回文件输出流        outputZipFile = new File(zipFileName);return outputZipFile;
    }/**     * 关闭流     */    private static void close(Closeable c) {if (c == null)return;try {
            c.close();
        } catch (IOException e) {logger.error("close fail!", e);
        }
        c = null;
    }/**     * 取相对路径 依据文件名和压缩源路径得到文件在压缩源路径下的相对路径     *     * @param dirPath 压缩源路径     * @param file     * @return 相对路径     */    public static String getRelativePath(String dirPath, File file) {File dir = new File(dirPath);String relativePath = file.getName();while (true) {
            file = file.getParentFile();if (file == null) {break;
            }if (file.equals(dir)) {break;
            } else {
                relativePath = file.getName() + "/" + relativePath;
            }
        } // end while        return relativePath;
    }
}

第三步:Controller控制器,Result是自己封装的返回类,可以自定义String之类的返回

public Result downloadMenuTreeAttachment(Integer menutreeId, HttpServletResponse response) {BufferedInputStream bis = null;OutputStream os = null;try {File file = resourcesMenutreeListService.downloadMenuTreeAttachment(menutreeId);
        response.reset();
        response.setCharacterEncoding("utf-8");
        response.setContentLength((int) file.length());// 设置content-disposition响应头控制浏览器以下载的形式打开文件,中文文件名要使用URLEncoder.encode方法进行编码,否则会出现文件名乱码        response.setHeader("content-disposition", "attachment;filename=" + URLEncoder.encode(file.getName(), "UTF-8"));
        bis = new BufferedInputStream(new FileInputStream(file));
        os = response.getOutputStream();byte[] buff = new byte[1024];int i = 0;while ((i = bis.read(buff)) != -1) {
            os.write(buff, 0, i);
            os.flush();
        }
    } catch (Exception e) {log.error("{}",e);return ResultGenerator.genFailResult("下载失败");
    } finally {try {
            bis.close();
            os.close();
        } catch (IOException e) {
            e.printStackTrace();
        }
    }return ResultGenerator.genSuccessResult();
}

感谢各位的阅读,以上就是“FTP服务器打包下载文件的步骤”的内容了,经过本文的学习后,相信大家对FTP服务器打包下载文件的步骤这一问题有了更深刻的体会,具体使用情况还需要大家实践验证。这里是亿速云,小编将为大家推送更多相关知识点的文章,欢迎关注!

推荐阅读:
  1. python从ftp服务器下载文件的示例
  2. 利用setuptools打包python程序的方法步骤

免责声明:本站发布的内容(图片、视频和文字)以原创、转载和分享为主,文章观点不代表本网站立场,如果涉及侵权请联系站长邮箱:is@yisu.com进行举报,并提供相关证据,一经查实,将立刻删除涉嫌侵权内容。

ftp 服务器

上一篇:怎么用Django动态随机生成温度并在前端实时动态展示

下一篇:MySQL中的隐藏列的具体查看方法

相关阅读

您好,登录后才能下订单哦!

密码登录
登录注册
其他方式登录
点击 登录注册 即表示同意《亿速云用户服务条款》