2012-04-11 2 views
0

J'ai une application de serveur client où j'utilise java serversocket (côté serveur) et sockets (côté client) avec la fonction de sélection java.nio. J'échange des messages entre le client et le serveur en utilisant des objets sérialisés via ObjectInput/Output Streams.StreamCorruptedException avec plusieurs paquets reçus

Voici le code scala pour recevoir le message du serveur qui est assez standard

enter code here 

var msg:CommunicationMessage = null 
    var buf:ByteBuffer = ByteBuffer.allocate(1024); 
    var numBytesRead:Int = 0 

    try { 
     // Clear the buffer and read bytes from socket 
     buf.clear(); 
     //println("Before Read") 



     numBytesRead = sChannel.read(buf) 


     //println("After Read " + numBytesRead) 


     numBytesRead match { 

      case -1 => 
      println("Something Wrong with the Channel") 

      case 0 => 
      //println("Nothing to read") 

      case _ => 
      //println("Read some bytes") 
      // To read the bytes, flip the buffer 
      buf.flip(); 

      // Read the bytes from the buffer ...; 
      // see Getting Bytes from a ByteBuffer 
      val bis:ByteArrayInputStream = new ByteArrayInputStream (buf.array()); 
      val ois:ObjectInputStream = new ObjectInputStream (bis); 
      msg = ois.readObject().asInstanceOf[CommunicationMessage]; 

      println("\n\n") 
      println("Received Message from Server") 

      msg.msgType match { 

       case CommunicationConstants.COMM_MSG_TYPE_RSP => 
        println("updating server info") 
        updateServerInfo(msg.msgData) 

       case CommunicationConstants.COMM_MSG_TYPE_IND => 
        if (serverAccepted) updateClientUI(msg) 

      } 

     } 

    } catch { 

     case e:StreamCorruptedException => 
     println("Stream Corruption Exception received " + e.getCause()) 

     case e:IOException => 
     // Connection may have been closed 
     println("IO Exception received" + e.getCause()) 
    } 
enter code here 

Tout fonctionne bien sauf pour des situations où le serveur écrit plusieurs messages dans un laps de temps très court et que le client les reçoit ensemble dans le tampon et provoque StreamCorruptedException. Si je comprends bien, l'objectinputstream ne peut pas délimiter entre plusieurs objets sérialisés dans le flux d'octets entrant donc il renvoie cette erreur de flux invalide. Aussi même j'ai mis l'exception pour l'attraper, le programme se bloque toujours.

Ce qui pourrait être une solution pour cela. ?

1) Créer mes propres délimiteurs dans le message en fonction d'un certain champ de longueur pour identifier les limites du message.

2) J'ai également lu quelque part pour fermer le socket après chaque réception et commencer un nouveau. Je ne sais pas comment cela va vous aider.

Plz suggérer.

Merci à l'avance

Répondre

0

Vous devez envoyer la longueur de l'avant ObjectOutputStream empaqueté son contenu. Ensuite, vous savez exactement combien de données entrantes appartiennent à chaque flux et vous pouvez construire votre ByteArrayInputStream en conséquence.

Questions connexes