2015-09-22 4 views
0

Я всегда думал, что сущности, полученные до транзакции (до entityManager.getTransaction().begin()), были отделены от контекста персистентности (при использовании того же менеджера сущностей для извлечения сущностей для обработки транзакции). Фактически, каждый раз, когда я управлял транзакциями, мне приходилось явно объединять объекты, которые были выведены за его пределы. Если бы я этого не сделал, обновления не отражались в базе данных.Являются ли сущности, получаемые за пределами транзакции, управляемой или отстраненной?

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

Единственная разница между нашими кодами в том, что мой persistence.xml файл имеет версию 2.0, а его версия 1.0. Но он использует JPA 2.1 в своем коде. Это причина этого странного поведения или есть что-то, чего я здесь не хватает?

Мы используем Hibernate как реализацию.

+1

Они будут управляться. – Antoniossss

+0

какая реализация вы используете? –

ответ

0

Им будет управлять. Любые изменения будут отражены в БД в следующих flush. Сделки транзакций сразу же сбрасываются вместе с изменениями, внесенными в префектурные транзакции.

+0

Дело в том, что для меня все так не пошло. Действия перед транзакцией не были сброшены в базу данных. Я должен был явно объединить объекты, полученные до начала транзакции, если бы я хотел, чтобы они управлялись! –

+0

Чем они должны были быть отстранены в какой-то момент. С транзакцией или нет.Возможно, вы загружаете их в разных контекстах стойкости (разные EntityManager), или, может быть, EntityManager закрыт в другом месте между вашим чтением и записью. Другого пути нет. Если вы получаете объекты, они управляются до тех пор, пока вы их не отделите, или EM не будет закрыт, и все chenges будут отражены в DB – Antoniossss

1

Если и как вещи автоматически объединяются в транзакционный контекст, зависит от нескольких факторов. Используемая реализация JPA, контекст контекста персистентности, а также изолированная транзакция. Не видя всей среды, на это нелегко ответить. Я хотел бы принять ваше приложение позволяет читать не транзакционные (грязное чтение, чтение фантом, чтение без повторения), и поэтому вам «разрешено» решать, с чем вы хотите объединиться. Другим объяснением может быть некоторый пример с кодом приложения, который смешивает несколько контекстов персистентности и, следовательно, требует от вас объединить ваши объекты, прочитанные в одном контексте персистентности, в другой контекст persitence (тот, с которого вы начали свой TX).

+0

. Я отредактировал свое сообщение, чтобы уточнить, какую реализацию JPA я использую: Hibernate. Как указано в другом комментарии, я не использую аннотацию @PersistenceContext, и поэтому по умолчанию я должен быть в области транзакций, но я мог ошибаться. Я использую только один менеджер объектов, поэтому у меня должен быть только один контекст постоянства (если я хорошо понял, как он работает). –

2

PersistenceContext может иметь две области:

  • TRANSACTIONAL-ОБЛАСТЬ ПРИМЕНЕНИЯ
  • РАСШИРЕННОЕ-ОБЛАСТЬ ПРИМЕНЕНИЯ

TRANSACTIONAL-ОБЛАСТЬ ПРИМЕНЕНИЯ

происходит только, когда это EntityManager container- удалось. В этом случае текущий PersistenceContext активен, пока существует текущая транзакция.

EXTENDED-СФЕРА

Происходит, когда EntityManager является применением управляемого (быть по умолчанию) или управляемый контейнером (EntityManager необходимо аннотация: @PersistenceContext(type=PersistenceContextType.EXTENDED)).

Короче говоря: EXTENDED-SCOPE означает, что текущий PersistenceContext живет до тех пор, пока ваш организм живет.

+0

Поскольку я не использовал аннотацию @PersistenceContext, я должен быть в области транзакций, что объясняет, почему мои обработанные транзакцией транзакции не управляются. Хотя, я не думаю, что мой коллега тоже использует эту аннотацию, но пока я не могу быть уверен. Я пойму, когда он приедет. –

+1

Расширение области действия от транзакционного до расширенного рассматривается не по самой аннотации «PersistenceContext», а по формуле «type = PersistenceContextType.EXTENDED». Если вы не используете аннотацию PersistenceContext, это означает, что ваш EntityManager управляется приложением, что приводит к увеличению объема. Помните, что каждый раз, когда вы вызываете «emf.createEntityManager», вы создаете новый PersistenceContext - возможно, вот в чем проблема. – Szarpul

Смежные вопросы