EJB heeft het concept van systeemuitzonderingen en toepassingsuitzonderingen.
Runtime-uitzonderingen, zoals EntityExistsException
zijn systeemuitzonderingen. Deze zorgen er onder andere voor dat elke transactie wordt teruggedraaid en dat de EJB-instance bean wordt weggegooid (vernietigd). Het belangrijkste voor uw probleem is dat ze worden verpakt in een EJBException
.
Er is geen magie om deze uitzonderingen te vangen. Door de code van Petr hierboven aan te passen,
het volgende werkt gewoon:
Steunboon:
@EJB
private DAOBean daoBean;
public void savePerson(Entity e) {
try {
daoBean.save(e);
} catch (EJBException e) {
FacesMessage message = new FacesMessage("entity is already exists.");
FacesContext.getCurrentInstance.addMessage(null, message);
}
}
EJB:
private EntityManager em;
public void save(Entity e) {
em.persist(e);
}
Merk op dat u de oorzaak van de uitzondering kunt achterhalen om te zien of het een EntityExistsException
was of niet (hierboven weggelaten voor de beknoptheid).
Aangezien u in dit geval waarschijnlijk uw EJB-instantie niet hoeft te vernietigen, is het een beter patroon om uw eigen uitzondering te definiëren die overerft van een RuntimeException
en is geannoteerd met de @ApplicationException
met de rollback
attribuut ingesteld op true.
Bijv.
@ApplicationException(rollback = true)
public class MyException extends RuntimeException {
public MyException(Throwable cause) {
super(cause);
}
}
Wikkel uw EntityExistsException
in je EJB in deze uitzondering en gooi en vang het.
Ik raad je ten zeerste aan NIET om als resultaat foutcodes of booleaans succes/mislukking te gebruiken. Dit is een bekend anti-patroon en maakt je code ongelooflijk foutgevoelig.