En CDI existe el @ApplicationScoped
y el pseudo-alcance ( javax.inject
) @Singleton
. ¿Cuál es la diferencia entre ellos? Además del hecho de que @ApplicationScoped
es proxy y @Singleton
no lo es.
¿Puedo cambiar mi @Singleton
frijol a @ApplicationScoped
? ¿Puede @ApplicationScoped
bean tener dos (o más) instancias?
@ApplicationScoped
y@Singleton
en su sección 5.4 (p. 36).Respuestas:
@Singleton
no forma parte de la especificación CDI. Es parte de EJB yjavax.inject
(JSR-330). No se menciona en la especificación cuál es su comportamiento, por lo que solo puede confiar en lo que está escrito en la documentación de Weld.fuente
@Singleton
. Se muestra en un solo ejemplo, sin aclaraciones. Es cierto que CDI se basa enjavax.inject
, pero estrictamente hablando, no es parte de la especificación CDI. Dicho esto, corrigí un poco mi respuesta.en resumen: incluso puedes mezclarlo (
@Singleton
y@ApplicationScoped
) y tiene sentido en algunos escenarios. (¡y funciona como se esperaba en el mío!)Además de las otras respuestas hasta ahora, me gustaría agregar algunos puntos más para aclarar en escenarios del mundo real.
Para mí, esta pregunta se desarrolló a partir de ¿Cómo obligo a un bean de ámbito de aplicación a crear una instancia al iniciar la aplicación? En alguna discusión allí dije esto y no puedo encontrar un argumento válido en su contra hasta ahora:
argumentos (discutibles pero no concluyentes) (desde mi punto de vista) en su contra hasta ahora: (@BalusC y todos los demás: me gustaría verlos siendo concluyentes, pero si no, lo anterior puede ser cierto y, sin embargo, los argumentos pueden todavía ayudar al lector a obtener las diferencias / ventajas / desventajas / malas / buenas prácticas)
EJB frente a Bean gestionado
pero:
... que todavía es cierto en mi caso.
Singleton EJB vs.Bean con ámbito de aplicación
Cierre
pero:
(No puedo ver el mazo aquí, lo siento ...) Es bueno saber los valores predeterminados de bloqueo (no lo sabía), pero esto parece ser incorrecto nuevamente: Tutorial de Oracle Java EE 6 sobre la administración del acceso concurrente en un Bean de sesión singleton
fuente
Por lo general, cuando desea tener solo una instancia de algún objeto, probablemente debería usar la
@ApplicationScoped
anotación; dicho objeto es proxy y, por lo tanto, incluso se puede serializar correctamente de forma inmediata.Por otro lado, también hay muchos casos en los que solo desea una instancia de la clase, pero dicha clase no puede ser sustituida por proxy (por ejemplo, debido a que es final), entonces
@Singleton
es un rescate. PorqueSingleton
es un pseudo-alcance y no se está utilizando como proxy como cualquier alcance "normal".fuente
@Singleton
en JSR-299 se refiere a beans de sesión Singleton (javax.ejb.Singleton
, nojavax.inject.Singleton
), no a beans administrados JSR-299 en un ámbito integrado llamado Singleton.Puede encontrar en su servidor que
@ApplicationScoped
sea uno por EAR o uno por WAR / EJB-JAR, ya que no está claro en la especificación, pero definitivamente no debe esperar que sea uno por JVM.fuente
Hay una diferencia más:
@Singleton
no es un bean que define anotaciones, ya que elSingleton
alcance no es un alcance normal. Entonces@ApplicationScoped
es el frijol que define las anotaciones.Con la especificación CDI 1.1: cuando la aplicación en modo de descubrimiento = anotado, Weld no identifica los beans con
@Singleton
y no carga estefuente
Una de las principales diferencias que puede escribir su clase con el constructor predeterminado tiene un modificador de acceso privado cuando se usa
javax.inject.Singleton
, pero su clase debe tener un constructor predeterminado con al menos un modificador de acceso predeterminado cuando se usajavax.enterprise.context.ApplicationScoped
y esta es laJBOSS 6.1 GA Final
implementaciónfuente