【问题标题】:How to compress file in SFTP or FTP server by using Java?如何使用 Java 在 SFTP 或 FTP 服务器中压缩文件?
【发布时间】:2017-03-06 12:54:53
【问题描述】:

我可以在本地计算机上压缩文件,但我想通过 Java 在 SFTP 服务器中压缩 (.zip) 文件。如何传递 URL 以及如何压缩 SFTP 或 FTP 服务器中的文件?

下面是我的本地系统,我需要在 SFTP 中实现相同的功能。

import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.zip.ZipEntry;
import java.util.zip.ZipOutputStream;

public class CompressToZip {

    public static void main(String[] args) throws Exception{
        String pattern = "ddMMyyyy";
        SimpleDateFormat simpleDateFormat = new SimpleDateFormat(pattern);
        String date = simpleDateFormat.format(new Date());
        System.out.println(date);
        String sourceFolderName =  "C:\\Users\\Desktop\\BackUpFiles\\"+date;

        File folder = new File("C:\\Users\\Desktop\\BackUpFileZip");
        String outputFileName = folder+"\\"+date+".zip";
        if(!folder.exists()){
            folder.mkdir();
        }else{
            System.out.println("Folder Exist.....");
        }


        System.currentTimeMillis();
        FileOutputStream fos = new FileOutputStream(outputFileName);
        ZipOutputStream zos = new ZipOutputStream(fos);
        //level - the compression level (0-9)
        zos.setLevel(9);

        System.out.println("Begin to compress folder : " + sourceFolderName + " to " + outputFileName);
        addFolder(zos, sourceFolderName, sourceFolderName);

        zos.close();
        System.out.println("Program ended successfully!");
    }

    private static void addFolder(ZipOutputStream zos,String folderName,String baseFolderName)throws Exception{
        File f = new File(folderName);
        if(f.exists()){

            if(f.isDirectory()){
                //Thank to peter 
                //For pointing out missing entry for empty folder
                if(!folderName.equalsIgnoreCase(baseFolderName)){
                    String entryName = folderName.substring(baseFolderName.length()+1,folderName.length()) + File.separatorChar;
                    System.out.println("Adding folder entry " + entryName);
                    ZipEntry ze= new ZipEntry(entryName);
                    zos.putNextEntry(ze);    
                }
                File f2[] = f.listFiles();
                for(int i=0;i<f2.length;i++){
                    addFolder(zos,f2[i].getAbsolutePath(),baseFolderName);    
                }
            }else{
                //add file
                //extract the relative name for entry purpose
                String entryName = folderName.substring(baseFolderName.length()+1,folderName.length());
                System.out.print("Adding file entry " + entryName + "...");
                ZipEntry ze= new ZipEntry(entryName);
                zos.putNextEntry(ze);
                FileInputStream in = new FileInputStream(folderName);
                int len;
                byte buffer[] = new byte[1024];
                while ((len = in.read(buffer)) > 0) {
                    zos.write(buffer, 0, len);
                }
                in.close();
                zos.closeEntry();
                System.out.println("OK!");

            }
        }else{
            System.out.println("File or directory not found " + folderName);
        }

    }

}

如何给出SFTP或FTP服务器地址的sourceFolderNameoutputFileName

为了连接到 SFTP,我使用以下代码:

public class JschTestDownload {

  public static void main(String s[]) {

       JSch jsch = new JSch();

       Session session = null;
       // Remote machine host name or IP
       String hostName = "xxx.xxx.xx.xxx";
       // User name to connect the remote machine
       String userName = "xxxxx";
       // Password for remote machine authentication
       String password = "xxxx";    
       // Source file path on local machine
       String srcFilePath = "/Inbound/testSFTP.txt";
       // Destination directory location on remote machine

       String destinationLocation = "C:/Users/Desktop/SftpUpDown/TestDownload";
       try {
        // Getting the session
        session = jsch.getSession(userName, hostName,22);

        // Ignore HostKeyChecking
        session.setConfig("StrictHostKeyChecking", "no");                  

        // set the password for authentication
        session.setPassword(password);
        System.out.println("try to get the connection");
        session.connect();
        System.out.println("got the connection");            
        // Getting the channel using sftp
        Channel channel = session.openChannel("sftp");
        channel.connect();
        ChannelSftp sftpChannel = (ChannelSftp) channel;

        sftpChannel.cd("/Inbound/");


        // Exist the channel
         sftpChannel.exit();

         // Disconnect the session
         session.disconnect();

       } catch (JSchException e) {
              e.printStackTrace();

       } catch (SftpException e) {
              e.printStackTrace();
       }
     }
}

通过使用上面的代码,我可以获取文件并放置文件。但我想使用第一个代码压缩 SFTP 服务器中的文件。我需要在我的计算机上运行该代码并在服务器上压缩文件并下载到我的计算机上。 我该怎么做?给我一些指导。

【问题讨论】:

  • 我怎样才能给出这样的 SFTP 服务器的文件路径 "C:\\Users\\Desktop\\BackUpFiles\\"+date".("sftp://userName:pssword@Address/文件夹名/")
  • 不知道,你是什么意思?像什么?您想在哪里提供路径?
  • String sourceFolderName = "C:\\Users\\Desktop\\BackUpFiles\\"+date;文件 f = new File(sourceFolderName);
  • 不,你不能。即使你可以(例如 PHP 可以使用它的协议包装器),它也不会改变任何东西。它仍然会在幕后下载文件。您不能通过任何语法技巧来规避协议的功能!

标签: java ftp sftp jsch zipfile


【解决方案1】:

你不能。无法通过 FTP 或 SFTP 协议就地压缩文件。

您所能做的就是下载文件,在本地压缩并上传回来。你似乎能做的事情。

这并不意味着您必须(临时)将文件存储在本地。您可以使用流在内存中完成所有这些操作。


当然,如果您对服务器有 shell 访问权限,您可以使用 SSH 协议连接并运行zip(或类似的)命令来压缩文件。但这不是 SFTP/FTP。


相关问题:

【讨论】:

  • 是否可以通过ip地址进行,表示系统已连接在我的网络中。并告诉我在不干扰原始文件的情况下制作 zip 的推荐。
  • “是否可以通过 ip 地址进行,表示系统已连接在我的网络中” - 这是什么意思? - “在不干扰原始文件的情况下制作 zip” - 我们不知道您的远程操作系统是什么,它使用什么 shell - 它安装了哪些工具。给我们一些信息。
  • 是否可以通过ip地址进行,表示系统连接在我的网络中:本地网络系统
  • 这并不意味着什么。如果您只有一个 IP 地址,那么机器是在本地网络中还是在 Internet 上的任何地方都没有关系。重要的是服务器提供什么服务。但是,如果机器在本地网络上,我看不到,下载和上传回来有什么问题?应该很快。
  • 文件大小超过每天 100 GB,需要压缩和下载。如果我能够压缩,它只会低于 20 GB。