W środowiskach zarządzanych (czyli np w serwerze aplikacyjnym JBoss AS) to te systemu mogą zarządzać transakcjami, czyli rozpoczynać, kończyć je w odpowiednim momencie, zwalniając z tego obowiązku programistę. W aplikacji można zdefiniować, jak dany fragment kodu ma wpływać na transakcje. Jeżeli sposób zachowanie nie zostanie zdefiniowany przez metodę, to kontener rozpoczyna transakcję zanim rozpocznie się wykonywanie metody, i kończy ją tuż przed końcem jej wykonywania. Nie są dozwolone zagnieżdżone transakcje, każda metoda może zostać skojarzona z jedną transakcją.
Definicja rodzaju transakcji
Rodzaje transakcji można zdefiniować przy użyciu adnotacji TransactionAttribute
oraz TransactionAttributeType
.
Adnotacja TransactionAttribute
może występować zarówno na poziomie deklaracji klasy jak i deklaracji metody. Jeżeli zostanie podana przy deklaracji klasy, oznacza to że dany poziom transakcji ma zostać użyty we wszystkich metodach danej klasy, w przypadku deklaracji na poziomie metody odnosi się tylko do niej. W przypadku gdy występuje w jednym jak i drugim miejscu, pod uwagę brana jest wartość występująca przy deklaracji metody.
Poniżej przykład deklarowania rodzajów transakcji, na poziomie klasy i metod:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 | import javax.ejb.TransactionAttribute; import javax.ejb.TransactionAttributeType; @TransactionAttribute(TransactionAttributeType.REQUIRES_NEW) public class UserManager { @TransactionAttribute(TransactionAttributeType.SUPPORTS) public String getUserName() { return null; } @TransactionAttribute(TransactionAttributeType.REQUIRED) public void setUserName(String name) { } } |
Typy transakcji
Za pomocą adnotacji TransactionAttributeType
można zdefiniować rodzaj transakcji, jaka ma obowiązywać w metodach. Występują następujące typy transakcji:
- MANDATORY
Konieczność wykonania metody w ramach istniejącej już transakcji. Jeżeli dla danego klienta istnieje już działająca transakcji, dana metoda zostanie w jej ramach wykonana. Jeżeli natomiast taka transakcji nie istnieje, to zostanie wyrzucony wyjątekTransactionRequiredException
. Należy użyć tego atrybutu używać wtedy, gdy dana metoda musi zostać wykonana w ramach transakcji klienta. - REQUIRED
Jeżeli klient działa w ramach transakcji i zostanie wywołana metoda oznaczona tym typem, to zostanie ona wykonana w ramach tej transakcji. Jeżeli natomiast klient nie działa w ramach transakcji, to zostanie rozpoczęta nowa, zanim metoda zostanie uruchomiona. Jest to także domyślne zachowanie, jeżeli nie zostanie ustawiony typ transakcji. - REQUIRES_NEW
Jeżeli klient nie działa w ramach transakcji, to po prostu jest rozpoczynana nowa przed uruchomieniem metody. Natomiast jeżeli jest istnieje już działająca transakcja, to podejmowane są następujące kroki:- Zawieszenie aktualnie działającej transakcji.
- Rozpoczęcie nowej transakcji do wykonania wybranej metody.
- Wywołanie i wykonanie metody.
- Po zakończeniu działania metody ponowne uruchomienie wcześniej zawieszonej transakcji.
Typu tego należy używać w sytuacji, gdy istnieje potrzeba wykonywania danej metody zawsze w nowej transakcji.
- SUPPORTS
Jeżeli klient działa w ramach transakcji i wywoła daną metodę, to zostanie ona wykonana w ramach tej transakcji. Jeżeli natomiast transakcja nie istnieje, to nie zostanie ona także rozpoczęta przed wykonaniem wybranej metody. - NOT_SUPPORTED
Jeżeli klient działa w ramach transakcji, to zostanie ona zatrzymana na czas wywołania wybranej metody, a po jej wykonaniu ponownie przywrócona. Jeżeli nie ma takiej transakcji, metoda zostanie po prostu wykonana, bez rozpoczynania nowej.Należy używać tego typu wtedy, gdy wybrana metoda nie potrzebuje transakcji do działania, a zależy nam na większej wydajności jej wykonywania (transakcje mają negatywny wpływ na szybkość wykonywania metod).
- NEVER
Jeżeli klient działa w ramach transakcji i wywoła metodą oznaczoną tym typem, zostanie wyrzucony wyjątekRemoteException
. Natomiast jeżeli transakcja nie istnieje, to metoda zostanie wykonana bez rozpoczynania nowej transakcji.
Mała tabela, która podsumowuje powyższe:
Nazwa atrybutu | Transakcja istnieje | Brak transakcji |
---|---|---|
MANDATORY | używa istniejącej | wyrzuca wyjątek |
REQUIRED | używa istniejącej | rozpoczyna nową |
REQUIRES_NEW | zawiesza istniejącą, rozpoczyna nową | rozpoczyna nową |
SUPPORTS | używa istniejącej | działa bez |
NOT_SUPPORTED | zawiesza istniejącą | działa bez |
NEVER | wyrzuca wyjątek | działa bez |