Search code examples
javasocketslimitfile-transfer

Java program won't transfer files larger than 64KB


I am making a program that sends a file from a server to the client. The program itself runs, and works for any file 64KB and under, but when I try to send a file larger than that it only transfers 64KB, for example, I tried sending a 232KB file test.txt, and the program only outputted a 64KB file receivedTest.txt.

Here is the server code

import java.io.BufferedInputStream;
import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
import java.io.OutputStream;
import java.net.ServerSocket;
import java.net.Socket;

public class FileTransferServer {

public static void main(String[] args) throws IOException {
    ServerSocket servsock = new ServerSocket(1234);
    File myFile = new File("C:/Users/Owner/Downloads/test.txt");
    while (true) {
      Socket sock = servsock.accept();
      byte[] mybytearray = new byte[(int) myFile.length()];
      BufferedInputStream bis = new BufferedInputStream(new FileInputStream(myFile));
      bis.read(mybytearray, 0, mybytearray.length);
      OutputStream os = sock.getOutputStream();
      os.write(mybytearray, 0, mybytearray.length);
      os.flush();
      sock.close();
    }
}
}

And this is the client

import java.io.BufferedOutputStream;
import java.io.FileOutputStream;
import java.io.InputStream;
import java.net.Socket;

public class FileTransferClient {
public static void main(String[] argv) throws Exception {
Socket sock = new Socket("127.0.0.1", 1234);
byte[] mybytearray = new byte[409600];
InputStream is = sock.getInputStream();

FileOutputStream fos=newFileOutputStream("C:/Users/Owner/Downloads/receivedTest.txt");
    BufferedOutputStream bos = new BufferedOutputStream(fos);
    int bytesRead = is.read(mybytearray, 0, mybytearray.length);
    bos.write(mybytearray, 0, bytesRead);
    bos.close();
    sock.close();
  }
}

Any help would be appreciated, can't find out what's going on.

EDIT: Thanks everyone, it works now, I changed the client code to this:

import java.io.*;
import java.net.*;

public class FileTransferClient {
  public static void main(String[] argv) throws Exception {
    Socket sock = new Socket("127.0.0.1", 1234);
    byte[] mybytearray = new byte[1024];
    int count;
    InputStream is = sock.getInputStream();
    FileOutputStream fos = new FileOutputStream("C:/Users/Owner/Downloads/receivedTest.jpg");
    BufferedOutputStream bos = new BufferedOutputStream(fos);

    while ((count = is.read(mybytearray)) > 0)
    {
        bos.write(mybytearray, 0, count);
    }
    bos.close();
    sock.close();
  }
}

Solution

  • Usual issues.

    1. You're assuming the file fits into memory.
    2. You're assuming the file size fits into an int.
    3. You're assuming that read() fills the buffer.

    The canonical way to copy streams in java is as follows:

    byte[] buffer = new byte[8192]; // any size greater than 0 will work
    int count;
    while ((count = in,read(buffer)) > 0)
    {
        out.write(buffer, 0, count);
    }
    

    I'm surprised you get as much as 64k from your code. Without a loop, you will only get one socket receive buffer-full, which can be as low as 8k on Windows.