Un giorno fa la mia applicazione era un EAR, contenente un WAR, un JAR EJB e un paio di file JAR di utilità. Ho avuto una classe POJO Singleton in uno di quei file di utilità, ha funzionato, e tutto andava bene con il mondo:Come scrivere un Java Singleton EE/EJB Java?
EAR
|--- WAR
|--- EJB JAR
|--- Util 1 JAR
|--- Util 2 JAR
|--- etc.
Poi ho creato una seconda guerra e scoperto (nel modo più duro) che ogni guerra ha la sua proprio ClassLoader, quindi ogni WAR vede un singleton diverso, e le cose si interrompono da lì. Non è così buono
EAR
|--- WAR 1
|--- WAR 2
|--- EJB JAR
|--- Util 1 JAR
|--- Util 2 JAR
|--- etc.
Quindi, sto cercando un modo per creare un oggetto Singleton Java che funziona attraverso guerre (in tutto ClassLoader?). L'annotazione EJB @Singleton
sembrava abbastanza promettente fino a quando ho scoperto che JBoss 5.1 non sembra supportare quell'annotazione (che è stata aggiunta come parte di EJB 3.1). Mi sono perso qualcosa: posso usare @Singleton
con JBoss 5.1? L'aggiornamento a JBoss AS 6 non è un'opzione al momento.
In alternativa, sarei altrettanto felice di non dover utilizzare EJB per implementare il mio singleton. Cos'altro posso fare per risolvere questo problema? Fondamentalmente, ho bisogno di un hook semi-application * in un gruppo di altri oggetti, come i vari dati memorizzati nella cache, e le informazioni di configurazione dell'app. Come ultima risorsa, ho già pensato di unire le mie due WAR in una, ma sarebbe stato piuttosto infernale.
* Significato: disponibile praticamente ovunque sopra un determinato livello; per ora, per lo più nelle mie WAR, la vista e il controller (in senso sciolto).
Modifica: Dovrei davvero chiamarlo Java EE piuttosto che J2EE, non dovrei?
Edit 2: Molte grazie ancora a @Yishai per tutto l'aiuto. Dopo un po 'di prove ed errori sembra che io abbia capito come usare un singolo ClassLoader su WARs sotto JBoss 5. Sto descrivendo questo sotto per il mio bene, e spero che anche altri trovino questo utile.
N.B. questo è piuttosto diverso dal fare questo sotto JBoss 4 (vedi la risposta di Yishai o i miei link sotto).
Invece di scrivere un jboss-web.xml
per ogni guerra e un jboss.xml
per l'orecchio EJB-JAR, mettere un file jboss-classloading.xml
in ogni guerra, nella stessa posizione del DD (web.xml
). Il contenuto di jboss-classloading.xml
dovrebbero essere:
<?xml version="1.0" encoding="UTF-8"?>
<classloading
xmlns="urn:jboss:classloading:1.0"
name="mywar.war"
domain="DefaultDomain"
parent-domain="Ignored"
export-all="NON_EMPTY"
import-all="true">
</classloading>
Ciò deriva dal JBoss CW here, mentre ciò che (credo) lavora per JBoss 4.x è descritto here. informazioni più generali su JBoss classload (ING/ERS):
Come meglio posso dire, la documentazione della comunità wiki JBoss sono piuttosto carente per JBoss 5 in confronto a JBoss 4.
@Bears, re: la modifica: solo se lavori nel reparto marketing di Oracle. – Yishai