2 Replies Latest reply on Sep 20, 2011 10:21 AM by almac

    Waiting until bus is completely set-up?

    almac

      Is there a way to wait until the errai-bus is completely set-up?  I.e., that all the behind-the-scenes

      handshaking between client and server is finished, and all the associated interface computation is

      complete?

       

      The reason I ask:  I have code that, in the client-side module-init method (techinically, in the

      @PostConstruct init() method of the @EntryPoint class) calls a method which calls a method

      which invokes an RPC function.  This throws a runtime exception that looks like:

       

      {code}

      java.lang.RuntimeException: No service definition for: project.shared.MyService

        at org.jboss.errai.bus.client.api.builder.AbstractRemoteCallBuilder.call(AbstractRemoteCallBuilder.java:59)

        at org.jboss.errai.bus.client.api.base.MessageBuilder.createCall(MessageBuilder.java:122)

      {code}

       

      I traced the spaghetti of callbacks and generated code far enough to figure out that this

      was because the RPC call was being made before the ExtensionsLoader gets created

      and initialized by ClientMessageBusImpl.

       

      If RPC calls (and, probably, other functionality) cannot be made until some amount of set-up and

      client-server handshaking is done, is there any way to wait until that state is acheived? 

       

      In general (and certainly in the code I am working with), it's not necessarilly possible

      (due to abstraction barriers/etc) to tell which methods are going to end up invoking RPC calls

      (or other bus operations) --- so one cannot just say "Don't make an RPC invocations until

      so-and-so state is acheived."  But, I don't think it would be too onerous for user code to say

      "I'm not going to do *anything* until the bus infrastructure is ready to go." (hopefully with a

      timeout and some handler to gracefully deal with bus failure).

       

      ps:  The code in ClientMessageBusImpl.initializeMessagingBus() which creates the ExtensionsLoader

      does so like this:

      {code}

      new Timer() {

            @Override

            public void run() {

              incomingTimer.scheduleRepeating(POLL_FREQUENCY);

              ExtensionsLoader loader = GWT.create(ExtensionsLoader.class);

              loader.initExtensions(ClientMessageBusImpl.this);

            }

          }.schedule(5);

      {code}

      I don't know what it is waiting for, but waiting for a fixed time of "5 milliseconds" can't possibly be

      the right way to do it.

        • 1. Re: Waiting until bus is completely set-up?
          cbrock

          You want to use the ClientMessageBus.addPostInitTask(Runnable runnable).

           

          You can do this by doing: @Inject private MessageBus bus into the client bean, and in your @PostConstruct method use:

           

          ((ClientMessageBus) bus).addPostInitTask(new Runnable() {

             public void run() {

                // do code here after bus is initialized

            }

          });

           

           

          In our CDI plugin we expose a CDI Event called BusReadyEvent which handles this. We may consider creating some sort of injectable proxy in the future for non-CDI applications to do this more cleanly.

           

          The 5 millisecond delay is, I believe, needed for a cross-browser compatibility issue. Although, I will look into that and confirm that is the right reason.

          1 of 1 people found this helpful
          • 2. Re: Waiting until bus is completely set-up?
            almac

            Mike Brock wrote:

             

            You want to use the ClientMessageBus.addPostInitTask(Runnable runnable).

             

            You can do this by doing: @Inject private MessageBus bus into the client bean, and in your @PostConstruct method use:

             

            ((ClientMessageBus) bus).addPostInitTask(new Runnable() {

               public void run() {

                  // do code here after bus is initialized

              }

            });

            Awesome --- that does what I need to get done.  (It would be nice if the cast could be avoided, i.e. it would be cleaner if one could inject the more

            specific ClientMessageBus, since the code now requires that it be that kind of MessageBus, and since that's what one will always have on the client-side.)

            In our CDI plugin we expose a CDI Event called BusReadyEvent which handles this. We may consider creating some sort of injectable proxy in the future for non-CDI applications to do this more cleanly.

             

            The 5 millisecond delay is, I believe, needed for a cross-browser compatibility issue. Although, I will look into that and confirm that is the right reason.

            This seems like the kind of situation where the code (and future/present generations of its readers) would benefit greatly from a comment

            explaining which browsers are involved and why "5" is the magic number.