Solved

ObjectOutputStream.writeObject() &  ObjectInputStream.readObject()

Posted on 2002-03-08
9
266 Views
Last Modified: 2008-07-03
I am trying to using an applet communicate with a servlet.  I established the communication.  And want to do:

1. applet send "Register" message to the servlet.
2. servlet send "Register Accept" message to the applet.
3. applet send "Hello" to the servlet.
4. servlet say "Hello!  How are you!" back.

step 1 and 2 are success.  But step 3 failed.

Could any one please tell me what is wrong?

=======================================

This is the Servlet.



import java.awt.*;
import java.awt.event.*;
import java.util.*;
import java.net.*;
import java.io.*;
import java.lang.*;
import javax.swing.*;
import java.text.*;
import java.math.*;
import java.lang.Runtime;
import javax.servlet.*;
import javax.servlet.http.*;

public class BLServlet extends HttpServlet {

      // for integration of BLServlet
      // declare variables
      Socket agentsocket = null;
        ObjectInputStream   inputFromApplet = null;
         ObjectOutputStream  outputToApplet = null;

          JFrame frame;
          JTextArea textArea;
      String command = new String();
      String outMsg = new String();

        static boolean realsim;
        static int iStep = 0;
        static int iterStep = 1;


         public void sendToApplet(String info) {

                 try {
                  outputToApplet.writeObject(info);
                  outputToApplet.flush();
            } catch (IOException ie) {
                  textArea.append("Error sending Information to Applet: "+ie);
                  System.exit(-1);
            } // end of try/catch

            try {
                  Thread.sleep(3000);
            } catch (InterruptedException exc) {
                  return;
            }
      } // end of sendInfoToApplet method


      public String receiveFromApplet() {

              String  inMsg = "";
              int     gotIt = 0;

              textArea.append("read from applet\n");

              while (gotIt <= 0 ) {
                           try {
                                 // write info to Applet
                            inMsg = (String) inputFromApplet.readObject();
                            gotIt = 1;
                      } catch (Exception e) {
                        textArea.append("Error reading Information from Applet:\n  "+e+"\n");
                            gotIt--;
                            if (gotIt < -5 ) gotIt = 1;
                        try {
                                Thread.sleep(3000);
                          } catch (InterruptedException exc) {
                              return "";
                          }
                  }
            } // end of try/catch

              textArea.append("read Msg: "+inMsg+"\n");
              return inMsg;
      } // end of sendInfoToApplet method


          public void doPost(HttpServletRequest request, HttpServletResponse response)
            throws ServletException, IOException {

             try {

                        frame = new JFrame("test");
                        frame.setTitle("BlowLoop Servlet");
                        frame.setVisible(true);
                        frame.setSize(800,600);

                        textArea = new JTextArea();
                        textArea.setSize(500, 400);
                        textArea.setBackground(new Color(255, 255, 255));
                        textArea.setLocation(0, 30);

                        JScrollPane sp = new JScrollPane(textArea);
                        sp.setSize(700,500);
                        sp.setLocation(50, 20);

                        Container c = frame.getContentPane();
                        c.setSize(800, 600);
                        c.setLayout(null);
                        c.add(sp);

                        frame.show();
                        textArea.append("start of main\n");

                  inputFromApplet = new ObjectInputStream(request.getInputStream());
                  String inMsg = new String(receiveFromApplet());
      
                  // read the contents of the message
                  if (inMsg.equals("Register")) {
                            outMsg = "Register Accept";
                        }
                        else {
                            outMsg = "MISTAKE2";
                        }

                        textArea.append("output message: "+outMsg+"\n");

                  outputToApplet = new ObjectOutputStream(response.getOutputStream());
                        textArea.append("object output stream: "+outputToApplet.toString()+"\n");
                  sendToApplet(outMsg);

                  inMsg = receiveFromApplet();
                  textArea.append(" - BLServlet - from Applet: "+inMsg+"\n");
                  inputFromApplet.close();

                  if (inMsg.equals("Hello")) {
                            outMsg = "Hello!  How are you!";
                        } else {
                            outMsg = "MISTAKE3";
                        }

                    textArea.append("output message: "+outMsg+"\n");
                  sendToApplet(outMsg);

              } catch (Exception exc) {
                    textArea.append("Exception: "+exc.toString()+"\n");
                  return;
            } // end of try/catch
      } // end of doPost method
}

