Author: ngn
Date: Tue Jun 22 20:29:40 2010
New Revision: 957018

URL: http://svn.apache.org/viewvc?rev=957018&view=rev
Log:
Improved XML parsing, improved session handling (VYSPER-212, by Bogdan Pistol)

Added:
    
mina/vysper/trunk/server/extensions/xep0124-xep0206-bosh/src/main/java/org/apache/vysper/xmpp/extension/xep0124/BoshRequestContext.java
    
mina/vysper/trunk/server/extensions/xep0124-xep0206-bosh/src/main/java/org/apache/vysper/xmpp/extension/xep0124/BoshSaxContentHandler.java
    
mina/vysper/trunk/server/extensions/xep0124-xep0206-bosh/src/main/java/org/apache/vysper/xmpp/extension/xep0124/ContentType.java
Modified:
    
mina/vysper/trunk/server/extensions/xep0124-xep0206-bosh/src/main/java/org/apache/vysper/xmpp/extension/xep0124/BoshBackedSessionContext.java
    
mina/vysper/trunk/server/extensions/xep0124-xep0206-bosh/src/main/java/org/apache/vysper/xmpp/extension/xep0124/BoshDecoder.java
    
mina/vysper/trunk/server/extensions/xep0124-xep0206-bosh/src/main/java/org/apache/vysper/xmpp/extension/xep0124/BoshHandler.java
    
mina/vysper/trunk/server/extensions/xep0124-xep0206-bosh/src/main/java/org/apache/vysper/xmpp/extension/xep0124/BoshServlet.java
    
mina/vysper/trunk/server/extensions/xep0124-xep0206-bosh/src/main/java/org/apache/vysper/xmpp/extension/xep0124/ServerMain.java

Modified: 
mina/vysper/trunk/server/extensions/xep0124-xep0206-bosh/src/main/java/org/apache/vysper/xmpp/extension/xep0124/BoshBackedSessionContext.java
URL: 
http://svn.apache.org/viewvc/mina/vysper/trunk/server/extensions/xep0124-xep0206-bosh/src/main/java/org/apache/vysper/xmpp/extension/xep0124/BoshBackedSessionContext.java?rev=957018&r1=957017&r2=957018&view=diff
==============================================================================
--- 
mina/vysper/trunk/server/extensions/xep0124-xep0206-bosh/src/main/java/org/apache/vysper/xmpp/extension/xep0124/BoshBackedSessionContext.java
 (original)
+++ 
mina/vysper/trunk/server/extensions/xep0124-xep0206-bosh/src/main/java/org/apache/vysper/xmpp/extension/xep0124/BoshBackedSessionContext.java
 Tue Jun 22 20:29:40 2010
@@ -19,9 +19,6 @@
  */
 package org.apache.vysper.xmpp.extension.xep0124;
 
-import javax.servlet.http.HttpServletRequest;
-import javax.servlet.http.HttpServletResponse;
-
 import org.apache.vysper.xmpp.protocol.SessionStateHolder;
 import org.apache.vysper.xmpp.server.AbstractSessionContext;
 import org.apache.vysper.xmpp.server.ServerRuntimeContext;
@@ -39,25 +36,31 @@ import org.slf4j.LoggerFactory;
 public class BoshBackedSessionContext extends AbstractSessionContext implements
         StanzaWriter {
 
-    private final Logger logger = LoggerFactory
+    private final static Logger LOGGER = LoggerFactory
             .getLogger(BoshBackedSessionContext.class);
 
-    private final BoshDecoder boshDecoder;
+    private final int inactivity = 60;
+
+    private final int polling = 15;
+
+    private final int requests = 2;
+
+    private String ver = "1.9";
 
-    private HttpServletRequest httpRequest;
+    private String contentType = ContentType.XML_CONTENT_TYPE;
 
-    private HttpServletResponse httpRespone;
+    private int wait = 60;
+
+    private int hold = 1;
 
     /**
      * Creates a new context for a session
      * @param serverRuntimeContext
      * @param boshHandler
      */
-    public BoshBackedSessionContext(ServerRuntimeContext serverRuntimeContext,
-            BoshHandler boshHandler) {
+    public BoshBackedSessionContext(ServerRuntimeContext serverRuntimeContext) 
{
         super(serverRuntimeContext, new SessionStateHolder());
         sessionStateHolder.setState(SessionState.INITIATED);
-        boshDecoder = new BoshDecoder(boshHandler, this);
     }
 
     public StanzaWriter getResponseWriter() {
@@ -68,11 +71,10 @@ public class BoshBackedSessionContext ex
     }
 
     public void write(Stanza stanza) {
-        //        minaSession.write(new StanzaWriteInfo(stanza, 
!openingStanzaWritten));
     }
 
     public void close() {
-        logger.info("session will be closed now");
+        LOGGER.info("session will be closed now");
     }
 
     public void switchToTLS() {
@@ -80,39 +82,61 @@ public class BoshBackedSessionContext ex
         // SSL can be enabled/disabled in BoshEndpoint#setSSLEnabled()
     }
 
