I've been trying to write a client/server app that sends multiple files using Java sockets. I've looked through what seems like every thread pertaining to this and I just can't figure out why my code for sending the file is throwing a Broken Pipe exception when I write to the socket. I could really use some help; I've tried every method under the sun and I can't figure it out.
EDIT - Thanks, everyone! The code below works perfectly.
Sender code:
long size;
dos.writeInt(fileArray.length);
//send every file in array
for (File fileArray1 : fileArray) {
int bytesRead = 0;
fis = new FileInputStream(fileArray1);
//send filename
dos.writeUTF(fileArray1.getName());
//send file size (bytes)
dos.writeLong(size = fileArray1.length());
System.out.println("Size: " + size);
//send file
try {
while ((bytesRead = fis.read(buf)) != -1) {
dos.write(buf, 0, bytesRead);
publish(new Progress(null, (int) ((sentByteCount / totalByteCount) * 100)));
}
dos.flush();
} catch (IOException ex) {
System.out.println("ERROR!!!!");
}
//close file stream, has been sent at this point
fis.close();
}
System.out.println("Done sending files");
dos.close();
clientSocket.close();
Receiver Code:
while (true) {
socket = serverSocket.accept();
dis = new DataInputStream(new BufferedInputStream(socket.getInputStream()));
//get number of files being received
numFiles = dis.readInt();
//read all files
for (int i = 0; i < numFiles; i++) {
filename = dis.readUTF();
System.out.println("Receiving " + filename);
size = dis.readLong();
file = new File(filename);
fos = new FileOutputStream(filename);
long total = 0;
int count = 0;
while ((total < size) && ((count = dis.read(buf, 0, (int) Math.min(buf.length, size - total))) > 0)){
fos.write(buf, 0, count);
total += count;
}
fos.close();
System.out.println("Received file " + filename);
}
dis.close();
}//end while
This line in the receiver has a return value which is important!
dis.read(buf);
Most likely, you just want to use readFully()
.
Also, you don't need to create a buffer for each read in the receiver, instead, using the multi-param read methods.
After the edit your write loop is still wrong. You're writing junk at the end of the file with this statement:
fos.write(buf);
A correct way to code that loop is as follows:
long total = 0;
while (total < size && (count = in.read(buffer, 0, size-total > buffer.length ? buffer.length : (int)(size-total))) > 0)
{
fos.write(buffer, 0, count);
total += count;
}
fos.close();
That way you don't write junk at the end of the file, and you don't need the DataInputStream
either.
NB:
You don't need this:
if (!file.exists()) file.createNewFile();
Calling new FileOutputStream()
already does all that. You're just repeating work that the operating system already does, and it will still do it anyway.
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.