简体   繁体   中英

data transfer not working using ObjectOutputStream.writeObject()

I created a android to pc client-server app, and throughout my app's other features i use ObjectOutputStream.writeObject(AbstractPacket object) to send controls and data b/w my apps and they all works fine, now when i tried to send a file(eg:a small jpg/png file), after sending the file bytes to the server side and recreating the original jpg file, the file is showing that its corrupted and is not displaying, but its size is exact same as sent from the client android app. here's some code,

client side:(file to bytearray)

  byte [] mybytearray  = new byte [(int)myFile.length()];

FileInputStream fis = new FileInputStream(myFile);

BufferedInputStream bis = new BufferedInputStream(fis);

bis.read(mybytearray, 0, mybytearray.length);

String filename= myFile.getName();

FileTransferPacket packet = new FileTransferPacket(mybytearray,mybytearray.length,filename);
TCPconnection.sendPacket(packet);

FileTransferPacket extends the AbstractPacket:

public class FileTransferPacket extends AbstractPacket implements Serializable {


byte[] bytes;
long size;
String filename;

public FileTransferPacket(byte[] bytes,long size,String filename) {
super(Protocol.Command.FILE_TRANSFER);
this.bytes = bytes;
this.size = size;

this.filename = filename;
}

public byte[] getBytes() {
return bytes;
}

public long getSize() {return size; }

public String getFilename() {return filename; }
}

Here's how i send the packet object to the server:

public void sendPacket(AbstractPacket packet) throws IOException {
    connectionOutput.writeObject(packet);
    connectionOutput.flush();
    connectionOutput.reset();

  }

At the server side I read the objects like:

AbstractPacket packet = (AbstractPacket) connectionInput.readObject();

receiver.handleReceiveData(packet, connection);

public synchronized void handleReceiveData(AbstractPacket packet, TcpConnection connection) {

String filename=packet.getFilename();
long size= packet.getSize();

byte [] mybytearray  = new byte [(int)size];

byte[] myByteArray=packet.getBytes();

String userHomeFolder = System.getProperty("user.home");

userHomeFolder+="\\Desktop\\"+filename;

try {
FileOutputStream fos = new FileOutputStream(userHomeFolder);

BufferedOutputStream bos = new BufferedOutputStream(fos);

bos.write(mybytearray, 0 , (int)size);

bos.flush();
fos.close();
bos.close();

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

Can somebody tell me what's actually wrong here, also please suggest how to fix them.

After some searching, i did found that maybe i can fix if i used normal OutputStreams to send only the file's bytearray to server, it could work:

outputStream.write(mybytearray, 0, mybytearray.length);

But in my whole app i used ObjectoutputStream, so how can i include both types of streams on a single socket, also on server side how can i distinguish the incoming data as an Object/bytesbuffer.

You can add control bytes to indicate the type of stream. Here's example code how it works.

It's bit tricky. If possible using different port number would be more simple.

import java.io.*;

public class Main {

    public static void main(String[] args) throws IOException, ClassNotFoundException {
        // File stream.
        FileOutputStream fos = new FileOutputStream("test1.txt");
        BufferedOutputStream bos = new BufferedOutputStream(fos);

        // add controll bytes.
        bos.write(0);
        bos.write("file contents".getBytes());
        bos.close();

        // Object stream.
        FileOutputStream fos2 = new FileOutputStream("test2.txt");
        // add controll bytes.
        fos2.write(1);
        ObjectOutputStream oos = new ObjectOutputStream(fos2);
        Exception serializableObj = new RuntimeException("serialize test");

        oos.writeObject(serializableObj);
        oos.close();

        readStream(new FileInputStream("test1.txt"));
        readStream(new FileInputStream("test2.txt"));
    }

    private static void readStream(InputStream in) throws IOException, ClassNotFoundException {
        int controll = in.read();
        if (controll == 0) { // File stream
            BufferedInputStream bis = new BufferedInputStream(in);
            FileOutputStream fos = new FileOutputStream("test3.txt");
            BufferedOutputStream bos = new BufferedOutputStream(fos);
            byte[] buff = new byte[1024];
            while (true) {
                int ret = bis.read(buff);
                if (ret < 0) {
                    break;
                }
                bos.write(buff, 0, ret);
            }
            in.close();
            bos.close();

            BufferedReader br = new BufferedReader(new FileReader("test3.txt"));
            String line = br.readLine();
            System.out.println("line: " + line);
            assert (line.equals("file contents"));
            br.close();
        } else if (controll == 1) { // Object stream
            ObjectInputStream ois = new ObjectInputStream(in);
            RuntimeException e = (RuntimeException)ois.readObject();
            assert (e instanceof RuntimeException);
            assert (e.getMessage().equals("serialize test"));
            System.out.println("message: " + e.getMessage());
            ois.close();
        }

    }
}

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