9 Replies Latest reply on Nov 4, 2005 2:16 PM by starksm64

    Supporting persistence of ejb timers

    starksm64

      I spent some time looking at supporting persistence of timers across ejb redeployments/server shutdowns and org.jboss.ejb.txtimer.EJBTimerService needs to change to expose such a notion:

       /**
       * Remove the TimerService for a given TimedObjectId
       *
       * @param containerId The identifier for a class of TimedObjects
       * @param pKey The primary key for an instance of a TimedObject, may be null
       * @param removePersistentState a flag indicating if the timer persistence state should be removed
       */
       void removeTimerService(ObjectName containerId, Object pKey, boolean removePersistentState) throws IllegalStateException;
      
       /**
       * Restore the timers for a given ejb container.
       *
       * @param containerId The identifier for a class of TimedObjects
       */
       void restoreTimers(ObjectName containerId);
      


      The org.jboss.ejb.txtimer.PersistencePolicy interface also needs a more targeted restoration notion
       /**
       * Restore the persistet timers for the given container
       * @param containerID the id of the ejb container whose timers should be restored. A null value indicates all container timers should be restored.
       * @return the timer handles that need to be restored
       */
       List<TimerHandleImpl> restoreTimers(ObjectName containerID);
      


      A general problem with the current PersistencePolicy interface is that too much detail about the restoration process is pushed to the PersistencePolicy implementation. Currently, the PersistencePolicy.restoreTimers is responsible for creating the timers in the various ejb containers.

      This should simply be returning the list of TimerHandleImpl that need to be created. Currently the org.jboss.ejb.txtimer.DatabasePersistencePolicy has to know implementation details of the ejb container timer service that I don't think it should. Its coupling of restoration to the server startup is also something it should not be dealing with. Restoration needs to be done on redeployment as well if timers persist across restarts.

      Restoration of timers should be requests from the ejb deployer to the ejb timer service. Hence the addition of the restoreTimers(ObjectName) to the EJBTimerService interface. If we want the initial restoration to be coupled to completion of the server startup, this notion needs to be moved from the DatabasePersistencePolicy to the EJBTimerServiceImpl.


        • 1. Re: Supporting persistence of ejb timers
          starksm64

          The main related jira issue which links in some others such as updating the timer pm to use hibernate is:

          http://jira.jboss.com/jira/browse/JBAS-1091

          • 2. Re: Supporting persistence of ejb timers
            starksm64

            A related topic is how to avoid leaking the hibernate dependencies into the user space: http://www.jboss.com/index.html?module=bb&op=viewtopic&t=70438

            • 3. Re: Supporting persistence of ejb timers
              gnvenky

              Scott,

              Developing code understanding for TimerServices.
              Also facing some build issues after checking out
              jboss-4.0.x
              Putting down my notes, please let me know if i am on
              the right path.

              Problem Statement:
              For all Stateless beans (MDB, Entity, Session),
              support persistence across server shutdown/ startup
              (or) restart. Persistence across crashes is already
              provided. If timer expires during the shutdown period,
              execute it once on system startup.

              Code Understanding:

              All interfaces defined under jboss/j2ee/src
              TimerImpl code is at:
              jboss/server/src/main/org/jboss/ejb/txtimer

              Timer method Services start with two transaction
              modes:
              NotSupported/ RequiredNew

              TimerImpl: Uses java.util.Timer and tracks tx state
              TimerServiceImpl: Binds the Timer with the
              TimerInvokerObject and provides impl. of createTimer
              calls
              TimerInvokerObjectImpl: implements the ejbTimeout
              Persistence policies and files are also present.

              Questions:
              1. What is the diff. between EJBTimerService and
              TimerService. Is it that EJBTimerService supports
              RequiredNew and TimerService is for NotSupported?

              2. Build is not going thru on Win XP for jboss-4.0.4,
              however succeeds for jboss-head. Using TortoiseCVS and
              anon. for checkout. Build error as follows:

              [javac] Compiling 24 source files to
              C:\JBOSS-~1\jboss-4.0\test\output\class
              es
              C:\JBOSS-~1\jboss-4.0\test\src\main\org\jboss\test\JBossTestCase.java:14
              :
              cannot
              resolve symbol
              symbol : class MBeanServerConnection
              location: package management
              import javax.management.MBeanServerConnection;
              ^
              C:\JBOSS-~1\jboss-4.0\test\src\main\org\jboss\test\JBossTestServices.jav
              a:13:
              ca
              nnot resolve symbol
              symbol : class MBeanServerConnection
              location: package management
              import javax.management.MBeanServerConnection;
              ^
              C:\JBOSS-~1\jboss-4.0\test\src\main\org\jboss\test\JBossTestServices.jav
              a:52:
              ca
              nnot resolve symbol
              symbol : class MBeanServerConnection
              location: class org.jboss.test.JBossTestServices
              protected MBeanServerConnection server;
              ^
              C:\JBOSS-~1\jboss-4.0\test\src\main\org\jboss\test\JBossTestServices.jav
              a:111:
              c
              annot resolve symbol
              symbol : class MBeanServerConnection
              location: class org.jboss.test.JBossTestServices
              public MBeanServerConnection getServer() throws
              Exception
              ^
              C:\JBOSS-~1\jboss-4.0\test\src\main\org\jboss\test\JBossTestServices.jav
              a:205:
              c
              annot resolve symbol
              symbol : class MBeanServerConnection
              location: class org.jboss.test.JBossTestServices
              protected Object invoke(MBeanServerConnection
              server, ObjectName name, String
              method, Object[] args, String[] sig)
              ^
              C:\JBOSS-~1\jboss-4.0\test\src\main\org\jboss\test\JBossTestCase.java:12
              2:
              canno
              t resolve symbol
              symbol : class MBeanServerConnection
              location: class org.jboss.test.JBossTestCase
              protected MBeanServerConnection getServer() throws
              Exception
              ^
              C:\JBOSS-~1\jboss-4.0\test\src\main\org\jboss\test\JBossTestSetup.java:1
              4:
              canno
              t resolve symbol
              symbol : class MBeanServerConnection
              location: package management
              import javax.management.MBeanServerConnection;
              ^
              C:\JBOSS-~1\jboss-4.0\test\src\main\org\jboss\test\JBossTestSetup.java:7
              3:
              canno
              t resolve symbol
              symbol : class MBeanServerConnection
              location: class org.jboss.test.JBossTestSetup
              protected MBeanServerConnection getServer() throws
              Exception
              ^
              C:\JBOSS-~1\jboss-4.0\test\src\main\org\jboss\test\JBossTestServices.jav
              a:116:
              c
              annot resolve symbol
              symbol : class MBeanServerConnection
              location: class org.jboss.test.JBossTestServices
              server =
              (MBeanServerConnection)initialContext.lookup(adaptorName);
              ^
              9 errors

              BUILD FAILED
              The dependent libraries are downloaded and correct
              under thirdparty and classpath does contain the paths.

              Also re-did the checkout.
              In some 3.2 build forums have seen similar errors..

              - rgds
              Venky

              • 4. Re: Supporting persistence of ejb timers
                dimitris

                Looking into the ejb timer persistence issue, I have a couple of questions:

                * Should timer persistence be enabled by default and let the user override this in the bean descriptor (e.g. <timer-persistence>false</timer-persistence>), or the other way round?

                * By changing the "internal" EJBTimerService API are we having the same integration issues with e.g. EJB3 wanting to run on previous jboss versions unchanged? If that is the case, I can add extra methods rather than change existing ones. I don't think we need extension interfaces for something used internally in jboss.

                * Since persistence is really a property of a TimerService, at the time of creation, rather than enhancing removeTimerService(..) we could instead offer new createTimerService(..) methods with the additional boolean flag.

                • 5. Re: Supporting persistence of ejb timers
                  dimitris

                  On the other hand, shouldn't timer persistence be just a matter of the chosen PersistencePolicy? i.e.

                  - if the NoopPersistencePolicy -> no persistence whatsoever
                  - if some other persistence policy is configured -> persistence enabled both for crash recovery and redeployments, which from the discussion, is what users really anticipate.

                  In the latter case, the persistent image is cleared when user code does a timer.cancel() or we offer some operation over the persistence mbean interface.

                  • 6. Re: Supporting persistence of ejb timers
                    starksm64

                     

                    "dimitris@jboss.org" wrote:
                    On the other hand, shouldn't timer persistence be just a matter of the chosen PersistencePolicy? i.e.

                    Yes, this is the path I think we should follow. A persistent timer exists until canceled or removed administratively.



                    • 7. Re: Supporting persistence of ejb timers
                      starksm64

                       

                      "dimitris@jboss.org" wrote:
                      Looking into the ejb timer persistence issue, I have a couple of questions:

                      ...

                      * By changing the "internal" EJBTimerService API are we having the same integration issues with e.g. EJB3 wanting to run on previous jboss versions unchanged? If that is the case, I can add extra methods rather than change existing ones. I don't think we need extension interfaces for something used internally in jboss.


                      Potentially, but as I have raised in the ejb3 forum such a dependency needs adequate isolation to allow for evolution of the timer implementation. If we can change this is a backward compatible way, fine, if not, ejb3 needs an isolation interface to deal with the changes.


                      • 8. Re: Supporting persistence of ejb timers
                        dimitris

                        I've tried the following changes, just want to make a quick check if I miss something, before I commit this in HEAD.

                        * The active timers for EJBs are not removed from persistent storage upon undeployment. Setting <timer-persistence> to false (default is true) at bean level, brings back the old behaviour (although I doubt anyone will use this)

                        * Upon deployment (container start) we'll attempt to restore any persisted timers found for the container (based on its name). A timer maybe found, either because the container had crashed, or because the timer was still active when the ejb was undeployed.

                        * The persistence policy is no longer responsible for timer restoration. Timers are not restored when the server has completed start-up. They are restored as ejbs are deployed (I assume this is okay since their dependencies must have been satisfied during container.start() ).

                        * The methods used by EJB3 are still there, although the default in this case is no timer persistence and no restoration (by looking at the code I think restoration from crashes was not working anyway for ejb3). We'll need to call the new EJBTimerService methods to get that functionality, whenever Bill is ready.

                        * BTW, I see in so many places in the code this pattern:
                        someMethod()
                        {
                        get a dynamic MBean proxy
                        make a single type-safe call
                        throw the proxy away
                        }
                        Is proxy creation really so cheap? Shouldn't those proxies be cached, or we are just lazy :)

                        Thanks

                        • 9. Re: Supporting persistence of ejb timers
                          starksm64

                          Yes, I agree with these statements. Caching requires a stable type system, which may not be meaningful for a shared service used with redeployment.