3 Replies Latest reply on Dec 12, 2013 5:28 PM by philipp91

    IllegalArgumentException: WELD-001456 with @Observes(IF_EXISTS)

    philipp91

      Hi,

       

      I am using Weld 2.1.0.Final. Please read below for the error description. First I describe the overall situation (just in case anyone can give tips on that as well :-) ).

       

      Currently I have the problem that I would technically need something like scope-specialization:

      - I have a WindowContext and a @WindowScoped annotation that allows beans to live "per-window" in JavaFX.

      - Thanks to previous help from this forum, it works fine.

      - I have different types of windows. Each scope-instance will always be of one type only. But of course I use the same scope/Context for all kinds of windows that I have.

      - In order to distinguish, I have an abstract class WindowInfo<T> and for each type of window I have a concrete class SomeKindOfWindowInfo extends WindowInfo<SomeClass>.

      - Initially I ran into some problems using @Inject WindowInfo<?>, because there are of course mulitple beans available in my deployment that match this injection points (all the concrete WindowInfo-Implementations that I have). However, I managed to resolve that by either using the kind I want, or by calling BeanManager.getReference(bean, WindowInfo.class, null, true) manually. (Note that the "null" parameter is the CreationalContext, preventing new WindowInfo-instances from being created, and therefore only returns the single one I want).

      - When I use @Observes, all instances are created anyway, so I used @Observes(notifyObserver=IF_EXISTS) instead, leading to the error described below.

      => If someone has a better idea on how to have different types of windows (each with its own model-type, and some specific code) allowing each window instance to have its own scope instance, that would be great. I read about Generic Beans from Weld extensions, but I didn't quite understand it, it's probably not what I want, because it doesn't have anything to do with the Java-generics I use?

       

       

      Without regard to my current setup, there seems to be the following problem:

      void receiveEvent(@Observes(notifyObserver=Reception.IF_EXISTS) SomeEventType event, SomeOtherClass parameter) { .. }

       

      When firing this event (Event<SomeEventType> eventInstance.fire(new SomeEventType()), I get:

      org.jboss.weld.exceptions.IllegalArgumentException: WELD-001456: Argument creationalContext must not be null

       

      The reason is:

      - ObserverMethodImpl.sendEvent() correctly finds out that there should be no CreationalContext.

      - In case the bean does not exist, nothing happens.

      - If the bean exists, the parameter will be resolved by MethodInjectionPoint.getParameterValues(), using the null-CreationalContext, leading to the exception in BeanManagerImpl.getReference(InjectionPoint, Bean, null).

       

      In my case, the parameter type "SomeOtherClass" is the a sub-class of the class containing the receiveEvent-method, but the error might occur even without that.

       

      Thank you for any help, workaround suggestions or even ideas about how to solve my window-typing-thing differently!

      Philipp

        • 1. Re: IllegalArgumentException: WELD-001456 with @Observes(IF_EXISTS)
          mkouba

          Hi Philipp,

          could you post the full stack trace?

          • 2. Re: IllegalArgumentException: WELD-001456 with @Observes(IF_EXISTS)
            philipp91

            Here it is (the important part is at the bottom). Note that de.schulscheduler is the custom namespace of the application and I raised the exception by pressing Ctrl+Q, which executes an action that at some point fires the event. Another thing to note might be the "de.schulscheduler.windows.AttachedMenuItem.fire(AttachedMenuItem.java:21)" in the top part of the stack trace. This is some code that first activates the WindowContext (which extends AbstractContext), then passes the event through and deactivates it afterwards. While the bean raising the event (WindowManager) is @ApplicationScoped, the bean(s) receiving the event is @WindowScoped (i.e. handled by WindowContext).

             

            java.lang.RuntimeException: java.lang.reflect.InvocationTargetException

              at javafx.fxml.FXMLLoader$ControllerMethodEventHandler.handle(FXMLLoader.java:1449)

              at com.sun.javafx.event.CompositeEventHandler.dispatchBubblingEvent(CompositeEventHandler.java:69)

              at com.sun.javafx.event.EventHandlerManager.dispatchBubblingEvent(EventHandlerManager.java:217)

              at com.sun.javafx.event.EventHandlerManager.dispatchBubblingEvent(EventHandlerManager.java:170)

              at com.sun.javafx.event.BasicEventDispatcher.dispatchEvent(BasicEventDispatcher.java:37)

              at com.sun.javafx.event.EventDispatchChainImpl.dispatchEvent(EventDispatchChainImpl.java:92)

              at com.sun.javafx.event.EventUtil.fireEventImpl(EventUtil.java:53)

              at com.sun.javafx.event.EventUtil.fireEvent(EventUtil.java:28)

              at javafx.event.Event.fireEvent(Event.java:171)

              at javafx.scene.control.MenuItem.fire(MenuItem.java:456)

              at de.schulscheduler.windows.AttachedMenuItem.fire(AttachedMenuItem.java:21)

              at com.sun.javafx.scene.control.skin.MenuButtonSkinBase$5.run(MenuButtonSkinBase.java:309)

              at com.sun.javafx.scene.KeyboardShortcutsHandler.processAccelerators(KeyboardShortcutsHandler.java:296)

              at com.sun.javafx.scene.KeyboardShortcutsHandler.dispatchBubblingEvent(KeyboardShortcutsHandler.java:119)

              at com.sun.javafx.event.CompositeEventDispatcher.dispatchBubblingEvent(CompositeEventDispatcher.java:38)

              at com.sun.javafx.event.BasicEventDispatcher.dispatchEvent(BasicEventDispatcher.java:37)

              at com.sun.javafx.event.EventDispatchChainImpl.dispatchEvent(EventDispatchChainImpl.java:92)

              at com.sun.javafx.event.BasicEventDispatcher.dispatchEvent(BasicEventDispatcher.java:35)

              at com.sun.javafx.event.EventDispatchChainImpl.dispatchEvent(EventDispatchChainImpl.java:92)

              at com.sun.javafx.event.EventUtil.fireEventImpl(EventUtil.java:53)

              at com.sun.javafx.event.EventUtil.fireEvent(EventUtil.java:33)

              at javafx.event.Event.fireEvent(Event.java:171)

              at javafx.scene.Scene$KeyHandler.process(Scene.java:3496)

              at javafx.scene.Scene$KeyHandler.access$2300(Scene.java:3455)

              at javafx.scene.Scene.impl_processKeyEvent(Scene.java:1904)

              at javafx.scene.Scene$ScenePeerListener.keyEvent(Scene.java:2253)

              at com.sun.javafx.tk.quantum.GlassViewEventHandler$KeyEventNotification.run(GlassViewEventHandler.java:136)

              at com.sun.javafx.tk.quantum.GlassViewEventHandler$KeyEventNotification.run(GlassViewEventHandler.java:100)

              at java.security.AccessController.doPrivileged(Native Method)

              at com.sun.javafx.tk.quantum.GlassViewEventHandler.handleKeyEvent(GlassViewEventHandler.java:163)

              at com.sun.glass.ui.View.handleKeyEvent(View.java:520)

              at com.sun.glass.ui.View.notifyKey(View.java:953)

              at com.sun.glass.ui.win.WinApplication._runLoop(Native Method)

              at com.sun.glass.ui.win.WinApplication.access$100(WinApplication.java:17)

              at com.sun.glass.ui.win.WinApplication$3$1.run(WinApplication.java:67)

              at java.lang.Thread.run(Thread.java:724)

            Caused by: java.lang.reflect.InvocationTargetException

              at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)

              at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:57)

              at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)

              at java.lang.reflect.Method.invoke(Method.java:606)

              at sun.reflect.misc.Trampoline.invoke(MethodUtil.java:75)

              at sun.reflect.GeneratedMethodAccessor1.invoke(Unknown Source)

              at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)

              at java.lang.reflect.Method.invoke(Method.java:606)

              at sun.reflect.misc.MethodUtil.invoke(MethodUtil.java:279)

              at javafx.fxml.FXMLLoader$ControllerMethodEventHandler.handle(FXMLLoader.java:1446)

              ... 35 more

            Caused by: org.jboss.weld.exceptions.IllegalArgumentException: WELD-001456: Argument creationalContext must not be null

              at org.jboss.weld.util.Preconditions.checkArgumentNotNull(Preconditions.java:40)

              at org.jboss.weld.manager.BeanManagerImpl.getReference(BeanManagerImpl.java:767)

              at org.jboss.weld.injection.ParameterInjectionPointImpl.getValueToInject(ParameterInjectionPointImpl.java:76)

              at org.jboss.weld.injection.MethodInjectionPoint.getParameterValues(MethodInjectionPoint.java:127)

              at org.jboss.weld.injection.MethodInjectionPoint.invokeOnInstanceWithSpecialValue(MethodInjectionPoint.java:93)

              at org.jboss.weld.event.ObserverMethodImpl.sendEvent(ObserverMethodImpl.java:266)

              at org.jboss.weld.event.ObserverMethodImpl.sendEvent(ObserverMethodImpl.java:253)

              at org.jboss.weld.event.ObserverMethodImpl.notify(ObserverMethodImpl.java:232)

              at org.jboss.weld.event.ObserverNotifier.notifyObserver(ObserverNotifier.java:169)

              at org.jboss.weld.event.ObserverNotifier.notifyObserver(ObserverNotifier.java:165)

              at org.jboss.weld.event.ObserverNotifier.notifyObservers(ObserverNotifier.java:119)

              at org.jboss.weld.event.ObserverNotifier.fireEvent(ObserverNotifier.java:112)

              at org.jboss.weld.event.EventImpl.fire(EventImpl.java:83)

              at de.schulscheduler.windows.WindowManager.closeCurrentWindow(WindowManager.java:173)

              at de.schulscheduler.windows.WindowManager.closeAllWindows(WindowManager.java:240)

              at de.schulscheduler.windows.WindowManager$Proxy$_$$_WeldClientProxy.closeAllWindows(Unknown Source)

              at de.schulscheduler.ui.eingabe.EingabeFensterController.handleBeendenAction(EingabeFensterController.java:145)

              ... 45 more

            • 3. Re: IllegalArgumentException: WELD-001456 with @Observes(IF_EXISTS)
              philipp91

              I just realized that in most of the observer methods I don't even use the second parameter, it was just there for copy-paste-reasons ...

              In the other cases, I was able to replace it by a normal @Inject field. This should be a general workaround, in case anyone else is affected. If you consider this a bug anyway, I am happy to provide any more information you need to fix it.

               

              My guess for a fix would be to change ObserverMethodImpl.sendEvent(T) to:

               

                  protected void sendEvent(final T event) {

                      if (observerMethod.getAnnotated().isStatic()) {

                          sendEvent(event, null, beanManager.createCreationalContext(declaringBean));

                      } else {

                          CreationalContext<X> creationalContext;

                          if (reception.equals(Reception.IF_EXISTS)) {

                              creationalContext = null;

                          } else {

                              creationalContext = beanManager.createCreationalContext(declaringBean);

                          }

               

               

                          Object receiver = getReceiverIfExists(creationalContext);

                          if (receiver != null) {

                              // INSERT FROM HERE

                              if (creationalContext == null) {

                                  creationalContext = beanManager.createCreationalContext(declaringBean);

                              }

                              // TO HERE

                              sendEvent(event, receiver, creationalContext);

                          }

                      }

                  }