【问题标题】:Android: Send serialized objects interspersed with parameters to serverAndroid:将散布有参数的序列化对象发送到服务器
【发布时间】:2014-01-27 06:39:04
【问题描述】:

情况::我必须向服务器发送一个参数,或者一个序列化的对象。它可以是任何随机顺序。

我做了什么:根据this post,我开发了一个协议,让服务器在我实际发送之前知道我正在发送什么。如果它是任何字符串,它只是通过 PrintWriter.println()。

但就在通过 ObjectInputStream 发送序列化对象之前,我发送了 PrintWriter.println("O")。所以服务器知道它接下来必须期待一个序列化的对象。

问题:我得到了 StreamCorruptedException,尽管在套接字的整个生命周期中我只在客户端使用了一个 ObjectInputStream 实例。是否应该在服务器端做任何事情?

----------- 编辑如下 ---------

客户端:

                PrintWriter out = new PrintWriter(new BufferedWriter(
                new OutputStreamWriter(thisSocket.getOutputStream())),
                true);

                if (!sent){
                    out.println("Dummy");
                    sent = true;
                }

                objectOutputStream.flush();
                objectOutputStream.reset();

                out.println("#SerialO#"); //This param signals the server
                                          //that an object will be sent next.

                if(((calcSum) this.obj).getRemotable()){
                    /*objectOutputStream.flush();
                    objectOutputStream.reset();*/

                        Log.i("ENDPOINT", "Sending Serialized data ...");
                        objectOutputStream.writeObject(this.obj);
                        objectOutputStream.flush();
                        objectOutputStream.reset();

                        // Get the byte array
                        byte[] byteArray = byteArrayOutputStream.toByteArray();
                }

服务器端:

while (!Thread.currentThread().isInterrupted()) {

                try{
                    this.input = new BufferedReader(new InputStreamReader(this.clientSocket.getInputStream()));

                    // NOW DECLARED AND USED IN UpdateUIThread
                    //PrintStream out = new PrintStream(socket.getOutputStream());

                    if(!sent)
                    {
                        flg = this.input.readLine().toString();
                        Log.i("SERVER","SERVER Received False flg as "+flg);
                        sent = true;
                    }
                    else{

                    flg = this.input.readLine().toString();

                    System.out.println("SERVER Received flg as "+flg);

                    if(flg.contains("#SerialO#")){  //Be prepared to
                                              // receive a serilized obj from client

                        //Log.d("SERVER","Received an object");
                        CommunicationThread commThread = new CommunicationThread(this.clientSocket,it);
                        new Thread(commThread).start();
                    }
                    else
                    {
                        //Log.d("SERVER","Received a parameter "+flg);
                        executor = Executors.newFixedThreadPool(5);
                        executor.execute(new updateUIThread(this.clientSocket,flg));
                    }
                  }
                } catch (IOException e) {
                    e.printStackTrace();
                    Log.e("SERVER", "Creation went bad -- "+e.toString());
                    break;
                }
                catch (Exception e)
                {
                    Log.d("CLIENT TAG", "Creation went bad -- "+e.toString());  
                }
            }
        }


...

public CommunicationThread(Socket clientSocket, Intent it) {

            this.clientSocket = clientSocket;

            try {

                Log.d("SERVER","Inside Server's Comm Thread");

                if (mInput==null){
                    Log.i("SERVER","Receiving very first serialized obj");
                    mOutput = new ObjectOutputStream(this.clientSocket.getOutputStream());
                    System.out.println("Inside Server's Comm Thread 2 ");

// EXCEPTION OCCURS IN THE LINE BELOW.
                    mInput = new ObjectInputStream(new BufferedInputStream(this.clientSocket.getInputStream()));
                }

【问题讨论】:

  • 能把发生异常的代码贴出来吗?
  • 嗨尼克。我刚刚用源代码编辑了这个问题。

标签: android serialization stream


【解决方案1】:

如果流和读取器/写入器中的任何一个被缓冲,则您不能在同一个套接字上混合它们。在这种情况下,我会对所有内容都使用对象流。

【讨论】:

  • 嗨,EJP。代替缓冲的写入器/读取器和 BufferedInputStream,它会由普通的写入器/读取器和 InputStream 工作吗?还是我必须对所有内容都使用 ObjectInputStream ?
  • 我尝试了你的建议,EJP。在发送序列化对象之前,我通过 ObjectOutputStream 发送布尔值。这适用于序列化对象的情况。但是当我发送一个字符串并尝试使用 readFully() 在服务器上接收它时,它就挂在该行。
  • 如何发送字符串?如果是你写的here,那就是一团糟。忘了它。我会将所有内容作为对象发送,或者,如果必须的话,使用 writeUTF() 发送字符串 a 并使用 readUTF() 读取它们。如果您要发送对象,则不需要协议来告诉您下一个对象是什么。它的类型告诉你:使用'instanceof'。
  • 嘿 EJP,我正在使用 David 建议的 writeUTF() 和 readUTF() 的组合。我已经在那篇文章中发布了结果的详细信息。
猜你喜欢
  • 1970-01-01
  • 2013-06-11
  • 2015-10-19
  • 2018-09-24
  • 1970-01-01
  • 2014-08-14
  • 2011-09-15
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多