Java 套接字文件传输 - 文件传输不完全

标签 java sockets client server

我正在尝试将文件从客户端发送到服务器,但只传输了 ~8kb 的大型文件(~100kb)。例如,png 并不是完全可见的。 我真的不知道为什么它会提前停止。

发送小测试文件(~1 kb)效果很好。

服务器部分:

                    ServerSocket fileSocket = new ServerSocket(p);
                    boolean rdy = false;
                    while (!rdy) {
                        Socket client = fileSocket.accept();
                        String fileName = "C:/" + args[2];
                        String cmd = fileName + "\n";

                        OutputStreamWriter sWriter = new OutputStreamWriter(client.getOutputStream());
                        sWriter.write(cmd, 0, cmd.length());
                        sWriter.flush();

                        InputStream inStream = client.getInputStream();

                        FileOutputStream fileStream = new FileOutputStream(fileName);

                        byte[] buffer = new byte[client.getReceiveBufferSize()];

                        int bytesRead = 0;

                        while ((bytesRead = inStream.read(buffer)) > 0) {
                            fileStream.write(buffer, 0, bytesRead);
                        }
                        fileStream.flush();

                        ta.append("File transfered");

                        inStream.close();
                        fileStream.close();
                        rdy = true;
                    }
                    fileSocket.close();
                    return;

客户端部分:

Socket client = new Socket(ip, port);
        OutputStream outStream = client.getOutputStream();

        FileInputStream fileStream = new FileInputStream(fileName);

        byte[] buffer = new byte[(int) fileStream.getChannel().size()];

        int bytesRead = 0;

        System.out.println("Sending file: " + fileName);

        while ((bytesRead = fileStream.read(buffer)) > 0) {
            outStream.write(buffer, 0, bytesRead);
        }

        outStream.close();
        fileStream.close();
        client.close();
        return;

最佳答案

您的代码的问题在于您假设服务器端立即接收所有数据,但事实并非如此。您应该首先告诉服务器图像文件有多大,然后发送您的数据。在服务器端,您首先读取大小,然后等待从客户端接收到所有数据。

客户端

    Socket client = new Socket(ip, port);
    DataOutputStream outStream = new DataOutputStream(client.getOutputStream());

    FileInputStream fileStream = new FileInputStream(fileName);

    byte[] buffer = new byte[filename.length()];

    int bytesRead = 0;

    System.out.println("Sending file: " + fileName);
    outStream.writeInt(filename.length()); //write image size

    while ((bytesRead = fileStream.read(buffer)) > 0) {
        outStream.write(buffer, 0, bytesRead);
    }

    outStream.close();
    fileStream.close();
    client.close();
    return;

服务器

                ServerSocket fileSocket = new ServerSocket(p);
                boolean rdy = false;
                while (!rdy) {
                    Socket client = fileSocket.accept();
                    String fileName = "C:/" + args[2];
                    String cmd = fileName + "\n";

                    OutputStreamWriter sWriter = new OutputStreamWriter(client.getOutputStream());
                    sWriter.write(cmd, 0, cmd.length());
                    sWriter.flush();

                    DataInputStream inStream = new DataInputStream(client.getInputStream());

                    FileOutputStream fileStream = new FileOutputStream(fileName);

                    while(inStream.available()<4) {} //wait for the size of an int
                    int imagesize = inStream.readInt();

                    byte[] buffer = new byte[imagesize];

                    while(inStream.available()<imagesize) {} //wait for all the image data
                    inStream.readFully(buffer);
                    fileStream.write(buffer, 0, imagesize);
                    fileStream.flush();

                    ta.append("File transfered");

                    inStream.close();
                    fileStream.close();
                    rdy = true;
                }
                fileSocket.close();
                return;

关于Java 套接字文件传输 - 文件传输不完全,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/29047793/

相关文章:

c - ACK真的在最简单的UDP套接字编程中迷失了吗?

ssl - LDAPS - 强制首先提供哪些客户端证书

java - 无法在 Mongodb 中序列化 LocalDate

c# - 套接字,接收序列化异常

c# - 存储从套接字读取的数据以供另一个线程读取的最有效方法是什么?

c++ - thrift cpp示例代码编译报错

client - 如何使用 SQuirreL 从表生成插入脚本

java - CompressedClassSpaceSize 区域是否包含 MaxMetaspaceSize 区域?

创建新对象行时出现 java.lang.NullPointerException

java - 用另一个和所有引用替换 Java 对象实例