javaandroidexceptionevent-busgreenrobot-eventbus

GreenRobot Exception : de.greenrobot.event.EventBusException: Invoking subscriber failed


Time to time I get this exception.

I just use green-robot the standard way, between views, fragments, activities, services and the app, with the default instance, and time to time some stickyEvents.

I did't find any other post that are related to this exception. Any idea, or hint to start my investigation ?

The event bus is working nicely (~ 20 events, 10 subscribers), everything is user triggered so no big workload in the field.

the complete stack-trace is here :

de.greenrobot.event.EventBusException: Invoking subscriber failed
10-27 15:37:00.522 25414-25414/fr.tech.app..u E/AndroidRuntime:     at de.greenrobot.event.EventBus.handleSubscriberException(EventBus.java:518)
10-27 15:37:00.522 25414-25414/fr.tech.app..u E/AndroidRuntime:     at de.greenrobot.event.EventBus.invokeSubscriber(EventBus.java:500)
10-27 15:37:00.522 25414-25414/fr.tech.app..u E/AndroidRuntime:     at de.greenrobot.event.EventBus.postToSubscription(EventBus.java:429)
10-27 15:37:00.522 25414-25414/fr.tech.app..u E/AndroidRuntime:     at de.greenrobot.event.EventBus.postSingleEventForEventType(EventBus.java:410)
10-27 15:37:00.522 25414-25414/fr.tech.app..u E/AndroidRuntime:     at de.greenrobot.event.EventBus.postSingleEvent(EventBus.java:383)
10-27 15:37:00.522 25414-25414/fr.tech.app..u E/AndroidRuntime:     at de.greenrobot.event.EventBus.post(EventBus.java:263)
10-27 15:37:00.522 25414-25414/fr.tech.app..u E/AndroidRuntime:     at fr.u.app.u.Dialog.TastingNavigationDialog$1.onSelection(TastingNavigationDialog.java:42)

error is triggered from a MaterialDialog instance :

  dialogBuilder = new MaterialDialog.Builder(context)
            .title(R.string.dialogTastingNavigationTripTitle)
            .negativeText(R.string.buttonCancel)
            .cancelable(false)
            .adapter(listAdapter, new MaterialDialog.ListCallback() {
                @Override
                public void onSelection(MaterialDialog dialog, View itemView, int which, CharSequence text) {
                    EventBus.getDefault().post(new TastingPageToEvent(listAdapter.list.get(which), which));
                    dialog.dismiss();
                }
            });

Edit

I found one thing that trigger the exception, is posting one stickyEvent from one Fragment. It is intended that a appearing soon fragment will be able to get back that sticky event.

When going to Eventbus source, it stops at :

   void invokeSubscriber(Subscription subscription, Object event) {
        try {
            subscription.subscriberMethod.method.invoke(subscription.subscriber, event);
        } catch (InvocationTargetException e) {
            handleSubscriberException(subscription, event, e.getCause());
        } catch (IllegalAccessException e) {
            throw new IllegalStateException("Unexpected exception", e);
        }
    }

Edit

Here is the scenario.

public class TopEvent {
    String name;
    public TopEvent(String name){
        this.name = name;
    }
}

public class MyEvent extends TopEvent {
    String extraInfo;
    public MyEvent(String name, String extra){
        super(name);
        this.extraInfo = extra; 
    }
}

Here is one Fragment Tx :

...
EventBus.getDefault().postStickyEvent(new MyEvent("Stack","Overflow");
...

Here is a second Fragment Rx

...
String extra = EventBus.getDefault().getStickyEvent(MyEvent.class).extraInfo;
...

Here is a service (the one that got a Strange behavior)

public class MyService extends ServiceĀ {

    ...

    EventBus.getDefault().registerSticky(this)

    onEvent(TopEvent event){
       ...
       ...
    }

}

At end of the onEvent, the exception is thrown. As if they were some hidden behavior with sticky extended Event (from super) posted that triggers non-sticky event of super event.


Solution

  • This is was due to EventBus configuration :

    EventBus.builder().throwSubscriberException(BuildConfig.DEBUG).installDefaultEventBus();
    

    However I have difficulties to understand why this option is interesting. In fact we only (almost) see the exception of the subscriber that failed, because there were another exception of a subscriber. But it is often hidden. So for why is this interesting ?