---------------------------

This is part of the applet:

import java.awt.*;
import java.awt.event.*;
import java.applet.*;
import java.util.*;
import java.net.*;
import java.io.*;
import java.lang.*;
import javax.swing.*;


class AppletThread implements Runnable {

    BlowLoopApplet  _owner;
    ObjectOutputStream  outputToServlet;
    ObjectInputStream  inputFromServlet;


    AppletThread(BlowLoopApplet owner) {
        _owner = owner;
        _owner.textArea.append("Applet thread initial....\n");
    }


    public boolean establishConnection() {

        try {

            _owner.textArea.append("run start...please wait......\n");
            String location = "http://111.111.11.111:8080/servlet/BLServlet";

            URL servletURL = new URL(location);

            URLConnection servletConnection = servletURL.openConnection();
              _owner.textArea.append("URL = "+location+"\n");

            servletConnection.setDoOutput(true);
            servletConnection.setDoInput(true);
            servletConnection.setUseCaches(false);
            servletConnection.setRequestProperty("Content-Type", "application/octet-stream");

            _owner.textArea.append("servlet connection: \n  "+servletConnection.toString()+"\n");

            outputToServlet = new ObjectOutputStream(servletConnection.getOutputStream());

            _owner.textArea.append("output to servelt:  "+outputToServlet.toString()+"\n");

            //outputToServlet.writeObject("Register");
            //outputToServlet.flush();

            write("Register");

            try {
                Thread.sleep(3000);
            } catch (InterruptedException exc) {
                _owner.textArea.append("Cannot Sleep.\n");
                return false;
            }

            inputFromServlet = new ObjectInputStream(servletConnection.getInputStream());
            _owner.textArea.append("input from servlet:   "+inputFromServlet.toString()+"\n");

            String st = read();
            _owner.textArea.append(st+"\n");

        } catch (Exception e){
            _owner.textArea.append("Error in establish connection: \n");
            _owner.textArea.append(e.toString()+"\n");
            _owner.stop();
            _owner.destroy();
            return false;
        }

        return true;
    }


    public void write(String st) {

        try {
            _owner.textArea.append("Send msg: "+st+"\n");
            outputToServlet.writeObject(st);
            _owner.textArea.append("Sent. \n");
            outputToServlet.flush();
            _owner.textArea.append("Flush. \n");
        } catch (IOException ioe) {
            _owner.textArea.append(ioe.toString()+"\n");
        }
    }


    public String read() {

        try {
            Object inMessage = new Object();
            inMessage = (Object) inputFromServlet.readObject();
            String strMess = inMessage.toString();
            return strMess;
        } catch (Exception ioe) {
            _owner.textArea.append(ioe.toString()+"\n");
            return "MISTAKE";
        }
    }


    public void run() {

        String  inMsg = "";

        establishConnection();

        _owner.textArea.append("output-to-servelt:  "+outputToServlet.toString()+"\n");
        _owner.textArea.append("input-from-servlet: "+inputFromServlet.toString()+"\n");

            write("Hello");
            _owner.textArea.append("sent: Hello\n");
            try {
                Thread.sleep(3000);
            } catch (InterruptedException exc) {
                _owner.textArea.append("Cannot Sleep.\n");
                return;
            }

            inMsg = read();
            _owner.textArea.append("Receive: "+inMsg+"\n");

        _owner.textArea.append("End of run\n");
    }
}
0
Comment
Question by:icefire
  • 4
  • 2
  • 2
  • +1
9 Comments
 
LVL 9

Expert Comment

by:Venci75
Comment Utility
1. NEVER use System.exit(-1); in a servlet! you can just thow an exception
2. Instead of using ObjectInputStream and ObjectOutputStream classes you can use just:
InputStream. To write to the stream use:
3. It is not a good idea to send/receive many messages with one conenction. At least you can't do it with the supported by Java HTTP 1.0. You need HTTP 1.1 support.
       
Applet:
1. You don't need the line
Object inMessage = new Object();
in the read() method. It could be:
return (String)inputFromServlet.readObject();

