简体   繁体   中英

Sending large files over socket

I got working over socket file sender, it worked perfectly, but I couldn't send large files with it. Always got heap error. Then I changed the code of client, so it would send file in chunks. Now I can send big files, but there is new problem. Now I recieve small files empty and larger files for example videos can't be played. Here is the code of client that sends file:

public void send(File file) throws UnknownHostException, IOException {

    // Create socket
    hostIP = "localhost";
    socket = new Socket(hostIP, 22333);

    //Send file

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

    DataInputStream dis = new DataInputStream(bis);


    OutputStream os = socket.getOutputStream();

    //Sending size of file.
    DataOutputStream dos = new DataOutputStream(os);
    dos.writeUTF(file.getName() + ":" + userName);

    byte[] arr = new byte[1024];
    try {
        int len = 0;
        while ((len = dis.read(arr)) != -1) {
            dos.write(arr, 0, len);

        }
    } catch (IOException ex) {
        ex.printStackTrace();
    }



    dos.flush();

    socket.close();
}

and here is the server code:

void start() throws IOException {

        // Starts server on port.
        serverSocket = new ServerSocket(port);

        int bytesRead;

        while (true) {
            connection = serverSocket.accept();

            in = connection.getInputStream();

            clientData = new DataInputStream(in);

            String[] data = clientData.readUTF().split(":");
            String fileName = data[0];
            String userName = data[1];

            output = new FileOutputStream("C:/" + fileName);
            long size = clientData.readLong();
            byte[] buffer = new byte[1024];

            // Build new file
            while (size > 0 && (bytesRead = clientData.read(buffer, 0, (int) Math.min(buffer.length, size))) != -1) {
                output.write(buffer, 0, bytesRead);
                size -= bytesRead;
            }
            output.close();
        }
    }

You failed to write out the length of the file to the stream in the client:

long size = clientData.readLong();

So that call in the server is reading the first 8 bytes of the actual file and who knows what that quantity is. You don't have to read the length from the stream since you only wrote a single file. After reading the filename, and username (not very secure is it?) you can just read the stream until EOF. If you ever wanted to send multiple files over the same open socket then you'd need to know the length before reading the file.

Also your buffers for reading are way to small. You should be at a minimum of 8192 instead of 1024. And you'll want to put all .close() in a finally block to make sure your server and clients shutdown appropriately if there is an exception ever.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM