поймать исключение БД в приложении JSF + EJB - PullRequest
3 голосов
/ 20 марта 2012

Я использую Glassfish 3.1 с JSF2 и EJB без сохранения состояния для запроса и записи базы данных Oracle. Таблица, которую пользователь хочет заполнить в этом веб-приложении, имеет первичный ключ. Когда пользователь пытается добавить новую запись, вызывается метод ejb, вызывающий em.persist. Теперь, если пользователь пытается добавить запись с уже использованным значением первичного ключа, я получил исключение в EJB. Я хотел бы выдать пользователю сообщение о том, что произошла ошибка в базе данных, но я не могу понять, как управляемый компонент JSF может перехватить исключение EJB. Есть ли способ?

Ответы [ 2 ]

7 голосов
/ 20 марта 2012

EJB имеет концепцию системных исключений и исключений приложений.

Исключения во время выполнения, такие как EntityExistsException, являются системными исключениями. Это, среди прочего, приведет к откату любой транзакции и к тому, что экземпляр компонента EJB будет отброшен (уничтожен). Самое главное для вашей проблемы, они будут обернуты в EJBException.

Нет волшебства вокруг ловли этих исключений. Корректирующий код от Петра выше,
следующее будет просто работать:

Фасоль:

@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);    
}

Обратите внимание, что вы можете найти причину исключения, чтобы узнать, был ли EntityExistsException или нет (для краткости опущено выше).

Поскольку в этом случае вам, вероятно, не нужно уничтожать свой экземпляр EJB, лучшим вариантом будет определение собственного исключения, которое наследуется от RuntimeException и аннотируется @ApplicationException с атрибутом rollback, установленным в правда.

1024 * Е.Г. *

@ApplicationException(rollback = true)
public class MyException extends RuntimeException {

    public MyException(Throwable cause) {
        super(cause);
    }
}

Оберните ваш EntityExistsException в EJB в это исключение и бросьте и поймайте его.

Я настоятельно советую вам НЕ использовать коды ошибок или логический успех / сбой в результате. Это хорошо известный анти-шаблон, который делает ваш код невероятно подверженным ошибкам.

2 голосов
/ 20 марта 2012

Вы можете создать собственный класс исключений. Допустим, UserException с перечислением значений возможных исключений.

В вашем EJB вы можете определить свои методы как throwable. Если вам нужно выбросить исключение.

В вашем JSF-SiteBean вам нужно всего лишь использовать простой try / catch.

Исключение из типа UserException ... получить причину перечисления ... и т. Д.

...