To solve this problem use separate connections for the "Register" and the "Hello" commands.
0
 

Author Comment

by:icefire
Comment Utility
How to use HTTP 1.1?
0
 

Author Comment

by:icefire
Comment Utility
I changed the doPost function, add a new class ServletThread.

ObjectInputStream  inputFromApplet = new ObjectInputStream(inputStream);

throw exception

 java.io.IOException: Stream closed

Why?

==============================

public void doPost(HttpServletRequest request, HttpServletResponse response)
    throws ServletException, IOException {

        try {

            textArea.append("start of doPost\n");
            ServletThread servletThread = new ServletThread(this, request, response);
            new Thread(servletThread).start();
        } catch (Exception exc) {
            textArea.append("Exception: "+exc.toString()+"\n");
            return;
        } // end of try/catch
} // end of doPost method

    private class ServletThread implements Runnable{

        BLServlet  blServlet;
        HttpServletRequest request;
        HttpServletResponse response;

        public ServletThread(BLServlet bls, HttpServletRequest request1, HttpServletResponse response1){
            blServlet = bls;
            request = request1;
            response = response1;
            textArea.append(blServlet.toString()+"\n");
            textArea.append(request.toString()+"\n");
            textArea.append(response.toString()+"\n");
        }

        public void run(){

        try {

            textArea.append("servlet thread run() start.\n");
            InputStream  inputStream = request.getInputStream();
            textArea.append("get input stream: "+inputStream.toString()+"\n");
            ObjectInputStream  inputFromApplet = new ObjectInputStream(inputStream);
//               ObjectInputStream  inputFromApplet = new ObjectInputStream(request.getInputStream());
               String  inMsg = "";
            int     gotIt = 0;

            textArea.append("read from applet\n");

            while (gotIt <= 0 ) {
                  try {
                       // write info to Applet
                    inMsg = (String) inputFromApplet.readObject();
                    gotIt = 1;
                  } catch (Exception e) {
                       textArea.append("Error reading Information from Applet:\n  "+e+"\n");
                    gotIt--;
                    if (gotIt < -5 ) gotIt = 1;
                     try {
                           Thread.sleep(3000);
                      } catch (InterruptedException exc) {
                          return;
                      }
                }
              } // end of try/catch

            textArea.append("read Msg: "+inMsg+"\n");

               inputFromApplet.close();

               // read the contents of the message
               if (inMsg.equals("Register")) {
                outMsg = "Register Accept";
            }
            else if (inMsg.equals("Hello")) {
                outMsg = "Hello! How are you!";
            }
            else {
                outMsg = "MISTAKE2";
            }

            textArea.append("output message: "+outMsg+"\n");

              ObjectOutputStream  outputToApplet = new ObjectOutputStream(response.getOutputStream());
            textArea.append("object output stream: "+outputToApplet.toString()+"\n");

              try {

                   outputToApplet.writeObject(outMsg);
                   // flush the ObjectOutputStream
                   outputToApplet.flush();
              } catch (IOException ie) {
                   textArea.append("Error sending Information to Applet: "+ie);
              } // end of try/catch

            outputToApplet.close();
            } catch (Exception e) {
                textArea.append("Error in servlet thread run():\n  "+e+"\n");
            }
        }//end of run
    }// end of class ServletThread
0
 
LVL 92

Expert Comment

by:objects
Comment Utility
Adding a thread won't help you. You'll need to send "Register" and "Hello" as seperate http requests.
Once the servlet has recieved register and sent the reply that connection is closed.
You cannot do full duplex communications over http, it is a simple request/response protocol.
0
Highfive Gives IT Their Time Back

Highfive is so simple that setting up every meeting room takes just minutes and every employee will be able to start or join a call from any room with ease. Never be called into a meeting just to get it started again. This is how video conferencing should work!

 
LVL 7

Expert Comment

by:Igor Bazarny
Comment Utility
Hi,

If yo need to keep some state between servlet calls, you can use session for that purpose. Below is form-based servlet sample. For applet you need to simplify request-response content.

Regards,
Igor Bazarny,
Brainbench MVP for Java 1
www.brainbench.com

package ee.servlet;

import java.io.IOException;
import java.io.PrintWriter;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

