it-swarm-vi.com

JPA 2.0: Tự động và các ứng dụng khác nhau

Tôi có một ứng dụng Java SE dựa trên CDI được xây dựng bằng maven, có mô-đun core và các mô-đun khác.
Core có persistence.xml và một số thực thể . Các mô-đun có các thực thể bổ sung.

Làm cách nào tôi có thể thêm các thực thể vào tiêu điểm của đơn vị kiên trì?

Tôi đã đọc hướng dẫn sử dụng Hibernate, http://docs.jboss.org/hibernate/urdy/entitymanager/reference/en/html/configuration.html#setup-configuration-packaging

Tôi cũng đã thấy những câu hỏi SO

Tôi đang tìm kiếm một giải pháp trong đó Hibernate sẽ quét tất cả các lớp đã tải hoặc sẽ chọn một số tệp cấu hình từ các tệp khác (ví dụ: CDI thực hiện với beans.xml). 

Ứng dụng của tôi không sử dụng Spring . Tôi không nhấn mạnh vào tính di động - Tôi sẽ gắn bó với Hibernate.

  • Có một số giải pháp như vậy?
  • Có cách nào để tạo PU từ persistence.xml và thêm các lớp vào đó theo chương trình không?
  • Tôi có thể thêm các lớp @Entity vào EntityManagerFactory sau khi nó được tạo không?

Cập nhật : Tôi đã tìm thấy trong org.​hibernate.​ejb.​Ejb3Configuration

public Ejb3Configuration configure(String persistenceUnitName, Map integration)  

http://docs.jboss.org/hibernate/entitymanager/3.6/javadocs/

37
Ondra Žižka

Có một số cách để giải quyết nó:

  1. Như được mô tả trong Tôi có cần các phần tử <class> trong tệp Persence.xml không? , bạn có thể đặt thuộc tính hibernate.archive.autodetection và Hibernate sẽ có thể tra cứu tất cả các lớp chú thích từ đường dẫn lớp. Tuy nhiên, đó không phải là thông số kỹ thuật JPA.

  2. Nếu bạn đang sử dụng Spring, từ Spring 3.1.2 (hoặc thậm chí sớm hơn một chút), trong LocalContainerEntityManagerFactoryBean, bạn có thể định nghĩa packageToScan sẽ yêu cầu LocalContainerEntityManagerFactoryBean quét trong đường dẫn lớp để tìm tất cả các lớp chú thích. Một lần nữa, không tuân thủ thông số kỹ thuật JPA. 

  3. Tôi đã sử dụng Maven làm công cụ xây dựng. Nhiều năm trước, tôi đã viết một plugin nhỏ sẽ tạo tệp bền vững trong quá trình xây dựng. Plugin sẽ quét từ build classpath để tìm ra tất cả các lớp có chú thích và liệt kê chúng trong tệp Persence.xml được tạo. Điều này là tẻ nhạt nhất nhưng kết quả là tuân thủ thông số kỹ thuật JPA. Một nhược điểm (không áp dụng cho hầu hết những người tôi tin) là việc tra cứu xảy ra trong thời gian xây dựng, không phải thời gian chạy. Điều đó có nghĩa là nếu bạn đang có một ứng dụng mà JAR thực thể chỉ được cung cấp khi triển khai/thời gian chạy nhưng không xây dựng thời gian, phương pháp này sẽ không hiệu quả.

11
Adrian Shum

Ejb3Configuration đã bị xóa trong 4.3.0. Nếu bạn không muốn tạo Trình tích hợp của Hibernate, bạn có thể sử dụng thuộc tính hibernate.ejb.loaded.classes.

properties.put(org.hibernate.jpa.AvailableSettings.LOADED_CLASSES, entities);
Persistence.createEntityManagerFactory("persistence-unit", properties);

Trong đó entities là một List<Class> của các lớp thực thể.

7
Ignacio Baca

Tôi có một thiết lập hơi khác khi tôi đặt tệp Persence.xml trong tệp WAR nhưng một số phụ thuộc của nó bao gồm chú thích @Entity được phân loại để đưa vào đơn vị lưu trữ. 

Tôi đã giải quyết vấn đề của mình bằng cách sử dụng Maven một chút giống như Adrian Shum được mô tả trong # 3, nhưng sử dụng phần tử để bao gồm các lọ được quét cho các chú thích @Entity. 

Tôi đã thêm một thuộc tính vào my-web/pom.xml cho mỗi phụ thuộc bao gồm các thực thể bổ sung. Tất cả các lọ của tôi là một phần của bản dựng đa hướng Maven vì vậy đối với tôi nó trông như thế. 

