如何通过 Java 中的套接字发送文件列表

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/11420250/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-10-31 05:02:58  来源:igfitidea点击:

How to send a list of files over a socket in Java

javasockets

提问by ewok

I have used the code hereto send an individual file over a socket. However, I need to be able to send multiple files (basically all files in a directory) over the socket and have the client recognize how the separation between files. Frankly, I am at a complete loss for what to do. Any tips would be helpful.

我已经使用此处的代码通过套接字发送单个文件。但是,我需要能够通过套接字发送多个文件(基本上是目录中的所有文件),并让客户端识别文件之间的分离方式。坦率地说,我完全不知道该怎么做。任何提示都会有所帮助。

NOTE 1:I need a way to send the files in one continuous stream that the client can segregate into individual files. It cannot rely on individual requests from the client.

注意 1:我需要一种方法以一个连续的流发送文件,客户端可以将其分离为单个文件。它不能依赖于来自客户端的个别请求。

NOTE 2:To answer a question I am pretty sure I will get in the comments, no, this is NOThomework.

注意 2:要回答一个问题,我很确定我会在评论中得到解答,不,这不是作业。

EDITit has been suggested that I could send the size of the file before the file itself. How can I do this, as sending a file over the socket is always done in either a predetermined array of bytes, or a single byte individually, rather than the long returned by File.length()

编辑有人建议我可以在文件本身之前发送文件的大小。我该怎么做,因为通过套接字发送文件总是在预先确定的字节数组或单个字节中完成,而不是由返回的长字节File.length()

回答by Eng.Fouad

Here is a full implementation:

这是一个完整的实现:

Sender Side:

发送方:

String directory = ...;
String hostDomain = ...;
int port = ...;

File[] files = new File(directory).listFiles();

Socket socket = new Socket(InetAddress.getByName(hostDomain), port);

BufferedOutputStream bos = new BufferedOutputStream(socket.getOutputStream());
DataOutputStream dos = new DataOutputStream(bos);

dos.writeInt(files.length);

for(File file : files)
{
    long length = file.length();
    dos.writeLong(length);

    String name = file.getName();
    dos.writeUTF(name);

    FileInputStream fis = new FileInputStream(file);
    BufferedInputStream bis = new BufferedInputStream(fis);

    int theByte = 0;
    while((theByte = bis.read()) != -1) bos.write(theByte);

    bis.close();
}

dos.close();

Receiver Side:

接收端:

String dirPath = ...;

ServerSocket serverSocket = ...;
Socket socket = serverSocket.accept();

BufferedInputStream bis = new BufferedInputStream(socket.getInputStream());
DataInputStream dis = new DataInputStream(bis);

int filesCount = dis.readInt();
File[] files = new File[filesCount];

for(int i = 0; i < filesCount; i++)
{
    long fileLength = dis.readLong();
    String fileName = dis.readUTF();

    files[i] = new File(dirPath + "/" + fileName);

    FileOutputStream fos = new FileOutputStream(files[i]);
    BufferedOutputStream bos = new BufferedOutputStream(fos);

    for(int j = 0; j < fileLength; j++) bos.write(bis.read());

    bos.close();
}

dis.close();

I did not test it, but I hope it will work!

我没有测试它,但我希望它会起作用!

回答by Attila

You could send the size of the file first before each file, that way the client will know when the current file is over and expect the next (size). This will allow you to use one contiguous stream for all files.

您可以在每个文件之前首先发送文件的大小,这样客户端将知道当前文件何时结束并期待下一个(大小)。这将允许您对所有文件使用一个连续的流。

回答by sshannin

A very simple way to do it would be to send the file length before sending each file so that you can determine the separation between files.

一个非常简单的方法是在发送每个文件之前发送文件长度,以便您可以确定文件之间的分隔。

Of course, if the receiving process is Java, you can just send Objects.

当然,如果接收进程是Java,直接发送Objects即可。

回答by Pierre

You could zip the files on the client side and send this zipped stream to the server.

您可以在客户端压缩文件并将此压缩流发送到服务器。

e.g: http://www.exampledepot.com/egs/java.util.zip/CreateZip.html

例如:http: //www.exampledepot.com/egs/java.util.zip/CreateZip.html

with ...

和 ...

OutputStream output = connection.getOutputStream();
ZipOutputStream out = new ZipOutputStream(output);

回答by Zechgron

Maybe the fastest way is to automatically zip and unzip the files in your directory into one file, see java.util.zip package

也许最快的方法是自动将目录中的文件压缩和解压为一个文件,参见 java.util.zip 包