11 Replies Latest reply: Apr 6, 2010 6:48 AM by Kobi Ianko RSS

JMS over HTTP problem

Marcelo Klein Newbie

Hi, I'm currently using JBoss 3.2.2, and connecting with JMS using the HTTPConnectionFactory over HTTPS.

In my server app, I send a JMS Message (a ping) to the client every 10 seconds to know if it's alive. When using UIL2ConnectionFactory, the client disconnection is detected in the server.
However, when I use the HTTPConnectionFactory, I explicitly kill the client, but the server keeps pinging as if it were alive.
How can I change this? I tried altering the timeouts in the sar of the httpilservlet, but nothing happened.
Any clues?
Thanks a lot,
Marcelo

  • 1. Re: JMS over HTTP problem
    Adrian Brock Master

    Have you configured a ping period?

    Regards,
    Adrian

  • 2. Re: JMS over HTTP problem
    Marcelo Klein Newbie

    Below is my jms configuration for both UIL and HTTPIL

    uil2-service.xml:


    <mbean code="org.jboss.mq.il.uil2.UILServerILService"
    name="jboss.mq:service=InvocationLayer,type=UIL2">
    <depends optional-attribute-name="Invoker">jboss.mq:service=Invoker</depends>
    <attribute name="ConnectionFactoryJNDIRef">UIL2ConnectionFactory</attribute>
    <attribute name="XAConnectionFactoryJNDIRef">UIL2XAConnectionFactory</attribute>
    <attribute name="BindAddress"></attribute>
    <attribute name="ServerBindPort">8093</attribute>
    <attribute name="PingPeriod">3000</attribute>
    <attribute name="EnableTcpNoDelay">true</attribute>
    <!-- Used to disconnect the client if there is no activity -->
    <!-- Ensure this is greater than the ping period -->
    <attribute name="ReadTimeout">4000</attribute>
    <!-- The size of the buffer (in bytes) wrapping the socket -->
    <!-- The buffer is flushed after each request -->
    <attribute name="BufferSize">2048</attribute>
    <!-- Large messages may block the ping/pong -->
    <!-- A pong is simulated after each chunk (in bytes) for both reading and writing -->
    <!-- It must be larger than the buffer size -->
    <attribute name="ChunkSize">1000000</attribute>
    </mbean>

    <!-- Aliases UIL -> UIL2 for backwards compatibility
    the deprecated UIL deployment can be found in docs/examples/jca -->
    <mbean code="org.jboss.naming.NamingAlias" name="jboss.mq:service=InvocationLayer,type=UIL">
    <attribute name="FromName">UILConnectionFactory</attribute>
    <attribute name="ToName">UIL2ConnectionFactory</attribute>
    </mbean>
    <mbean code="org.jboss.naming.NamingAlias" name="jboss.mq:service=InvocationLayer,type=UILXA">
    <attribute name="FromName">UILXAConnectionFactory</attribute>
    <attribute name="ToName">UIL2XAConnectionFactory</attribute>
    </mbean>


    Here's the jboss-service in the META-INF in the HTTPIL SAR:

    <mbean code="org.jboss.mq.il.http.HTTPServerILService"
    name="jboss.mq:service=InvocationLayer,type=HTTP">
    <depends optional-attribute-name="Invoker">jboss.mq:service=Invoker</depends>
    <depends>jboss.web:service=WebServer</depends>
    <attribute name="ConnectionFactoryJNDIRef">HTTPConnectionFactory</attribute>
    <attribute name="XAConnectionFactoryJNDIRef">HTTPXAConnectionFactory</attribute>
    <attribute name="PingPeriod">0</attribute>
    <attribute name="TimeOut">60</attribute>
    <attribute name="RestInterval">0</attribute>
    <!--attribute name="UseHostName">false</attribute-->
    <attribute name="URL">https://marcelo.MERCADOS/jbossmq-httpil/HTTPServerILServlet</attribute>
    <!--attribute name="URLPrefix">https://</attribute-->
    <!--attribute name="URLSuffix">jbossmq-httpil/HTTPServerILServlet</attribute>
    <attribute name="URLPort">443</attribute>
    <attribute name="URLHostName">localhost</attribute-->
    </mbean>


    And my code uses the Scheduler service to send a JMS Message every 10 secs to each client to probe if it's alive.
    Maybe this will help....
    Thanks,
    Marcelo

  • 3. Re: JMS over HTTP problem
    Marcelo Klein Newbie

    sorry, but neither the quote nor the code is displaying correclty the "" in the code.
    Any ideas about how to solve this problem?
    Maybe anyone has changed this ping period times to a correct situation?
    Thanks a lot. Any help will be appreciated.
    Marcelo.

  • 4. Re: JMS over HTTP problem
    ducngo Newbie

    Hi,
    I'm having similar problem with a JMS client listening on a Queue over HTTPIL on JBOSS 3.2.3.

    My JMS client can be configured to work on both UIL2 and HTTPIL by using different jndi.properties files. This client is registered to listen on queue/testQueue on JBOSS-JMS.

    And I am using "jmx-console" to view number of "receivers" for "testQueue" just to test if HTTPIL and UIL2 can detect disconnection of the client.

    Result:
    - When JMS client connects via UIL2, jmx-console reports number of receivers as 1. As soon as the client is "killed", number of receivers is reset to 0.
    - When JMS client connects via HTTPIL and is "killed", the number of receivers is not reset to 0 and still indicates that one client is connected with ID like this (using jmx-console -> "listReceivers" on the testQueue) - same as before it was killed:
    [org.jboss.mq.Subscription{connection=SpyDistributedConnection:ID:1/a192e723111b867288c50e3c702fab74 subscriptionId=-2147483648 destination=QUEUE.testQueue messageSelector=null Local Create}]

    This is what I played with
    => I've checked the configuration of HTTPIL service in jms\jbossmq-httpil.sar\META-INF\jboss-service.xml and set PingPeriod to 500 ms and repeat the test but nothing change.
    => Using jmx-console to configure this PingPeriod parameter did not make any difference.
    => Looking at the source code I found that PingPeriod is not used:
    1. jboss-3.2.3-src\messaging\src\main\org\jboss\mq\il\http\HTTPServerIL.java:

    ...
     * @author Nathan Phelps (nathan@jboss.org)
     * @version $Revision: 1.1.2.1 $
     * @created January 15, 2003
    ....
    line 271
     public void ping(ConnectionToken dc, long clientTime) throws Exception
     {
     // This is never called because we don't do pings. It is here for completeness.
     if (log.isTraceEnabled())
     {
    .....


    2. jboss-3.2.3-src\messaging\src\main\org\jboss\mq\il\http\HTTPServerILService.java:
    ...
     * @author Nathan Phelps (nathan@jboss.org)
     * @version $Revision: 1.1.2.2 $
     * @created January 15, 2003
    ...
    line 64
     public void startService() throws Exception
     {
     super.startService();
     this.pingPeriod = 0; // We don't do pings.
     if (this.url == null)
    ....


    I guess this is why "HTTPIL" failed to detect client disconnection.

    Is there any reason for not "do pings" for HTTPIL service?

    Thanks,

  • 5. Re: JMS over HTTP problem
    ducngo Newbie

    It seems that even PingPeriod is set, it won't fix the problem because there is a HTTPClientIL instance created on the JBOSS to listen on the queue on behalf of remote HTTP JMS client - the PingTask only applied to this instance that's why PingPeriod is turned off.

    I guess that the only way available now is to use ClientMonitorInterceptor as Adrian suggested in another thread but this means that all the messages in the queue from the time the HTTP client is "killed" to the time it's detected as inactive to be removed would be "lost".

    OR go and change the code yourself to fix this up?

  • 6. Re: JMS over HTTP problem
    Adrian Brock Master

    Yes, the problem with http is that is stateless. There is nothing the server
    can keep open (like a tcp/ip connectio) to detect when a client fails.

    The client monitor helps, but only if the client is pinging to keep the connection alive.
    Is it not just a case of setting the PingPeriod in deploy/jms/jbossmq-httpil.sar/META-INF/jboss-service.xml
    to something other than 0 (zero)?

  • 7. Re: JMS over HTTP problem
    ducngo Newbie

    The main problem I found with the current HTTPIL for JMS is that the server will not know if the client is still connected or not - HTTP is stateless.

    When a client is connected over HTTPIL and registers as a MessageListener for a queue, an instance of HTTPClientIL is created on the server which stores messages on behalf of the JMS HTTP client. When the HTTP connection from client to server is "interruptedly killed", the instance of HTTPClientIL still exists accepting messages and store them to HTTPClientILStorageQueue. Thus any message sent to this HTTPClientIL instance is lost.

    When JMS HTTP client tries to "reconnect" after detecting the failure to the JMS HTTPIL server, "another" instance of HTTPClientIL is created. The first one would be "finalized" when the HTTP session is timeout on tomcat. But until then there are still JMS messages received and lost in that HTTPClientIL instance.

    So the current HTTPIL is good for sending JMS messages to the queues/topics but it's not good for receiving JMS messages. I have to at the end write a web service for HTTP client to poll for received JMS messages instead and persistently manage the connection to the queue/topic on the server side.

  • 8. Re: JMS over HTTP problem
    Adrian Brock Master

    I can't help people if they don't read my responses.

  • 9. Re: JMS over HTTP problem
    Kobi Ianko Apprentice

    Hi Adrian,

    I'm trying to config JMS over HTTP,

    I was able to config all EJB calls to work with HTTP, using this article:

    http://community.jboss.org/wiki/EJBOverHTTPWithLegacyInvoker

     

    but JMS did not work over 80, and had no success after config the  "$JBoss_Server\deploy\jms\jbossmq-httpil.sar\META-INF\jboss-service.xml" file also.

     

    can you help me with steps to succeed in this task.

     

    10x, Kobi

    I'm sorry if this is the wrong place to post me question,

    but I'm desperate for reply.

  • 11. Re: JMS over HTTP problem
    Kobi Ianko Apprentice

    Hi Adrian,

    I'm working with JBoss 4.0.5, EJB 2.1 only, on windows and linux.

     

    on the FAQ you attached it looks like it only for linux, and only changes port 8080 to 80 (clients will still connect on port 1099),

     

    I'd like clients to connect via:

     

    Context.INITIAL_CONTEXT_FACTORY, "org.jboss.naming.HttpNamingContextFactory
    Context.PROVIDER_URL, "http://[externalHost]:80/invoker/JNDIFactory"


    and get all ejb calls and jms working well.
    with the article I've attached in the last post, I've got ejb calls to work on port 80.
    but jms in not working.

    10x for your help,
    Kobi