public final class SessionServlet extends HttpServlet {

    public void doPost(HttpServletRequest request,
                      HttpServletResponse response)
        throws IOException, ServletException
    {
        doGet(request,response);
    }


    /**
     * Respond to a GET request for the content produced by
     * this servlet.
     *
     * @param request The servlet request we are processing
     * @param response The servlet response we are producing
     *
     * @exception IOException if an input/output error occurs
     * @exception ServletException if a servlet error occurs
     */
    public void doGet(HttpServletRequest request,
                      HttpServletResponse response)
      throws IOException, ServletException {

     response.setContentType("text/html");
     PrintWriter writer = response.getWriter();

     writer.println("<html>");
     writer.println("<head>");
     writer.println("<title>Session State Test</title>");
     writer.println("</head>");
     writer.println("<body bgcolor=white>");

     String command = request.getParameter("command").trim();
     Object state = request.getSession().getAttribute("state");
     writer.println("Command: "+command+"<br>");
     writer.println("Input State: "+state+"<br>");
     if( command != null && command.length() > 0){
            if( state == null ){
                if( "Register".equals(command) ){
                    request.getSession().setAttribute("state","registered");
                    writer.println("Register OK<br>");
                }
                else{
                    writer.println("Invalid Command<br>");
                }
            }
            else if( "registered".equals(state) ){
             if( "Hello".equals(command) ){
                   writer.println("Hello! How are you?<br>");
             }
             else if( "Bye".equals(command) ){
                   writer.println("See you later<br>");
                 request.getSession().removeAttribute("state");
             }
                else{
                    writer.println("Invalid Command<br>");
             }
            }
     }
     writer.println("Output State: "+request.getSession().getAttribute("state")+"<br>");

     writer.println("<form action=\"\" method=\"POST\" >"
         +"Command: <input name=\"command\" type=\"text\" ><br>"
         +"<input type=\"submit\" value=\"Send\"></form>" );

     writer.println("</body>");
     writer.println("</html>");

    }
}


0
 

Author Comment

by:icefire
Comment Utility
The target of my program is

1. Use servlet as a server which can be visited by the same applet running on more than one PCs.  

2. The applets can communicate with the servlet not according to request/respons pattern, ie both the servlet and the applets can start the sending of message.

Is there exist a reasonable design?  
0
 
LVL 9

Expert Comment

by:Venci75
Comment Utility
ok - then after the applet calls the servlet they can use plain socket connection. But I don't think that this makes much sense. Why do you need exactly a servlet? You can create your own application that listens for applet conenctions
0
 
LVL 7

Accepted Solution

by:
Igor Bazarny earned 200 total points
Comment Utility
Yes,
Servlet communicates via http protocol, which is request/response based. As far as I know, there is no way to change it's nature.
So, you don't need servlet on server side. Here is what it might look like:

ServerSocket socket = new ServerSocket(PORT_NUMBER);
while(!exitRequested()){
    final Socket wire = socket.accept();
    new Thread(){
        public void run(){
            talkToApplet(wire);
        }
    }.start();
}

In case you want read and write from/to socket independently, you will need 2 threads per connection.

Regards,
Igor Bazarny
0
 

Author Comment

by:icefire
Comment Utility
Thanks a lot.
0

Featured Post

Maximize Your Threat Intelligence Reporting

Reporting is one of the most important and least talked about aspects of a world-class threat intelligence program. Here’s how to do it right.

Join & Write a Comment

For customizing the look of your lightweight component and making it look lucid like it was made of glass. Or: how to make your component more Apple-ish ;) This tip assumes your component to be of rectangular shape and completely opaque. (COD…
For beginner Java programmers or at least those new to the Eclipse IDE, the following tutorial will show some (four) ways in which you can import your Java projects to your Eclipse workbench. Introduction While learning Java can be done with…
Viewers will learn about the regular for loop in Java and how to use it. Definition: Break the for loop down into 3 parts: Syntax when using for loops: Example using a for loop:
This theoretical tutorial explains exceptions, reasons for exceptions, different categories of exception and exception hierarchy.

744 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question

Need Help in Real-Time?

Connect with top rated Experts

17 Experts available now in Live!

Get 1:1 Help Now