org.hibernate.AssertionFailure - PullRequest
       16

org.hibernate.AssertionFailure

10 голосов
/ 25 июня 2011

Иногда я получаю эту странную ошибку во время выполнения моего потока. С чем это может быть связано?

2011-Jun-25 09:05:22,339 ERROR AssertionFailure:45 - an assertion failure occured (this             may indicate a bug in Hibernate, but is more likely due to unsafe use of the session)
org.hibernate.AssertionFailure: null id in com.inrev.bm.bean.IRKeyWordTweet entry (don't flush the Session after an exception occurs)
    at         org.hibernate.event.def.DefaultFlushEntityEventListener.checkId(DefaultFlushEntityEventListener.java:78)
at org.hibernate.event.def.DefaultFlushEntityEventListener.getValues(DefaultFlushEntityEventListener.java:187)
at org.hibernate.event.def.DefaultFlushEntityEventListener.onFlushEntity(DefaultFlushEntityEventListener.java:143)
at org.hibernate.event.def.AbstractFlushingEventListener.flushEntities(AbstractFlushingEventListener.java:219)
at org.hibernate.event.def.AbstractFlushingEventListener.flushEverythingToExecutions(AbstractFlushingEventListener.java:99)
at org.hibernate.event.def.DefaultFlushEventListener.onFlush(DefaultFlushEventListener.java:49)
at org.hibernate.impl.SessionImpl.flush(SessionImpl.java:1028)
at org.hibernate.impl.SessionImpl.managedFlush(SessionImpl.java:366)
at org.hibernate.transaction.JDBCTransaction.commit(JDBCTransaction.java:137)
at com.inrev.bm.streaming.IRKeyWordStreaminThread.run(IRKeyWordStreaminThread.java:119)

Мой код для вставки,

    Transaction tx = null;
    Session session = sessionFactory.openSession();
    tx = session.beginTransaction();

    int count = 0;
    try
    {
        for (Iterator itrList = statusToInsert.iterator(); itrList.hasNext();) 
        {
            try 
            {
                IRecord record = (IRecord) itrList.next();
                session.save(record);
                count++;
                if ( count % 10 == 0 ) 
                { 
                    session.flush();
                    session.clear();
                    tx.commit();
                    tx = session.beginTransaction();
                }

            }
            catch (Exception e) 
            {
                tx.commit();
                session.close();
                session = sessionFactory.openSession();
                tx = session.beginTransaction();
                StringWriter sw = new StringWriter(); 
                PrintWriter pw = new PrintWriter(sw); 
                e.printStackTrace(pw); 
                log.error(sw.toString());
            }
        }
    }
    catch (Exception e) {
        StringWriter sw = new StringWriter(); 
        PrintWriter pw = new PrintWriter(sw); 
        e.printStackTrace(pw); 
        log.error(sw.toString());
    }
    finally {
        tx.commit();
        session.close();
    }

С уважением,

Рохит

Ответы [ 3 ]

33 голосов
/ 25 июня 2011

Проблема в том, что ваш код обрабатывает исключение, что является плохим или плохим делом в 99,9% случаев, и происходит следующее:

Одно из взаимодействий с сеансом завершается неудачно в блоке try и выдает исключение. Когда это происходит, сеанс становится недействительным и не может использоваться для абсолютно ничего , поскольку он находится в несогласованном состоянии. Но ваш код взаимодействует с сеансом в блоке catch, который вызывает утверждение.

Единственная безопасная вещь, которую нужно сделать после исключения из сеанса, - откатить транзакцию и закрыть ее. Любой другой тип взаимодействия, вероятно, будет генерировать другое исключение (в данном случае исключение утверждения).

3 голосов
/ 06 ноября 2012

Один случай использования, который не обрабатывается без ошибок - это какой-то опросник. Если приложение устанавливает какое-либо «состояние выполнения» для большого фонового задания, фиксирует, а затем разделяет опрос потока / запроса http / сеанса, в то время как асинхронный фоновый поток генерирует исключение, этот асинхронный поток должен быть ответственным за перехват этого исключения и пометьте статус как «сбой» на том, что опрашивает опросник. В этом случае его неудобный b / c сеанс становится недействительным b / c из-за низкого уровня спящего режима. Похоже, это правильный случай для ловли и обработки исключений.

Является ли единственным способом получения нового сеанса? Чистый / стандартный способ сделать это в управляемой транзакции env, такой как Seam?

0 голосов
/ 10 июня 2016

В дополнение к @Augustoanswer:

В файле UserDAOImpl.java

@Override
public int addUser(User user) {

    // Maintain Hibernate session manually 
    Session openSession = sessionFactory.openSession();

    int retVal = 0;

    try {
        openSession.getTransaction().begin();
        openSession.persist(user);
        openSession.getTransaction().commit();
        retVal = 1;
    } catch (HibernateException e) {
        openSession.getTransaction().rollback();
        retVal = -1;
    } finally {
        openSession.close();
    }
    return retVal;
}
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...