StaleObjectStateException ОШИБКА

Кто-нибудь может указать мне на ошибку, пожалуйста?

Примечание: это упрощенный тестовый пример, извлеченный из моего реального приложения. Таким образом, странное использование трех менеджеров сущностей и em1.getTransaction (). begin (); em1.clear (); em1.close (); в конце каждого раздела. В реальном приложении это бывает в разное время. HibernateUtil в основном скопирован из учебника.

        HibernateUtil.open();

        EntityManager em1 = HibernateUtil.reserveEntityManager();
        em1.getTransaction().begin();
        StringType st1 = new StringType();
        st1.setName("a");
        em1.persist(st1);
        em1.getTransaction().commit();
        em1.getTransaction().begin();
        em1.clear();
        em1.close();

        EntityManager em2 = HibernateUtil.reserveEntityManager();
        em2.getTransaction().begin();
        StringType st2 = new StringType();
        st2.setName("a");
        st2.setId(st1.getId());
        em2.merge(st2);
        em2.getTransaction().commit();
        em2.getTransaction().begin();
        em2.clear();
        em2.close();

        EntityManager em3 = HibernateUtil.reserveEntityManager();
        em3.getTransaction().begin();
        StringType st3 = new StringType();
        st3.setName("a");
        st3.setId(st1.getId());
        [b]em3.merge(st3);[/b]
        em3.getTransaction().commit();
        em3.getTransaction().begin();
        em3.clear();
        em3.close();



public static EntityManager reserveEntityManager()
    {
        return emf.createEntityManager();
    }

public static void open()
    {
        try
        {           
            emf = Persistence.createEntityManagerFactory("manager1");
        }
        catch (Throwable e)
        {
            throw new ExceptionInInitializerError(e);
        }
    }

javax.persistence.OptimisticLockException: org.hibernate.StaleObjectStateException: строка была обновлена ​​или удалена другой транзакцией (или сопоставление несохраненных значений было неправильным): [WebOrganizer.classes.types.StringType # 174] в org.hibernate.ejb.AbstractEntityManagerImpl.wrapStaleStateException (AbstractEntityManagerImpl.java:646) в org.hibernate.ejb.AbstractEntityManagerImpl.throwPersistenceException (AbstractEntityManagerImpl.java:600) в org.hibernate.ejb.AbstractEntityManagerImpl.merge (AbstractEntityManagerImpl.java:237) в WebOrganizer.web.servlets.TypeServlet.test2 (TypeServlet.java:356) в sun.reflect.NativeMethodAccessorImpl.invoke0 (собственный метод) в sun.reflect.NativeMethodAccessorImpl.invoke (NativeMethodAccessorImpl.java:39) в sun.reflect.DelegatingMethodAccessorImpl.invoke (DelegatingMethodAccessorImpl.java:25) в java.lang.reflect.Method.invoke (Method.java:597) в org.testng.internal.MethodHelper.invokeMethod (MethodHelper.java:580) в org.testng.internal.Invoker.invokeMethod (Invoker.java:517) в org.testng.internal.Invoker.invokeTestMethod (Invoker.java:669) в org.testng.internal.Invoker.invokeTestMethods (Invoker.java:956) в org.testng.internal.TestMethodWorker.invokeTestMethods (TestMethodWorker.java:126) в org.testng.internal.TestMethodWorker.run (TestMethodWorker.java:110) в org.testng.TestRunner.runWorkers (TestRunner.java:720) в org.testng.TestRunner.privateRun (TestRunner.java:590) в org.testng.TestRunner.run (TestRunner.java:484) в org.testng.SuiteRunner.runTest (SuiteRunner.java:332) в org.testng.SuiteRunner.runSequential (SuiteRunner.java:327) в org.testng.SuiteRunner.privateRun (SuiteRunner.java:299) в org.testng.SuiteRunner.run (SuiteRunner.java:204) в org.testng.TestNG.createAndRunSuiteRunners (TestNG.java:864) в org.testng.TestNG.runSuitesLocally (TestNG.java:830) в org.testng.TestNG.run (TestNG.java:748) в org.testng.remote.RemoteTestNG.run (RemoteTestNG.java:73) в org.testng.remote.RemoteTestNG.main (RemoteTestNG.java:124) в sun.reflect.NativeMethodAccessorImpl.invoke0 (собственный метод) в sun.reflect.NativeMethodAccessorImpl.invoke (NativeMethodAccessorImpl.java:39) в sun.reflect.DelegatingMethodAccessorImpl.invoke (DelegatingMethodAccessorImpl.java:25) в java.lang.reflect.Method.invoke (Method.java:597) в com.intellij.rt.execution.application.AppMain.main (AppMain.java:90)

Вызвано: org.hibernate.StaleObjectStateException: строка была обновлена ​​или удалена другой транзакцией (или сопоставление несохраненных значений было неправильным): [WebOrganizer.classes.types.StringType # 174] в org.hibernate.event.def.DefaultMergeEventListener.entityIsDetached (DefaultMergeEventListener.java:261) в org.hibernate.event.def.DefaultMergeEventListener.onMerge (DefaultMergeEventListener.java:120) в org.hibernate.event.def.DefaultMergeEventListener.onMerge (DefaultMergeEventListener.java:53) в org.hibernate.impl.SessionImpl.fireMerge (SessionImpl.java:677) в org.hibernate.impl.SessionImpl.merge (SessionImpl.java:661) в org.hibernate.impl.SessionImpl.merge (SessionImpl.java:665) в org.hibernate.ejb.AbstractEntityManagerImpl.merge (AbstractEntityManagerImpl.java:228) ... еще 28

Пользовательский скаляр GraphQL
Пользовательский скаляр GraphQL
Листовые узлы системы типов GraphQL называются скалярами. Достигнув скалярного типа, невозможно спуститься дальше по иерархии типов. Скалярный тип...
Как вычислять биты и понимать побитовые операторы в Java - объяснение с примерами
Как вычислять биты и понимать побитовые операторы в Java - объяснение с примерами
В компьютерном программировании биты играют важнейшую роль в представлении и манипулировании данными на двоичном уровне. Побитовые операции...
Поднятие тревоги для долго выполняющихся методов в Spring Boot
Поднятие тревоги для долго выполняющихся методов в Spring Boot
Приходилось ли вам сталкиваться с требованиями, в которых вас могли попросить поднять тревогу или выдать ошибку, когда метод Java занимает больше...
Полный курс Java для разработчиков веб-сайтов и приложений
Полный курс Java для разработчиков веб-сайтов и приложений
Получите сертификат Java Web и Application Developer, используя наш курс.
3
0
6 269
2

Ответы 2

Я бы попробовал что-то вроде этого:

EntityTransaction tx1 = em1.getTransaction();
// make your modifications
em1.merge(st1);
tx1.commit();

Не уверен, почему вы начинаете транзакцию прямо перед очисткой EntityManager. Я не работаю с транзакциями JPA программно, так что это просто обоснованное предположение. Кроме того, почему вы каждый раз создаете новый EntityManager, если он возвращает один и тот же экземпляр?

Почему вы сохраняете среднее состояние объектов? Если необходимо, попробуйте другой подход. Передайте идентификатор, убедившись, что вы начали транзакцию прямо перед get и сразу после flush.

Помните, что лучше очистить сеанс, чем вызывать фиксацию. Поскольку flush фактически выполняет запись в базу данных, вам не нужно вызывать close.

Другие вопросы по теме