<properties>
    <common.jar>common-${project.version}.jar</common.jar>
    <foo.jar>foo-${project.version}.jar</foo.jar>
</properties>

Sau đó, tôi thêm phần sau vào tệp Persence.xml

<?xml version="1.0" encoding="UTF-8"?>
<persistence version="2.0" ... >
    <persistence-unit name="primary">
        <jta-data-source>Java:jboss/datasources/mysource</jta-data-source>

        <jar-file>lib/${common.jar}</jar-file>
        <jar-file>lib/${foo.jar}</jar-file>

        ...
    </persistence-unit>
</persistence>

Cuối cùng, tôi định cấu hình maven-resource-plugin trong web/pom.xml để thay thế các biểu thức $ trong tệp Persence.xml bằng các thuộc tính được đặt trong POM

<build>
  <resources>
    <resource>
      <directory>src/main/resources</directory>
      <filtering>true</filtering>
      <includes>
        <include>**/persistence.xml</include>
      </includes>
    </resource>
    <resource>
      <directory>src/main/resources</directory>
      <filtering>false</filtering>
      <excludes>
        <exclude>**/persistence.xml</exclude>
      </excludes>
    </resource>
  </resources>
  ...
</build>
5
Jesper Tejlgaard

Tôi đã trải qua vấn đề tương tự và thật không may, không có giải pháp dễ dàng nào, về cơ bản có vẻ như JPA không được thiết kế để sử dụng theo cách này. Một trong những giải pháp là chỉ cần one Persence.xml cho mỗi dự án (ứng dụng) cấp cao nhất. Nó tương tự như cấu hình log4j. Tệp bền vững phải liệt kê tất cả các lớp (sử dụng <class>) hoặc, nếu đó không phải là ứng dụng Java SE, các tệp jar (sử dụng <jar-file>) được ứng dụng sử dụng. Bằng cách này, bạn có thể đặt các thực thể từ nhiều mô-đun (bình) vào đơn vị lưu giữ đơn. Hạn chế là rõ ràng: bạn phải liệt kê mọi thứ trong một tệp.

EDIT: Tôi đã (có thể) tìm thấy một giải pháp khác sử dụng các tệp ánh xạ XML, kiểm tra nó ở đây: Nhiều lọ, giải pháp đơn vị duy trì?

3
Adam Dyga

Bạn có thể sử dụng khái niệm này: https://wiki.Eclipse.org/Packaging_and_Deploying_EclipseLink_JPA_Appluggest_(ELUG)

<persistence version="2.1" xmlns="http://xmlns.jcp.org/xml/ns/persistence" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/persistence http://xmlns.jcp.org/xml/ns/persistence/persistence_2_1.xsd">
   <persistence-unit name="mamcaPU" transaction-type="JTA">
        <provider>org.Eclipse.persistence.jpa.PersistenceProvider</provider>
        <jta-data-source>mamcaPU</jta-data-source>
        <mapping-file>/META-INF/common-layer-mappings.xml</mapping-file>
    </persistence-unit>
</persistence>

lớp chung-mappings.xml

<entity-mappings>   
   <entity class="vub.be.mamca.entity.Surveyactorgrouptable"></entity>
   <entity class="vub.be.mamca.entity.Userevaluationelicitationtable"></entity>
   <entity class="vub.be.mamca.entity.Userevaluationtable"></entity>
   <entity class="vub.be.mamca.entity.Usertable"></entity>
   <entity class="vub.be.mamca.entity.Userweightelicitationtable"></entity>
</entity-mappings>
1
Tunde Pizzle

Tôi có một vấn đề tương tự và đã giải quyết nó với Hibernate's Integrator SPI:

@Override
public void integrate(Configuration configuration,
    SessionFactoryImplementor sessionFactory,
    SessionFactoryServiceRegistry serviceRegistry) {

    configuration.addAnnotatedClass(MyEntity.class);
    configuration.buildMappings();
}

Trình tích hợp được cung cấp dưới dạng Dịch vụ Java .

0
Markus Malkusch

Có thể trùng lặp, xem câu hỏi SO của tôi

Chúng tôi đã đối mặt với cùng một vấn đề và cách duy nhất chúng tôi tìm thấy là tích lũy tất cả các thực thể trong một tệp bền vững cho ứng dụng (web-) cuối cùng. 

Đồng thời, chúng tôi xác định các tệp kiên trì riêng biệt trong tài nguyên thử nghiệm của mình để chúng tôi có thể chạy thử nghiệm chấp nhận cho mỗi mô-đun.

0
Pete