JTA не откатывается при удалении каскада

Использование: Glassfish 3.1.2, EclipseLink.

У меня есть следующая модель JPA трех классов:

@Entity public class Customer implements Serializable {

@Id private Integer id;

@OneToOne(cascade={CascadeType.PERSIST, CascadeType.MERGE, CascadeType.REMOVE}, orphanRemoval=true)
private Person person;

[...]

@Entity public class Person implements Serializable {

@Id private Integer id;

[...]

@Entity public class Request implements Serializable {

@Id private Integer id;

@ManyToOne private Person person;

Я пытаюсь удалить клиента со следующей стратегией (используя CMT ):



    org.eclipse.persistence.jpa.PersistenceProvider
    false
    
        
        

        
        
                          
        
        
        
    

[...]

@PersistenceContext(unitName="MyPU")
private EntityManager entityManager;   

@Resource private SessionContext context;

[...]

public void delete(Entity object) {

    try{

        object = this.getEntityManager().merge(object);
        this.getEntityManager().remove(object);

    } catch (Exception e){

        this.context.setRollbackOnly();
    }
}

Когда объект Клиент прикреплен к объекту Person , прикрепленному к запросу , каскад удаления Лицо не позволяет откатить транзакцию, но Клиент удален из базы данных. Я получаю следующую ошибку:

INFO: [EL Fine]: 2012-12-28 10:53:38.1--Connection(27132168)--DELETE FROM CUSTOMER WHERE (ID = ?)
bind => [97]
INFO: [EL Fine]: 2012-12-28 10:53:38.125--Connection(27132168)--DELETE FROM PERSON WHERE (ID = ?)
bind => [111]
INFO: [EL Fine]: 2012-12-28 10:53:38.126--SELECT 1
WARNING: DTX5014: Caught exception in beforeCompletion() callback:
Local Exception Stack:
INFO: [EL Warning]: 2012-12-28 10:53:38.127--Exception [EclipseLink-4002] (Eclipse Persistence Services - 2.3.2.v20111125-r10461): org.eclipse.persistence.exceptions.DatabaseException
Internal Exception: org.postgresql.util.PSQLException: ERRO: atualização ou exclusão em tabela "person" viola restrição de chave estrangeira "fk_request_person_id" em "request"
Detalhe: Chave (id)=(111) ainda é referenciada pela tabela "request".
Error Code: 0
Call: DELETE FROM PERSON WHERE (ID = ?)
bind => [111]
Query: DeleteObjectQuery(111)
[...]
SEVERE: javax.ejb.EJBException: Transaction aborted
[...]

Итак, как я могу отменить удаление клиента при неудачном отказе каскада?

1
nl ja de
Может быть, ваше соединение с БД установлено на autocommit? Если нет, пожалуйста, покажите нам свои границы транзакций.
добавлено автор sorencito, источник
С границей я подразумеваю начало и конец транзакции - в любом случае, если она работает с Oracle, проблема заключается в DB (соединение). Отправьте настройки для подключения.
добавлено автор sorencito, источник
Перемещал мои комментарии в реальный ответ, поскольку это становилось длинным.
добавлено автор sorencito, источник
Чтобы проверить, что может быть неправильно с вашим соединением Postgres DB, я хотел бы получить более подробную информацию: какой сервер приложений вы используете, как вы настроили источник данных, задали ли вы какие-либо конкретные свойства и т. Д.
добавлено автор sorencito, источник
Это может быть проблемой. Я протестировал приложение, используя соединение Oracle 10g , и откат работает (мне нужно, чтобы приложение работало с этими двумя БД - Oracle 10g и Postgres 8.4). Транзакция находится в состоянии без состояния, boudary - по умолчанию для JTA (НЕОБХОДИМ). Невозможно отключить Postgres 8.4 (который я использую) autocommit в соответствии с этой ссылкой : stackoverflow.com/questions/13837146/… . Может быть, мне придется использовать транзакцию, управляемую бобами?
добавлено автор user1934440, источник
Да, я использую аннотации. Я использую пул соединений JTA с атрибутами по умолчанию. Не могли бы вы уточнить настройки соединения?
добавлено автор user1934440, источник

1 ответы

Здесь возможны две ошибки.

  • Неправильно указаны границы транзакций.

Возможно, из-за этого ваш сервер приложений не выдаёт инструкцию BEGIN правильно. Это объясняет, что Postgres имеет проблемы, в то время как Oracle не делает (он неявно запускает транзакцию). Убедитесь, что ваши методы обслуживания носят правильные аннотации. Если все в порядке, возможно

  • Проблема с вашим источником данных.

Является ли это JTA-совместимым источником данных? Использует ли он правильный драйвер для Postgres? Пожалуйста, разместите свой конфиг, чтобы мы могли проверить.

Я нашел интересную ссылку, которая может вам помочь. Речь идет о том, что Postgres остается в режиме автосохранения (хотя при использовании Spring):

http://archives.postgresql.org/pgsql-jdbc/2007-07 /msg00115.php

0
добавлено
Хорошо, я адаптирую ответ, чтобы он стал более читателем, чем это было. Не могли бы вы сказать, какой класс вы используете? Простой наш PoolableDatasource?
добавлено автор sorencito, источник
Используя defaultAutocommit = false (как описано в ссылке, которую вы публикуете) в моих свойствах пула соединений JDBC на Glassfish решили проблему. Я с PostgreSQL 8.4.15 и postgresql-8.4-703.jdbc4.jar.
добавлено автор user1934440, источник
Я использую простой класс.
добавлено автор user1934440, источник