Forskellen mellem CDI og EJB Singleton

1. Oversigt

I denne vejledning ser vi nærmere på to typer singletoner, der er tilgængelige i Jakarta EE. Vi forklarer og demonstrerer forskellene og ser de anvendelser, der passer til hver enkelt.

Lad os først se, hvad singletoner handler om, inden vi går ind i detaljerne.

2. Singleton designmønster

Husk at en almindelig måde at implementere Singleton-mønster på er med en statisk forekomst og en privat konstruktør:

offentlig finaleklasse Singleton {privat statisk endelig Singleton-instans = ny Singleton (); privat Singleton () {} offentlig statisk Singleton getInstance () {return instans; }} 

Men desværre er dette ikke rigtig objektorienteret. Og det har nogle multi-threading problemer.

CDI- og EJB-containere giver os dog et objektorienteret alternativ.

3. CDI Singleton

Med CDI (Contexts and Dependency Injection) kan vi nemt oprette singletoner ved hjælp af @Singleton kommentar. Denne kommentar er en del af javax.inject pakke. Det instruerer containeren i at Instant singleton en gang og videregiver sin henvisning til andre genstande under injektionen.

Som vi kan se, er implementering af singleton med CDI meget enkel:

@Singleton offentlig klasse CarServiceSingleton {// ...} 

Vores klasse simulerer en bilservicebutik. Vi har mange forekomster af forskellige Bils, men de bruger alle den samme butik til service. Derfor passer Singleton godt.

Vi kan kontrollere, at det er den samme forekomst med en simpel JUnit-test, der spørger konteksten for klassen to gange. Bemærk, at vi har en getBean hjælpermetode her for læsbarhed:

@Test offentlig ugyldighed givetASingleton_whenGetBeanIsCalledTwice_thenTheSameInstanceIsReturned () {CarServiceSingleton one = getBean (CarServiceSingleton.class); CarServiceSingleton to = getBean (CarServiceSingleton.class); assertTrue (en == to); } 

På grund af @Singleton kommentar, containeren returnerer den samme reference begge gange. Hvis vi prøver dette med en almindelig administreret bønne, vil containeren dog give en anden forekomst hver gang.

Og mens dette fungerer det samme for begge javax.inject.Singleton eller javax.ejb.Singleton, der er en nøgleforskel mellem disse to.

4. EJB Singleton

For at oprette en EJB-singleton bruger vi @Singleton kommentar fra javax.ejb pakke. På denne måde skaber vi en Singleton Session Bean.

Vi kan teste denne implementering på samme måde, som vi testede CDI-implementeringen i det foregående eksempel, og resultatet bliver det samme. EJB-singletoner giver som forventet klassen en enkelt forekomst.

Imidlertid, EJB Singletons leverer også yderligere funktionalitet i form af containerstyret samtidighedskontrol.

Når vi bruger denne type implementering, sikrer EJB-containeren, at der er adgang til enhver offentlig metode i klassen med en enkelt tråd ad gangen. Hvis flere tråde forsøger at få adgang til den samme metode, kan kun en tråd bruge den, mens andre venter på deres tur.

Vi kan bekræfte denne adfærd med en simpel test. Vi introducerer en servicekø-simulering til vores singleton-klasser:

privat statisk int serviceQueue; public int service (Car car) {serviceQueue ++; Tråd. Søvn (100); car.setServiced (true); serviceQueue--; retur serviceQueue; } 

serviceQueue implementeres som et almindeligt statisk heltal, der øges, når en bil “kommer ind” i tjenesten og falder, når den “forlader”. Hvis beholderen sørger for korrekt låsning, skal denne variabel være lig med nul før og efter servicen og lig med en under servicen.

Vi kan kontrollere denne adfærd med en simpel test:

@Test offentligt ugyldigt nårEjb_thenLockingIsProvided () {for (int i = 0; i <10; i ++) {new Thread (new Runnable () {@Override public void run () {int serviceQueue = carServiceEjbSingleton.service (new Car ("Speedster) xyz ")); assertEquals (0, serviceQueue);}}). start (); } Vend tilbage; } 

Denne test starter 10 parallelle tråde. Hver tråd styrer en bil og prøver at servicere den. Efter tjenesten hævder den, at værdien af serviceQueue er tilbage til nul.

Hvis vi f.eks. Udfører en lignende test på CDI-singleton, vil vores test mislykkes.

5. Konklusion

I denne artikel gennemgik vi to typer singleton-implementeringer, der er tilgængelige i Jakarta EE. Vi så deres fordele og ulemper, og vi demonstrerede også, hvordan og hvornår de skulle bruges.

Og som altid er den komplette kildekode tilgængelig på GitHub.


$config[zx-auto] not found$config[zx-overlay] not found