Re: Can't Get Network I/O To Write And Read Properly...
import java.io.*;
import java.net.*;
public class SimpleClient {
Socket socket;
String fileName;
int fileBytes;
public void go() {
try {
//Start a new socket to get the info
socket = new Socket("127.0.0.1",7575);
InputStreamReader isr = new InputStreamReader(socket.getInputStream());
BufferedReader reader = new BufferedReader(isr);
fileName = reader.readLine();
fileBytes = Integer.parseInt(reader.readLine());
socket.close();
//Socket to handle file transfer
socket = new Socket("127.0.0.1",7575);
byte[] bytes = new byte[fileBytes];
InputStream is = socket.getInputStream();
for(int i=0;i<fileBytes;i++) {
is.read(bytes);
}
//Stores the file in a new directory in your system's default directory
File dir = new File("/TestApp");
if(!dir.exists()) {
dir.mkdir();
}
FileOutputStream fos = new FileOutputStream("/TestApp/"+fileName);
BufferedOutputStream bos = new BufferedOutputStream(fos);
bos.write(bytes,0,bytes.length);
bos.close();
socket.close();
System.out.println("Transfer Complete");
} catch (UnknownHostException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
}
}
In RED
Re: Can't Get Network I/O To Write And Read Properly...
Ah ok see I think I changed that later after posting it here. I will re-add and try again.
Re: Can't Get Network I/O To Write And Read Properly...
Whoa... yes ok. It writes a bunch of data and then a seemingly infinite number of "-1" returns. So the stream was writing data even though it had ended... One file actually ran my JVM out of memory. So, in short, my idea to use a FOR loop was awful. Right... well here is an updated version of the original program using a while loop. It's still not working though... it writes a file that is several times larger than the original file.
Code java:
[CODE] protected void sendFile() throws IOException {
if((file.length())<63000) {
byte[] bytes = new byte[(int)file.length()];
buffin = new BufferedInputStream(new FileInputStream(file));
buffin.read(bytes,0,bytes.length);
out = sock.getOutputStream();
out.write(bytes,0,bytes.length);
out.close();
} else {
//int read;
byte[] bytes = new byte[64000];
buffin = new BufferedInputStream(new FileInputStream(file));
out = sock.getOutputStream();
while(buffin.read()!=-1) {
int read = buffin.read(bytes,0,bytes.length);
System.out.println(read);
out.write(bytes,0,bytes.length);
}
out.flush();
}
}
protected void receiveFile() throws IOException {
if(fileBytes<63000) {
byte[] bytes = new byte[fileBytes];
in = sock.getInputStream();
System.out.println(in.available());
in.read(bytes,0,fileBytes);
fos = new FileOutputStream("/Datawire/"+fileName);
buffout = new BufferedOutputStream(fos);
buffout.write(bytes,0,bytes.length);
buffout.close();
} else {
byte[] bytes = new byte[64000];
in = sock.getInputStream();
fos = new FileOutputStream("/Datawire/"+fileName);
buffout = new BufferedOutputStream(fos);
while(in.read()!=-1) {
in.read(bytes,0,bytes.length);
buffout.write(bytes,0,bytes.length);
}
buffout.close();
}
}[/CODE]
Re: Can't Get Network I/O To Write And Read Properly...
The code you just posted looks a mess. You can fix the simple program you gave me to work. Go back and work on that.
For the first pass, don't mix the reading and writing. Just read in all of the data.
Look at using all of the args to the read(byte[], start, length) method.
Adjust the start and length as you read.
When you get that logic working, then try merging the writing into the loop with the reading.
You need to use the number of bytes read in your logic.
What happens to the byte that is read here?
Re: Can't Get Network I/O To Write And Read Properly...
Quote:
Originally Posted by
Norm
What happens to the byte that is read here?
It's meant only as a check... oh does that remove a byte? Hmmm. I see. Ok... could you give me an example of adjusting the start variable?
Re: Can't Get Network I/O To Write And Read Properly...
Here's a way to work out the logic. Say you are going to read a total of 10 bytes.
On the first read you use start=0 and length=10
But you only read 3 bytes into the buffer.
Now compute what the start and the length should be for the next read. It needs to be past the last
If the next read reads 4 bytes
Now where should start and length be for the next read.
Continue until you have read all 10 bytes.
You advance start and decrement length as you go.
Re: Can't Get Network I/O To Write And Read Properly...
Like this?
Code java:
[CODE] protected void sendFile() throws IOException {
if((file.length())<63000) {
byte[] bytes = new byte[(int)file.length()];
buffin = new BufferedInputStream(new FileInputStream(file));
buffin.read(bytes,0,bytes.length);
out = sock.getOutputStream();
out.write(bytes,0,bytes.length);
out.close();
} else {
byte[] bytes = new byte[(int)file.length()];
buffin = new BufferedInputStream(new FileInputStream(file));
out = sock.getOutputStream();
int bytesRead = buffin.read(bytes,0,bytes.length);
int pos = bytesRead;
out.write(bytes,0,bytesRead);
while(bytesRead !=-1) {
bytesRead = buffin.read(bytes,pos,bytes.length - pos);
if(bytesRead !=-1) {
out.write(bytes,pos,bytes.length-pos);
pos += bytesRead;
}
}
out.flush();
}
}
protected void receiveFile() throws IOException {
if(fileBytes<63000) {
byte[] bytes = new byte[fileBytes];
in = sock.getInputStream();
System.out.println(in.available());
in.read(bytes,0,fileBytes);
fos = new FileOutputStream("/Datawire/"+fileName);
buffout = new BufferedOutputStream(fos);
buffout.write(bytes,0,bytes.length);
buffout.close();
} else {
byte[] bytes = new byte[64000];
in = sock.getInputStream();
fos = new FileOutputStream("/Datawire/"+fileName);
buffout = new BufferedOutputStream(fos);
int bytesRead = in.read(bytes,0,bytes.length);
int pos = bytesRead;
buffout.write(bytes,0,bytesRead);
while(bytesRead !=-1) {
bytesRead = in.read(bytes,pos,bytes.length - pos);
if(bytesRead !=-1) {
out.write(bytes,pos,bytes.length-pos);
pos += bytesRead;
}
}
buffout.flush();
}
}[/CODE]
I know this isn't the TestApp but they run on virtually the same concept. And this one was easier to edit since it was already moving in that direction. I will make the changes to the test app as well though.
Re: Can't Get Network I/O To Write And Read Properly...
JFYI, the 64k limit is the default ServerSocket receive buffer size (see ServerSocket.setReceiveBufferSize(..)).
It pays to read the API docs of the classes involved... ;)
Re: Can't Get Network I/O To Write And Read Properly...
No, that's way too complicated. The loop I was talking about is about 12 statements total.
It doesn't have any max record size test. It adjusts the start pointer and the length as the data is read into the one buffer that the code had set to hold the incoming file.
Re: Can't Get Network I/O To Write And Read Properly...
Quote:
Originally Posted by
dlorde
Oh trust me I spend A LOT of time on the API. I must've missed that though... thanks for your help!
Re: Can't Get Network I/O To Write And Read Properly...
Quote:
Originally Posted by
Norm
No, that's way too complicated. The loop I was talking about is about 12 statements total.
It doesn't have any max record size test. It adjusts the start pointer and the length as the data is read into the one buffer that the code had set to hold the incoming file.
I got it to work! Here is the final code:
Code java:
[CODE]
protected void sendFile() throws IOException {
if((file.length())<63000) {
byte[] bytes = new byte[(int)file.length()];
buffin = new BufferedInputStream(new FileInputStream(file));
buffin.read(bytes,0,bytes.length);
out = sock.getOutputStream();
out.write(bytes,0,bytes.length);
out.close();
} else {
byte[] bytes = new byte[32000];
buffin = new BufferedInputStream(new FileInputStream(file));
out = sock.getOutputStream();
int bytesRead;
while((bytesRead = buffin.read(bytes))>0) {
out.write(bytes,0,bytesRead);
}
out.close();
}
}
protected void receiveFile() throws IOException {
if(fileBytes<63000) {
byte[] bytes = new byte[fileBytes];
in = sock.getInputStream();
System.out.println(in.available());
in.read(bytes,0,fileBytes);
fos = new FileOutputStream("/Datawire/"+fileName);
buffout = new BufferedOutputStream(fos);
buffout.write(bytes,0,bytes.length);
buffout.close();
} else {
byte[] bytes = new byte[32000];
in = sock.getInputStream();
fos = new FileOutputStream("/Datawire/"+fileName);
buffout = new BufferedOutputStream(fos);
int bytesRead;
while((bytesRead = in.read(bytes))>0) {
buffout.write(bytes,0,bytesRead);
}
buffout.close();
}
}
[/CODE]
NOTE: I only use the size test for performance reasons. If the file is below the server's limit, there is no point in chunking it. It makes more sense to send it straight through. I'm sure it would work by simply using chunked data all the time, but I figure handling smaller amounts of data directly means I can have larger chunk sizes for larger file sizes.
It was really only a performance thing I suppose.... correct me if I'm wrong.
Re: Can't Get Network I/O To Write And Read Properly...
Looks like it should work.