[weld-dev] Application scoped bean and its lifecycle

Martin Kouba mkouba at redhat.com
Mon May 22 06:34:01 EDT 2017


I don't recommend downgrading Weld. A more important issues could be 
fixed in newer versions.

In your case, I would modify the Test bean to count with multiple 
@Initialized events and replace @Destroyed with @PreDestroy callback:

class Test {

void appContextInit(@Observes @Initialized(ApplicationScoped.class) init) {
  // Empty body - force eager instantiation
}

@PostConstruct
void onInit() {
  // logic... will only be called once
}

@PreDestroy
void onDestroy() {
  // logic.... will be called once before 
@Destroyed(ApplicationScoped.class)
}

}



Dne 22.5.2017 v 12:03 Alex Sviridov napsal(a):
> Martin,
> 
> Thank you for your answer. I replaced 2.3.5.Final with 2.2.16.Final. 
> Besides in 2.2.16
> manifest I had to export package org.jboss.weld.config which is used by 
> pax-cdi.
> 
> Now  on bundle start:
> Test was created.
> java.lang.Object at 6bc3928f
> Test was initialized
> 
> Now  on bundle stop:
> java.lang.Object at 6bc3928f
> Test was destroyed.
> 
> Понедельник, 22 мая 2017, 12:27 +03:00 от Martin Kouba <mkouba at redhat.com>:
> 
> 
>     Dne 22.5.2017 v 11:14 Alex Sviridov napsal(a):
>      > Martin,
>      >
>      > In your message you wrote : "Up to version 2.2 Weld did not fire
>      > @Initialized/@Destroyed events for
>      > @ApplicationScoped for non-web modules.".
>      >
>      > In WELD-2389 you wrote : "Right now, this service is registered
>     for any
>      > non-SE environment".
>      >
>      > I use OSGi + PAX-CDI + WELD + JAVAFX. As I suppose this is a SE
>      > application (not EE).
>      > Could you explain "Right now, this service is registered for any
>     non-SE
>      > environment" ?
> 
>     Well, I'm talking about Weld SPI and I'm refering to the environment
>     info provided by the integrator. PAX CDI provides a custom
>     implementation of org.jboss.weld.bootstrap.api.Environment, which is
>     fine. The problem is that Weld currently skips registration only if
>     org.jboss.weld.bootstrap.api.Environments.SE is used.
> 
>      >
>      > Best regards, Alex
>      >
>      >
>      > Понедельник, 22 мая 2017, 11:51 +03:00 от Martin Kouba
>      > <mkouba at redhat.com <mailto:mkouba at redhat.com>>:
>      >
>      > Ok, now I know what's going on.
>      >
>      > The event with payload "Application context initialized." comes
>      > directly
>      > from Weld. Whereas the second one java.lang.Object at 48813e62 comes
>     from
>      > PAX CDI [1].
>      >
>      > Up to version 2.2 Weld did not fire @Initialized/@Destroyed
>     events for
>      > @ApplicationScoped for non-web modules. The behavior changed in 2.3 -
>      > see also WELD-1821 [2].
>      >
>      > This explains the events fired twice.
>      >
>      > WRT Test bean instance created twice - the problem is that
>      > @Destroyed(ApplicationScoped.class) event is fired after the actual
>      > destruction. So if you declare an observer on an @ApplicationScoped
>      > you're entering the "undefined behavior zone". In Weld, the Test
>      > bean is
>      > created again.
>      >
>      > I've created WELD-2389 [3] to track this issue.
>      >
>      > Thanks,
>      >
>      > Martin
>      >
>      > [1]
>      >
>     https://github.com/ops4j/org.ops4j.pax.cdi/blob/master/pax-cdi-weld/src/main/java/org/ops4j/pax/cdi/weld/impl/WeldCdiContainer.java#L154
>      >
>      > [2]
>      > https://issues.jboss.org/browse/WELD-1821
>      >
>      > [3]
>      > https://issues.jboss.org/browse/WELD-2389
>      >
>      >
>      > Dne 22.5.2017 v 09:57 Alex Sviridov napsal(a):
>      > > Hi Martin
>      > >
>      > > Thank you for your answer.
>      > >
>      > > 1) I don't inject Test class anywhere.
>      > > 2) I modified init and destroy methods:
>      > > public void init(@Observes @Initialized(ApplicationScoped.class)
>      > > Object init) {
>      > > System.out.println(init);
>      > > System.out.println("Test was initialized");
>      > > }
>      > >
>      > > public void destroy(@Observes @Destroyed(ApplicationScoped.class)
>      > > Object init) {
>      > > System.out.println(init);
>      > > System.out.println("Test was destroyed.");
>      > > }
>      > >
>      > > Now on bundle start:
>      > >
>      > > Test was created.
>      > > Application context initialized.
>      > > Test was initialized
>      > > java.lang.Object at 48813e62
>      > > Test was initialized
>      > >
>      > > Now on bundle stop:
>      > >
>      > > java.lang.Object at 48813e62
>      > > Test was destroyed.
>      > > Test was created.
>      > > Application context destroyed.
>      > > Test was destroyed.
>      > >
>      > >
>      > > Понедельник, 22 мая 2017, 10:48 +03:00 от Martin Kouba
>      > > <mkouba at redhat.com <mailto:mkouba at redhat.com>
>     <mailto:mkouba at redhat.com <mailto:mkouba at redhat.com>>>:
>      > >
>      > > Hi Alex,
>      > >
>      > > this looks really weird. Could you try to print out the event
>      > payload,
>      > > e.g. System.out.println(init)?
>      > >
>      > > Also you should be always very careful when using code inside the
>      > > no-args constructor of a normal-scoped bean -> it will be also
>      > executed
>      > > when creating a client proxy. In your case, if you do @Inject
>      > Test and
>      > > invoke any method then you will also see "Test was created" printed
>      > > twice.
>      > >
>      > > Martin
>      > >
>      > > Dne 22.5.2017 v 08:50 Alex Sviridov napsal(a):
>      > > > Hi all
>      > > >
>      > > > I use pax-cdi -1.0.0.RC2 and weld 2.3.5.Final and this is my test
>      > > class:
>      > > >
>      > > > import javax.enterprise.context.ApplicationScoped;
>      > > > import javax.enterprise.context.Destroyed;
>      > > > import javax.enterprise.context.Initialized;
>      > > > import javax.enterprise.event.Observes;
>      > > >
>      > > > @ApplicationScoped
>      > > > public class Test {
>      > > >
>      > > > public Test() {
>      > > > System.out.println("Test was created.");
>      > > > }
>      > > >
>      > > > public void init(@Observes @Initialized(ApplicationScoped.class)
>      > > Object
>      > > > init) {
>      > > > System.out.println("Test was initialized");
>      > > > }
>      > > >
>      > > > public void destroy(@Observes @Destroyed(ApplicationScoped.class)
>      > > > Object init) {
>      > > > System.out.println("Test was destroyed.");
>      > > > }
>      > > > }
>      > > >
>      > > > When I start test-bundle I see the following output:
>      > > > Test was created.
>      > > > Test was initialized
>      > > > Test was initialized
>      > > > When I stop test-bundle I see the following output:
>      > > > Test was destroyed.
>      > > > Test was created.
>      > > > Test was destroyed.
>      > > >
>      > > > So as result this bean was two times created, two times
>      > > initialized and two
>      > > > times destroyed.
>      > > >
>      > > > I expected that this bean must be once created, one initialized
>      > > and once
>      > > > destroyed.
>      > > >
>      > > > Is this a bug that must be reported or my mistake?
>      > > >
>      > > > --
>      > > > Alex Sviridov
>      > > >
>      > > >
>      > > > _______________________________________________
>      > > > weld-dev mailing list
>      > > > weld-dev at lists.jboss.org <mailto:weld-dev at lists.jboss.org>
>     <mailto:weld-dev at lists.jboss.org <mailto:weld-dev at lists.jboss.org>>
>      > <mailto:weld-dev at lists.jboss.org
>     <mailto:weld-dev at lists.jboss.org> <mailto:weld-dev at lists.jboss.org
>     <mailto:weld-dev at lists.jboss.org>>>
>      > > > https://lists.jboss.org/mailman/listinfo/weld-dev
>      > > >
>      > >
>      > > --
>      > > Martin Kouba
>      > > Senior Software Engineer
>      > > Red Hat, Czech Republic
>      > >
>      > >
>      > >
>      > > --
>      > > Alex Sviridov
>      >
>      > --
>      > Martin Kouba
>      > Senior Software Engineer
>      > Red Hat, Czech Republic
>      >
>      >
>      >
>      > --
>      > Alex Sviridov
> 
>     -- 
>     Martin Kouba
>     Senior Software Engineer
>     Red Hat, Czech Republic
> 
> 
> 
> -- 
> Alex Sviridov

-- 
Martin Kouba
Senior Software Engineer
Red Hat, Czech Republic


More information about the weld-dev mailing list