Kiritishdan oldin AJ ga AJB ni tanlang

@Local interfeysining ikkita ilovasi borligini tasavvur qiling

@Local
public interface LocalInterface {
}

@Stateless
public class MyFirstImplementation implements LocalInterface {
}

@Stateless
public class MySecondImplementation implements LocalInterface {
}

Men loyihani (ya'ni ish vaqti yoki tashqi konfiguratsiya xususiyatidan foydalangan holda) foydalanmoqchi bo'lgan (MyFirstImplementation yoki MySecondImplementation) loyihani recompiling holda tanlashni xohlayman.

public class MyClass {
   @EJB
   LocalInterface local;
}

Agar bitta tanlov amalga oshirilsa, u o'zgarmaydi. Agar yordam berilsa, JBoss 5.1dan foydalanaman.

3

3 javoblar

Yana bir yondashuv, JNDI bilan EJB mos yozuvlar topish uchun, avtomatik ravishda inyeksiyaga tayanish o'rniga boshqa har qanday yordam berishi mumkin:

public class MyClass {
   LocalInterface local;

   @PostConstruct
   public void init() {
       local = findImplementation();
   }

   private LocalInterface findImplementation() {
       try {
            InitialContext context = new InitialContext();
            String ejbPath =//read from an external property
            return (LocalInterface) context.lookup(ejbPath);
       } catch ... { ... }
   }
}

This is what I finally did, because with JBoss 5 (< Java EE 6, EJB 3.0) you can not make use of the useful @Produces annotation. I set PedroKowalski's answer as accepted as CDI annotations seems to be the better solution if you do not have other restrictions.

2
qo'shib qo'ydi
Afsuski, MyClass mavjud bo'lgan WARning web.xml kodlari hali ham JNDI daraxtidagi fasolni izlang. pastki elementi java: comp/env ostida EJBni qaerda topishini bildiradi. web.xml kodini o'zgartirish, albatta, qurilish vaqtidagi o'zgarishdir.
qo'shib qo'ydi muallif lotz, manba

Siz buni tarqatuvchi identifikatori yordamida olishingiz mumkin - ejb-jar.xml . Bunga o'xshash narsa (100% aniq bo'lmasligi mumkin, ammo sizda nuqta bor deb o'ylayman):

 
   
      
         MyClass
         
            ejb/myLocalReferencedBean
            Session
            com.yourpackage.LocalInterface
            MyFirstImplementation
            local
         
      

      
         MyFirstImplementation
         <!-- ... -->
      
      
         MySecondImplementation
         <!-- ... -->
      
   

Another way is to use the CDI as described here: Inject @EJB bean based on conditions

2
qo'shib qo'ydi
Rahmat. "MyClass" EJB emas, ejb-jar yechimi ishlashi ko'rinmaydi, chunki DTD-ga ko'ra, uy/masofaviy interfeyslarni ko'rsatish kerak. CDI yondashuvi, agar men noto'g'ri bo'lmasam, faqat JEE 6 uchun amal qiladi.
qo'shib qo'ydi muallif Guido García, manba
@ GuidoGarcía Siz haqsiz - MyClass EJB sinf bo'lishi kerak. CDI yechimi yanada moslashuvchan, chunki siz konfiguratsiyani boshqa joyga, ya'ni ma'lumotlar bazasiga joylashtirasiz. Bundan tashqari, u @Inject foydalanadigan joyda ishlaydi. Faqat kichik bir eslatma: bu xml sxemasi va DTD emas. Uy/masofaviy interfeyslar talab qilinmaydi - siz foydalanadigan EJB versiyasiga bog'liq.
qo'shib qo'ydi muallif Piotr Nowicki, manba

PedroKovalki tomonidan qayd etilgan usul, buning odatiy usulidir. "Tashqi konfiguratsiya moslamasi" ga nisbatan yana bir hiyla-naytni ishlab chiquvchini EJB-larni ushlab turadigan jarima ichida faqat bitta dastur tugaydi deb konfiguratsiya qiladi.

Shunday qilib, siz saboqlarni qayta kompilyatsiya qilishingiz yoki biron-bir manba kodini o'zgartirishingiz shart emas, ammo sizning kassangizni boshqa dasturni tanlash uchun qayta qurishingiz kerak.

1
qo'shib qo'ydi
Arjanga rahmat. Bu hozirgi yondashuvdan foydalanishdir, lekin u endi haqiqiy emas, chunki jar restorani ishlab chiqarish muhitida variant emas.
qo'shib qo'ydi muallif Guido García, manba