-    /**
-     * Updates the context with the session's {...@link HttpServletRequest} 
and {...@link HttpServletResponse}
-     * <p>
-     * The HTTP context is updated every time a new HTTP request is received.
-     * @param req
-     * @param resp
-     */
-    public void setHttpContext(HttpServletRequest req, HttpServletResponse 
resp) {
-        httpRequest = req;
-        httpRespone = resp;
+    public void setContentType(String contentType) {
+        this.contentType = contentType;
     }
 
-    /**
-     * Getter for the HTTP request
-     * @return
-     */
-    public HttpServletRequest getHttpRequest() {
-        return httpRequest;
+    public String getContentType() {
+        return contentType;
     }
 
-    /**
-     * Getter for the HTTP response
-     * @return
-     */
-    public HttpServletResponse getHttpResponse() {
-        return httpRespone;
+    public void setWait(int wait) {
+        this.wait = Math.min(wait, this.wait);
     }
 
-    /**
-     * Getter for the decoder
-     * @return
-     */
-    public BoshDecoder getDecoder() {
-        return boshDecoder;
+    public int getWait() {
+        return wait;
+    }
+
+    public void setHold(int hold) {
+        this.hold = Math.min(hold, this.hold);
     }
+
+    public int getHold() {
+        return hold;
+    }
+
+    public void setVer(String ver) {
+        String[] serverVer = this.ver.split("\\.");
+        int serverMajor = Integer.parseInt(serverVer[0]);
+        int serverMinor = Integer.parseInt(serverVer[1]);
+        String[] clientVer = ver.split("\\.");
+        
+        if (clientVer.length == 2) {
+            int clientMajor = Integer.parseInt(clientVer[0]);
+            int clientMinor = Integer.parseInt(clientVer[1]);
+
+            if (clientMajor < serverMajor
+                    || (clientMajor == serverMajor && clientMinor < 
serverMinor)) {
+                this.ver = ver;
+            }
+        }
+    }
+
+    public String getVer() {
+        return ver;
+    }
+
+    public int getInactivity() {
+        return inactivity;
+    }
+
+    public int getPolling() {
+        return polling;
+    }
+
+    public int getRequests() {
+        return requests;
+    }
+
 }

Modified: 
mina/vysper/trunk/server/extensions/xep0124-xep0206-bosh/src/main/java/org/apache/vysper/xmpp/extension/xep0124/BoshDecoder.java
URL: 
http://svn.apache.org/viewvc/mina/vysper/trunk/server/extensions/xep0124-xep0206-bosh/src/main/java/org/apache/vysper/xmpp/extension/xep0124/BoshDecoder.java?rev=957018&r1=957017&r2=957018&view=diff
==============================================================================
--- 
mina/vysper/trunk/server/extensions/xep0124-xep0206-bosh/src/main/java/org/apache/vysper/xmpp/extension/xep0124/BoshDecoder.java
 (original)
+++ 
mina/vysper/trunk/server/extensions/xep0124-xep0206-bosh/src/main/java/org/apache/vysper/xmpp/extension/xep0124/BoshDecoder.java
 Tue Jun 22 20:29:40 2010
@@ -26,53 +26,40 @@ import javax.servlet.http.HttpServletReq
 
 import org.apache.mina.core.buffer.IoBuffer;
 import org.apache.vysper.charset.CharsetUtil;
-import org.apache.vysper.mina.codec.StanzaBuilderFactory;
-import org.apache.vysper.xml.decoder.XMPPContentHandler;
-import org.apache.vysper.xml.decoder.XMPPContentHandler.StanzaListener;
-import org.apache.vysper.xml.fragment.XMLElement;
 import org.apache.vysper.xml.sax.NonBlockingXMLReader;
 import org.apache.vysper.xml.sax.impl.DefaultNonBlockingXMLReader;
-import org.apache.vysper.xmpp.server.SessionContext;
-import org.apache.vysper.xmpp.stanza.Stanza;
+import org.xml.sax.ContentHandler;
 import org.xml.sax.SAXException;
 
 /**
  * Decodes bytes into BOSH stanzas
  * <p>
  * Uses nbxml for XML processing.
- * Every HTTP session has its own instance of BoshDecoder
- * (because decoding state is associated with the decoder, and to ensure that
- * the decoding errors of a session do not affect another session).
+ * For every HTTP request there is a BoshDecoder instance
+ * to ensure that parsing errors (e.g. malformed XML) do not affect other 
requests.
  * 
  * @author The Apache MINA Project ([email protected])
  */
-public class BoshDecoder implements StanzaListener {
-
-    private final BoshHandler boshHandler;
+public class BoshDecoder {
 
     private final NonBlockingXMLReader reader;
-
-    private final BoshBackedSessionContext sessionContext;
+    
+    private final BoshRequestContext boshRequestContext;
 
     /**
-     * Creates a new decoder associated with a {...@link SessionContext}
+     * Creates a new decoder associated with a {...@link BoshRequestContext}
      * @param boshHandler
-     * @param sessionContext
      */
-    public BoshDecoder(BoshHandler boshHandler,
-            BoshBackedSessionContext sessionContext) {
-        this.boshHandler = boshHandler;
-        this.sessionContext = sessionContext;
+    public BoshDecoder(BoshHandler boshHandler, BoshRequestContext 
boshRequestContext) {
+        this.boshRequestContext = boshRequestContext;
         reader = new DefaultNonBlockingXMLReader();
-        XMPPContentHandler contentHandler = new XMPPContentHandler(
-                new StanzaBuilderFactory());
-        contentHandler.setListener(this);
+        ContentHandler contentHandler = new BoshSaxContentHandler(boshHandler, 
boshRequestContext);
         reader.setContentHandler(contentHandler);
     }
 
     /**
      * Decodes the bytes from the {...@link InputStream} provided by the 
current {...@link HttpServletRequest} of
-     * the session context into BOSH stanzas.
+     * the request context into a BOSH stanza.
      * @throws IOException
      * @throws SAXException
      */
@@ -80,7 +67,7 @@ public class BoshDecoder implements Stan
         IoBuffer ioBuf = IoBuffer.allocate(1024);
         ioBuf.setAutoExpand(true);
         byte[] buf = new byte[1024];
-        InputStream in = sessionContext.getHttpRequest().getInputStream();
+        InputStream in = boshRequestContext.getRequest().getInputStream();
 
         for (;;) {
             int i = in.read(buf);
@@ -93,8 +80,4 @@ public class BoshDecoder implements Stan
         reader.parse(ioBuf, CharsetUtil.UTF8_DECODER);
     }
 
-    public void stanza(XMLElement element) {
-        boshHandler.processStanza(sessionContext, (Stanza) element);
-    }
-
 }
\ No newline at end of file

Modified: 
mina/vysper/trunk/server/extensions/xep0124-xep0206-bosh/src/main/java/org/apache/vysper/xmpp/extension/xep0124/BoshHandler.java
URL: 
http://svn.apache.org/viewvc/mina/vysper/trunk/server/extensions/xep0124-xep0206-bosh/src/main/java/org/apache/vysper/xmpp/extension/xep0124/BoshHandler.java?rev=957018&r1=957017&r2=957018&view=diff
==============================================================================
--- 
mina/vysper/trunk/server/extensions/xep0124-xep0206-bosh/src/main/java/org/apache/vysper/xmpp/extension/xep0124/BoshHandler.java
 (original)
+++ 
mina/vysper/trunk/server/extensions/xep0124-xep0206-bosh/src/main/java/org/apache/vysper/xmpp/extension/xep0124/BoshHandler.java
 Tue Jun 22 20:29:40 2010
@@ -20,40 +20,118 @@
 package org.apache.vysper.xmpp.extension.xep0124;
 
 import java.io.IOException;
-import java.util.Random;
+import java.util.Map;
+import java.util.concurrent.ConcurrentHashMap;
 
 import javax.servlet.http.HttpServletResponse;
 
+import org.apache.vysper.xml.fragment.Renderer;
+import org.apache.vysper.xmpp.server.ServerRuntimeContext;
 import org.apache.vysper.xmpp.stanza.Stanza;
+import org.apache.vysper.xmpp.stanza.StanzaBuilder;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
 
 /**
- * Processes the BOSH requests from the clients and then responds back
+ * Processes the BOSH requests from the clients
+ * <p>
+ * This class is thread safe.
+ * Concurrent BOSH clients can be handled simultaneously by this class safely. 
  * 
  * @author The Apache MINA Project ([email protected])
  */
 public class BoshHandler {
+    
+    private static final Logger LOGGER = 
LoggerFactory.getLogger(BoshHandler.class);
+    
+    private static final String BOSH_NS = 
"http://jabber.org/protocol/httpbind";;
+    
+    private ServerRuntimeContext serverRuntimeContext;
+    
+    private Map<String, BoshBackedSessionContext> sessions;
+    
+    public BoshHandler() {
+        sessions = new ConcurrentHashMap<String, BoshBackedSessionContext>();
+    }
+
+    public void setServerRuntimeContext(
+            ServerRuntimeContext serverRuntimeContext) {
+        this.serverRuntimeContext = serverRuntimeContext;
+    }
 
     /**
-     * Handles the BOSH stanzas received from the decoder
-     * @param sessionContext
+     * Processes BOSH stanzas concurrently
+     * @param boshRequestContext
      * @param stanza
      */
-    public void processStanza(BoshBackedSessionContext sessionContext,
-            Stanza stanza) {
+    public void process(BoshRequestContext boshRequestContext, Stanza stanza) {
+        if (!stanza.getNamespaceURI().equalsIgnoreCase(BOSH_NS)) {
+            LOGGER.error("Invalid namespace for body wrapper '{}', should be 
'{}'!", stanza.getNamespaceURI(), BOSH_NS);
+            return;
+        }
+        if (!stanza.getName().equalsIgnoreCase("body")) {
+            LOGGER.error("Invalid body wrapper '{}'!", stanza.getName());
+            return;
+        }
+        if (stanza.getAttribute("rid") == null) {
+            LOGGER.error("Invalid request that does not have a request 
identifier (rid) attribute!");
+            return;
+        }
         
-        // TODO
-        HttpServletResponse resp = sessionContext.getHttpResponse();
-        String sid = Long.toString(new Random().nextLong(), 16);
-        resp.setContentType("text/xml; charset=UTF-8");
-        try {
-            resp.getWriter().print("<body 
xmlns='http://jabber.org/protocol/httpbind' wait='60' inactivity='60' 
polling='5' requests='2' hold='1' maxpause='120' sid='");
-        resp.getWriter().print(sid);
-        resp.getWriter().print("' ver='1.6' from='vysper.org'/>");
-        resp.flushBuffer();
-        } catch (IOException e) {
-            // TODO Auto-generated catch block
-            e.printStackTrace();
+        if (stanza.getAttribute("sid") == null) {
+            // the session creation request (first request) does not have a 
"sid" attribute
+            try {
+                createSession(boshRequestContext, stanza);
+            } catch (IOException e) {
+                LOGGER.error("Exception thrown while processing the session 
creation request", e);
+                return;
+            }
+        } else {
+//            handleSession(boshRequestContext, stanza);
         }
     }
 
+    private void createSession(BoshRequestContext boshRequestContext,
+            Stanza stanza) throws IOException {
+        BoshBackedSessionContext session = new 
BoshBackedSessionContext(serverRuntimeContext);
+        if (stanza.getAttribute("content") != null) {
+            session.setContentType(stanza.getAttributeValue("content"));
+        }
+        if (stanza.getAttribute("wait") != null) {
+            int wait = Integer.parseInt(stanza.getAttributeValue("wait"));
+            session.setWait(wait);
+        }
+        if (stanza.getAttribute("hold") != null) {
+            int hold = Integer.parseInt(stanza.getAttributeValue("hold"));
+            session.setHold(hold);
+        }
+        if (stanza.getAttribute("ver") != null) {
+            String ver = stanza.getAttributeValue("ver");
+            session.setVer(ver);
+        }
+        sessions.put(session.getSessionId(), session);
+        HttpServletResponse resp = boshRequestContext.getResponse();
+        resp.setContentType(session.getContentType());
+        String msg = new 
Renderer(getSessionCreationResponse(session)).getComplete();
+        resp.setContentLength(msg.length());
+        resp.addDateHeader("Date", System.currentTimeMillis());
+        resp.addHeader("Access-control-allow-origin", "*");
+        resp.addHeader("Access-control-allow-headers", "Content-Type");
+        resp.getWriter().print(msg);
+        resp.flushBuffer();
+    }
+    
+    public Stanza getSessionCreationResponse(BoshBackedSessionContext session) 
{
+        StanzaBuilder stanzaBuilder = new StanzaBuilder("body", BOSH_NS);
+        stanzaBuilder.addAttribute("wait", 
Integer.toString(session.getWait()));
+        stanzaBuilder.addAttribute("inactivity", 
Integer.toString(session.getInactivity()));
+        stanzaBuilder.addAttribute("polling", 
Integer.toString(session.getPolling()));
+        stanzaBuilder.addAttribute("requests", 
Integer.toString(session.getRequests()));
+        stanzaBuilder.addAttribute("hold", 
Integer.toString(session.getHold()));
+        stanzaBuilder.addAttribute("sid", session.getSessionId());
+        stanzaBuilder.addAttribute("ver", session.getVer());
+        stanzaBuilder.addAttribute("from", 
session.getServerJID().getFullQualifiedName());
+        return stanzaBuilder.build();
+    }
+
 }

Added: 
mina/vysper/trunk/server/extensions/xep0124-xep0206-bosh/src/main/java/org/apache/vysper/xmpp/extension/xep0124/BoshRequestContext.java
URL: 
http://svn.apache.org/viewvc/mina/vysper/trunk/server/extensions/xep0124-xep0206-bosh/src/main/java/org/apache/vysper/xmpp/extension/xep0124/BoshRequestContext.java?rev=957018&view=auto
==============================================================================
--- 
mina/vysper/trunk/server/extensions/xep0124-xep0206-bosh/src/main/java/org/apache/vysper/xmpp/extension/xep0124/BoshRequestContext.java
 (added)
+++ 
mina/vysper/trunk/server/extensions/xep0124-xep0206-bosh/src/main/java/org/apache/vysper/xmpp/extension/xep0124/BoshRequestContext.java
 Tue Jun 22 20:29:40 2010
@@ -0,0 +1,50 @@
+/*
+ *  Licensed to the Apache Software Foundation (ASF) under one
+ *  or more contributor license agreements.  See the NOTICE file
+ *  distributed with this work for additional information
+ *  regarding copyright ownership.  The ASF licenses this file
+ *  to you under the Apache License, Version 2.0 (the
+ *  "License"); you may not use this file except in compliance
+ *  with the License.  You may obtain a copy of the License at
+ *
+ *    http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing,
+ *  software distributed under the License is distributed on an
+ *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ *  KIND, either express or implied.  See the License for the
+ *  specific language governing permissions and limitations
+ *  under the License.
+ *
+ */
+package org.apache.vysper.xmpp.extension.xep0124;
+
+import javax.servlet.http.HttpServletRequest;
+import javax.servlet.http.HttpServletResponse;
+
+/**
+ * Encapsulates a {...@link HttpServletRequest} and it's corresponding 
{...@link HttpServletResponse}
+ * 
+ * @author The Apache MINA Project ([email protected])
+ */
+public class BoshRequestContext {
+
+    private final HttpServletRequest request;
+
+    private final HttpServletResponse response;
+
+    public BoshRequestContext(HttpServletRequest request,
+            HttpServletResponse response) {
+        this.request = request;
+        this.response = response;
+    }
+
+    public HttpServletRequest getRequest() {
+        return request;
+    }
+
+    public HttpServletResponse getResponse() {
+        return response;
+    }
+
+}

Added: 
mina/vysper/trunk/server/extensions/xep0124-xep0206-bosh/src/main/java/org/apache/vysper/xmpp/extension/xep0124/BoshSaxContentHandler.java
URL: 
http://svn.apache.org/viewvc/mina/vysper/trunk/server/extensions/xep0124-xep0206-bosh/src/main/java/org/apache/vysper/xmpp/extension/xep0124/BoshSaxContentHandler.java?rev=957018&view=auto
==============================================================================
--- 
mina/vysper/trunk/server/extensions/xep0124-xep0206-bosh/src/main/java/org/apache/vysper/xmpp/extension/xep0124/BoshSaxContentHandler.java
 (added)
+++ 
mina/vysper/trunk/server/extensions/xep0124-xep0206-bosh/src/main/java/org/apache/vysper/xmpp/extension/xep0124/BoshSaxContentHandler.java
 Tue Jun 22 20:29:40 2010
@@ -0,0 +1,158 @@
+/*
+ *  Licensed to the Apache Software Foundation (ASF) under one
+ *  or more contributor license agreements.  See the NOTICE file
+ *  distributed with this work for additional information
+ *  regarding copyright ownership.  The ASF licenses this file
+ *  to you under the Apache License, Version 2.0 (the
+ *  "License"); you may not use this file except in compliance
+ *  with the License.  You may obtain a copy of the License at
+ *
+ *    http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing,
+ *  software distributed under the License is distributed on an
+ *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ *  KIND, either express or implied.  See the License for the
+ *  specific language governing permissions and limitations
+ *  under the License.
+ *
+ */
+package org.apache.vysper.xmpp.extension.xep0124;
+
+import org.apache.vysper.mina.codec.StanzaBuilderFactory;
+import org.apache.vysper.xml.decoder.XMLElementBuilderFactory;
+import org.apache.vysper.xml.decoder.XMPPContentHandler;
+import org.apache.vysper.xml.fragment.AbstractXMLElementBuilder;
+import org.apache.vysper.xml.fragment.Renderer;
+import org.apache.vysper.xml.fragment.XMLElement;
+import org.apache.vysper.xmpp.stanza.Stanza;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+import org.xml.sax.Attributes;
+import org.xml.sax.ContentHandler;
+import org.xml.sax.Locator;
+import org.xml.sax.SAXException;
+
+/**
+ * SAX handler that constructs stanzas by parsing XML from BOSH clients.
+ * <p>
+ * This class is similar to {...@link XMPPContentHandler}
+ *
+ * @author The Apache MINA Project ([email protected])
+ */
+public class BoshSaxContentHandler implements ContentHandler {
+
+    private static final Logger LOGGER = LoggerFactory
+            .getLogger(BoshSaxContentHandler.class);
+
+    private final BoshHandler boshHandler;
+
+    private final BoshRequestContext boshRequestContext;
+
+    private final XMLElementBuilderFactory builderFactory;
+
+    @SuppressWarnings("rawtypes")
+    private AbstractXMLElementBuilder builder;
+
+    private int depth = 0;
+    
+    private boolean isBodyPayloadDecoded = false;
+
+    public BoshSaxContentHandler(BoshHandler boshHandler,
+            BoshRequestContext boshRequestContext) {
+        this.boshHandler = boshHandler;
+        this.boshRequestContext = boshRequestContext;
+        builderFactory = new StanzaBuilderFactory();
+    }
+
+    public void characters(char[] ch, int start, int length)
+            throws SAXException {
+        // TODO handle start and length
+        if (builder != null) {
+            builder.addText(new String(ch));
+        }
+    }
+
+    public void endElement(String uri, String localName, String qName)
+            throws SAXException {
+        depth--;
+        if (depth == 0 && !isBodyPayloadDecoded) {
+            // complete body, emit
+            emitStanza();
+        } else {
+            builder.endInnerElement();
+        }
+    }
+
+    private void emitStanza() {
+        isBodyPayloadDecoded = true;
+        XMLElement element = builder.build();
+        if (LOGGER.isDebugEnabled()) {
+            LOGGER.debug("BOSH decoding stanza: {}",
+                    new Renderer(element).getComplete());
+        }
+        boshHandler.process(boshRequestContext, (Stanza) element);
+        builder = null;
+    }
+
+    public void startElement(String uri, String localName, String qName,
+            Attributes atts) throws SAXException {
+        depth++;
+        if (builder == null) {
+            builder = builderFactory.createBuilder(localName, uri,
+                    extractPrefix(qName), null, null);
+        } else {
+            builder.startInnerElement(localName, uri);
+        }
+
+        for (int i = 0; i < atts.getLength(); i++) {
+            builder.addAttribute(atts.getURI(i), atts.getLocalName(i),
+                    atts.getValue(i));
+        }
+    }
+
+    private String extractPrefix(String qname) {
+        int index = qname.indexOf(':');
+        if (index > -1) {
+            return qname.substring(0, index);
+        } else {
+            return "";
+        }
+    }
+
+    public void setDocumentLocator(Locator locator) {
+        // ignore
+    }
+
+    public void startDocument() throws SAXException {
+        // ignore
+    }
+
+    public void endDocument() throws SAXException {
+        // ignore
+    }
+
+    public void startPrefixMapping(String prefix, String uri)
+            throws SAXException {
+        // ignore
+    }
+
+    public void endPrefixMapping(String prefix) throws SAXException {
+        // ignore
+    }
+
+    public void ignorableWhitespace(char[] ch, int start, int length)
+            throws SAXException {
+        // ignore
+    }
+
+    public void processingInstruction(String target, String data)
+            throws SAXException {
+        // ignore
+    }
+
+    public void skippedEntity(String name) throws SAXException {
+        // ignore
+    }
+
+}

Modified: 
mina/vysper/trunk/server/extensions/xep0124-xep0206-bosh/src/main/java/org/apache/vysper/xmpp/extension/xep0124/BoshServlet.java
URL: 
http://svn.apache.org/viewvc/mina/vysper/trunk/server/extensions/xep0124-xep0206-bosh/src/main/java/org/apache/vysper/xmpp/extension/xep0124/BoshServlet.java?rev=957018&r1=957017&r2=957018&view=diff
==============================================================================
--- 
mina/vysper/trunk/server/extensions/xep0124-xep0206-bosh/src/main/java/org/apache/vysper/xmpp/extension/xep0124/BoshServlet.java
 (original)
+++ 
mina/vysper/trunk/server/extensions/xep0124-xep0206-bosh/src/main/java/org/apache/vysper/xmpp/extension/xep0124/BoshServlet.java
 Tue Jun 22 20:29:40 2010
@@ -28,7 +28,6 @@ import javax.servlet.ServletException;
 import javax.servlet.http.HttpServlet;
 import javax.servlet.http.HttpServletRequest;
 import javax.servlet.http.HttpServletResponse;
-import javax.servlet.http.HttpSession;
 
 import org.apache.vysper.xmpp.server.ServerRuntimeContext;
 import org.slf4j.Logger;
@@ -36,7 +35,7 @@ import org.slf4j.LoggerFactory;
 import org.xml.sax.SAXException;
 
 /**
- * Handles BOSH requests from HTTP clients.
+ * Receives BOSH requests from HTTP clients.
  *
  * @author The Apache MINA Project ([email protected])
  */
@@ -46,20 +45,12 @@ public class BoshServlet extends HttpSer
 
     private static final String FLASH_CROSS_DOMAIN_POLICY_URI = 
"/crossdomain.xml";
 
-    private static final String HTML_CONTENT_TYPE = "text/html; charset=UTF-8";
-
-    private static final String XML_CONTENT_TYPE = "text/xml; charset=UTF-8";
-
     private static final String INFO_GET = "This is an XMPP BOSH connection 
manager, you need to use a compatible BOSH client to use its services!";
     
-    private static final String SESSION_CONTEXT_ATTRIBUTE = 
"SESSION_CONTEXT_ATTRIBUTE";
-
     private final Logger logger = LoggerFactory.getLogger(BoshServlet.class);
     
     private final BoshHandler boshHandler = new BoshHandler();
 
-    private ServerRuntimeContext serverRuntimeContext;
-
     private ByteArrayOutputStream flashCrossDomainPolicy;
 
     /**
@@ -68,7 +59,7 @@ public class BoshServlet extends HttpSer
      */
     public void setServerRuntimeContext(
             ServerRuntimeContext serverRuntimeContext) {
-        this.serverRuntimeContext = serverRuntimeContext;
+        boshHandler.setServerRuntimeContext(serverRuntimeContext);
     }
 
     /**
@@ -95,10 +86,10 @@ public class BoshServlet extends HttpSer
     protected void doGet(HttpServletRequest req, HttpServletResponse resp)
             throws ServletException, IOException {
         if (FLASH_CROSS_DOMAIN_POLICY_URI.equals(req.getRequestURI())) {
-            resp.setContentType(XML_CONTENT_TYPE);
+            resp.setContentType(ContentType.XML_CONTENT_TYPE);
             flashCrossDomainPolicy.writeTo(resp.getOutputStream());
         } else {
-            resp.setContentType(HTML_CONTENT_TYPE);
+            resp.setContentType(ContentType.HTML_CONTENT_TYPE);
             resp.getWriter().println(INFO_GET);
         }
         resp.flushBuffer();
@@ -107,25 +98,12 @@ public class BoshServlet extends HttpSer
     @Override
     protected void doPost(HttpServletRequest req, HttpServletResponse resp)
             throws ServletException, IOException {
-        HttpSession httpSession = req.getSession(true);
-        BoshBackedSessionContext sessionContext = (BoshBackedSessionContext) 
httpSession.getAttribute(SESSION_CONTEXT_ATTRIBUTE);
-        if (sessionContext == null) {
-            sessionContext = new 
BoshBackedSessionContext(serverRuntimeContext, boshHandler);
-            httpSession.setAttribute(SESSION_CONTEXT_ATTRIBUTE, 
sessionContext);
-        }
-        
-        /*
-         * The following block is synchronized on the session context to 
prevent simultaneous
-         * access from a session (simultaneous access is possible in certain 
cases because of the 
-         * nature of HTTP sessions tracking mechanism - cookies, URL rewrites, 
etc).
-         */
-        synchronized (sessionContext) {
-            sessionContext.setHttpContext(req, resp);
-            try {
-                sessionContext.getDecoder().decode();
-            } catch (SAXException e) {
-                logger.error("Exception thrown while decoding XML", e);
-            }            
+        BoshRequestContext boshRequestContext = new BoshRequestContext(req, 
resp);
+        BoshDecoder boshDecoder = new BoshDecoder(boshHandler, 
boshRequestContext);
+        try {
+            boshDecoder.decode();
+        } catch (SAXException e) {
+            logger.error("Exception thrown while decoding XML", e);
         }
     }
 

Added: 
mina/vysper/trunk/server/extensions/xep0124-xep0206-bosh/src/main/java/org/apache/vysper/xmpp/extension/xep0124/ContentType.java
URL: 
http://svn.apache.org/viewvc/mina/vysper/trunk/server/extensions/xep0124-xep0206-bosh/src/main/java/org/apache/vysper/xmpp/extension/xep0124/ContentType.java?rev=957018&view=auto
==============================================================================
--- 
mina/vysper/trunk/server/extensions/xep0124-xep0206-bosh/src/main/java/org/apache/vysper/xmpp/extension/xep0124/ContentType.java
 (added)
+++ 
mina/vysper/trunk/server/extensions/xep0124-xep0206-bosh/src/main/java/org/apache/vysper/xmpp/extension/xep0124/ContentType.java
 Tue Jun 22 20:29:40 2010
@@ -0,0 +1,33 @@
+/*
+ *  Licensed to the Apache Software Foundation (ASF) under one
+ *  or more contributor license agreements.  See the NOTICE file
+ *  distributed with this work for additional information
+ *  regarding copyright ownership.  The ASF licenses this file
+ *  to you under the Apache License, Version 2.0 (the
+ *  "License"); you may not use this file except in compliance
+ *  with the License.  You may obtain a copy of the License at
+ *
+ *    http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing,
+ *  software distributed under the License is distributed on an
+ *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ *  KIND, either express or implied.  See the License for the
+ *  specific language governing permissions and limitations
+ *  under the License.
+ *
+ */
+package org.apache.vysper.xmpp.extension.xep0124;
+
+/**
+ * Typical HTTP content-types
+ *
+ * @author The Apache MINA Project ([email protected])
+ */
+public class ContentType {
+    
+    public static final String HTML_CONTENT_TYPE = "text/html; charset=UTF-8";
+
+    public static final String XML_CONTENT_TYPE = "text/xml; charset=UTF-8";
+
+}

Modified: 
mina/vysper/trunk/server/extensions/xep0124-xep0206-bosh/src/main/java/org/apache/vysper/xmpp/extension/xep0124/ServerMain.java
URL: 
http://svn.apache.org/viewvc/mina/vysper/trunk/server/extensions/xep0124-xep0206-bosh/src/main/java/org/apache/vysper/xmpp/extension/xep0124/ServerMain.java?rev=957018&r1=957017&r2=957018&view=diff
==============================================================================
--- 
mina/vysper/trunk/server/extensions/xep0124-xep0206-bosh/src/main/java/org/apache/vysper/xmpp/extension/xep0124/ServerMain.java
 (original)
+++ 
mina/vysper/trunk/server/extensions/xep0124-xep0206-bosh/src/main/java/org/apache/vysper/xmpp/extension/xep0124/ServerMain.java
 Tue Jun 22 20:29:40 2010
@@ -123,6 +123,7 @@ public class ServerMain {
         }
     }
 
+    @SuppressWarnings("unchecked")
     private static List<Module> createModuleInstances(String[] 
moduleClassNames) {
         List<Module> modules = new ArrayList<Module>();
 


Reply via email to