0 Replies Latest reply on Jul 18, 2012 10:03 AM by Joshua Junqueira

    Setting up reverse ajax(using jquery socket)/comet/Asynchronous servlet in Jboss AS 7.1.1

    Joshua Junqueira Newbie

      I am new to developing Java Servlets and Java EE in general, I am attempting to get the example from jquery socket working here : https://github.com/flowersinthesand/jquery-socket The problem is that when I deploy it to the server I keep getting this warning and my servlet is not getting deployed :

       

      09:57:16,560 WARN  [org.jboss.as.ee] (MSC service thread 1-2) JBAS011006: Not installing optional component com.saviops.rst.service.ChatServlet$2 due to exception: org.jboss.as.server.deployment.DeploymentUnitProcessingException: JBAS011054: Could not find default constructor for class com.saviops.rst.service.ChatServlet$2

                at org.jboss.as.ee.component.ComponentDescription$DefaultComponentConfigurator.configure(ComponentDescription.java:606)

                at org.jboss.as.ee.component.deployers.EEModuleConfigurationProcessor.deploy(EEModuleConfigurationProcessor.java:81)

                at org.jboss.as.server.deployment.DeploymentUnitPhaseService.start(DeploymentUnitPhaseService.java:113) [jboss-as-server-7.1.1.Final.jar:7.1.1.Final]

                at org.jboss.msc.service.ServiceControllerImpl$StartTask.startService(ServiceControllerImpl.java:1811) [jboss-msc-1.0.2.GA.jar:1.0.2.GA]

                at org.jboss.msc.service.ServiceControllerImpl$StartTask.run(ServiceControllerImpl.java:1746) [jboss-msc-1.0.2.GA.jar:1.0.2.GA]

                at java.util.concurrent.ThreadPoolExecutor$Worker.runTask(ThreadPoolExecutor.java:886) [classes.jar:1.6.0_33]

                at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:908) [classes.jar:1.6.0_33]

                at java.lang.Thread.run(Thread.java:680) [classes.jar:1.6.0_33]

       

       

      I am using Jboss AS 7.1.1 and using Jboss Developer Studio to do the development. Everything is running using the default configuration, so it is possible I do not have something setup correctly. Here is the code example I am trying to get working.

       

       

      package com.saviops.rst.service;
      
      import java.io.IOException;
      import java.io.PrintWriter;
      import java.util.Map;
      import java.util.Map.Entry;
      import java.util.concurrent.BlockingQueue;
      import java.util.concurrent.ConcurrentHashMap;
      import java.util.concurrent.LinkedBlockingQueue;
      
      import javax.servlet.AsyncContext;
      import javax.servlet.AsyncEvent;
      import javax.servlet.AsyncListener;
      import javax.servlet.ServletException;
      import javax.servlet.annotation.WebServlet;
      import javax.servlet.http.HttpServlet;
      import javax.servlet.http.HttpServletRequest;
      import javax.servlet.http.HttpServletResponse;
      
      import com.google.gson.Gson;
      
      @WebServlet(urlPatterns = "/chat", asyncSupported = true)
      public class ChatServlet extends HttpServlet {
      
           private static final long serialVersionUID = -6741151503530066933L;
      
           private Map connections = new ConcurrentHashMap();
           private BlockingQueue queue = new LinkedBlockingQueue();
           private Thread broadcaster = new Thread(new Runnable() {
                @Override
                public void run() {
                     while (true) {
                          try {
                               Event event = queue.take();
                               for (Entry entry : connections.entrySet()) {
                                    try {
                                         send(entry.getValue(), event);
                                    } catch (IOException ex) {
                                         fire(new Event("close").socket(entry.getKey()));
                                    }
                               }
                          } catch (InterruptedException e) {
                               break;
                          }
                     }
                }
           });
      
           @Override
           public void init() throws ServletException {
                broadcaster.setDaemon(true);
                broadcaster.start();
           }
      
           @Override
           protected void doGet(HttpServletRequest request, HttpServletResponse response)
                     throws ServletException, IOException {
                final String id = request.getParameter("id");
                String transport = request.getParameter("transport");
                AsyncContext asyncContext = request.startAsync();
      
                response.setCharacterEncoding("utf-8");
                response.setHeader("Access-Control-Allow-Origin", "*");
                response.setContentType("text/" + ("sse".equals(transport) ? "event-stream" : "plain"));
                asyncContext.addListener(new AsyncListener() {
                     public void onStartAsync(AsyncEvent event) throws IOException {
      
                     }
      
                     public void onComplete(AsyncEvent event) throws IOException {
                          cleanup(event);
                     }
      
                     public void onTimeout(AsyncEvent event) throws IOException {
                          cleanup(event);
                     }
      
                     public void onError(AsyncEvent event) throws IOException {
                          cleanup(event);
                     }
      
                     private void cleanup(AsyncEvent event) {
                          fire(new Event("close").socket(id));
                     }
                });
      
                PrintWriter writer = response.getWriter();
                for (int i = 0; i < 2000; i++) {
                     writer.print(' ');
                }
                writer.print("\n");
                writer.flush();
      
                connections.put(id, asyncContext);
                fire(new Event("open").socket(id));
           }
      
           private void send(AsyncContext asyncContext, Event event) throws IOException {
                String data = new Gson().toJson(event);
                PrintWriter writer = asyncContext.getResponse().getWriter();
      
                for (String datum : data.split("\r\n|\r|\n")) {
                     writer.print("data: ");
                     writer.print(datum);
                     writer.print("\n");
                }
      
                writer.print("\n");
                writer.flush();
           }
      
           @Override
           protected void doPost(HttpServletRequest request, HttpServletResponse response)
                     throws ServletException, IOException {
                request.setCharacterEncoding("utf-8");
                response.setHeader("Access-Control-Allow-Origin", "*");
      
                String data = request.getReader().readLine();
                if (data != null) {
                     data = data.substring("data=".length());
                     fire(new Gson().fromJson(data, Event.class));
                }
           }
      
           private void fire(Event event) {
                if (event.type.equals("close")) {
                     connections.remove(event.socket);
                }
      
                handle(event);
           }
      
           private void handle(Event event) {
                if (event.type.equals("message")) {
                     queue.offer(new Event("message").data(event.data));
                }
           }
      
           private static class Event {
                private String socket;
                private String type;
                private Object data;
      
                @SuppressWarnings("unused")
                public Event() {
      
                }
      
                public Event(String type) {
                     this.type = type;
                }
      
                public Event data(Object data) {
                     this.data = data;
                     return this;
                }
      
                public Event socket(String socket) {
                     this.socket = socket;
                     return this;
                }
           }
      
      }
      

       

      Just for reference I want to be able to have a constant connection from the client to the server so that the server can push status updates. I don't necessarily need this chat program working, I just wanted to get a working example of doing the server push. Also if there are any better ways to do this I am open to implementing this in a different manner.

       

      Thanks for the help!