Reputation: 1497
I annotated a method with the REQUIRE_NEW and I expected it to be executed in a new transaction. Following is the code:
public class EJBAImpl implements EJBA {
@EJB
private EJBB ejbb;
public void someMethod(entity){
ejbb.create(entity);
//doMoreStuff
}
}
public class BaseEJB {
public void create(Entity entity) {
//saveHere
}
}
public class EJBBImpl extends BaseEJB implements EJBB {
@Override
@TransactionAttribute(TransactionAttributeType.REQUIRES_NEW)
public void create(Entity entity) {
super.create(entity);
}
}
Howerver, when I put a breakpoint in the line after the create method invocation (where says doMoreStuff) my entity is not saved in the DB. What am I missing? I checked and EJBB is a proxy.
Edit: Figured out, if the method is inherited, it doesn't work. The solution was to change the method in EJBB, as follow:
public class EJBBImpl extends BaseEJB implements EJBB {
@TransactionAttribute(TransactionAttributeType.REQUIRES_NEW)
public void anotherNameForCreate(Entity entity) {
super.create(entity);
}
}
Does anyone know why it doesn't work when override the method from another class?
Upvotes: 3
Views: 7491
Reputation:
Points to be consider for RequiresNew annotation
The Container must invoke an enterprise Bean method whose transaction attribute is set to RequiresNew with a NEW transaction context.
If the client invokes the enterprise Bean's method while the client is NOT associated with a transaction context, the container AUTOMATICALLY STARTS a new transaction before delegating a method call to the enterprise Bean business method. The Container automatically enlists all the resource managers accessed by the business method with the transaction.
If the business method invokes other enterprise beans, the Container passes the transaction context with the invocation. The Container attempts to commit the transaction when the business method has completed. The container performs the commit protocol before the method result is sent to the client.
If a client calls with a transaction context, the container SUSPENDS the association of the transaction context with the current thread before starting the new transaction and invoking the business method. The container resumes the suspended transaction association after the business method and the new transaction have been completed.
Solution
The new transaction will be created only when calling method by EJB reference from another bean. Invoking create within the same bean won't spawn the new transaction.so you have to call it from another bean.
Upvotes: 0
Reputation: 2981
The @TransactionAttribute has special rules as ejb3.1 specification describes in section 13.3.7.1.
If the bean class has superclasses, the following additional rules apply.
1) A transaction attribute specified on a superclass S applies to the business methods defined by S. If a class-level transaction attribute is not specified on S, it is equivalent to specification of TransactionAttribute(REQUIRED) on S.
2) A transaction attribute may be specified on a business method M defined by class S to override for method M the transaction attribute value explicitly or implicitly specified on the class S.
3) If a method M of class S overrides a business method defined by a superclass of S the transaction attribute of M is determined by the above rules as applied to class S.
According to my understandig you are in the third point, therefore, for the ejb container the actual transaction attribute is @REQUIERED insted of REQUIRES_NEW.
Upvotes: 4