it-swarm.com.de

JPA 2.0: Hinzufügen von Entitätsklassen zu PersistenceUnit * aus einer anderen JAR * automatisch

Ich besitze eine von Maven erstellte CDI-basierte Java SE-App mit einem Core -Modul und anderen Modulen.
Core hat den persistence.xml und einige Entitäten. Module haben zusätzliche Entitäten.

Wie kann ich die Objekte zum Spotlight der Persistenz-Einheit hinzufügen?

Ich habe das Hibernate-Handbuch gelesen, http://docs.jboss.org/hibernate/stable/entitymanager/reference/en/html/configuration.html#setup-configuration-packaging

Ich habe auch diese SO Fragen gesehen

Ich suche nach einer Lösung, bei der Hibernate nach allen geladenen Klassen sucht oder eine Konfigurationsdatei aus den anderen Gläsern aufnimmt (wie es beispielsweise CDI mit beans.xml tut).

Meine App verwendet Spring nicht. Ich bestehe nicht auf Portabilität - ich bleibe bei Hibernate.

  • Gibt es eine solche Lösung?
  • Gibt es eine Möglichkeit, aus persistence.xml ein PU zu erstellen und programmgesteuert Klassen hinzuzufügen?
  • Kann ich @Entity-Klassen zu EntityManagerFactory hinzufügen, nachdem sie erstellt wurden?

Update: Ich fand in org.​hibernate.​ejb.​Ejb3Configuration:

public Ejb3Configuration configure(String persistenceUnitName, Map integration)  

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

37
Ondra Žižka

Es gibt mehrere Wege, um es zu lösen:

  1. Wie beschrieben in Benötige ich <class> -Elemente in persistence.xml? , Sie können die hibernate.archive.autodetection-Eigenschaft festlegen, und Hibernate sollte in der Lage sein, alle mit Anmerkungen versehenen Klassen in classpath nachzuschlagen. Dies entspricht jedoch nicht den Vorgaben der JPA-Spezifikationen.

  2. Wenn Sie Spring aus Spring 3.1.2 (oder wahrscheinlich sogar etwas früher) verwenden, können Sie in LocalContainerEntityManagerFactoryBeanpackageToScan definieren, das LocalContainerEntityManagerFactoryBean dazu auffordert, im Klassenpfad nach allen mit Anmerkungen versehenen Klassen zu suchen. Wiederum nicht konform mit JPA-Spezifikationen. 

  3. Ich habe Maven als Build-Tools verwendet. Vor Jahren habe ich ein kleines Plugin geschrieben, das während des Erstellungsprozesses persistence.xml generiert. Das Plugin scannt aus build classpath nach allen mit Anmerkungen versehenen Klassen und listet sie in der generierten persistence.xml auf. Dies ist sehr langwierig, aber das Ergebnis entspricht den JPA-Spezifikationen. Ein Nachteil (der für die meisten Menschen, von dem ich glaube, dass er nicht zutrifft) ist, dass die Suche in der Build-Zeit und nicht in der Laufzeit erfolgt. Das heißt, wenn Sie über eine Anwendung verfügen, für die Entitäten-JARs nur zur Implementierungs-/Laufzeitumgebung, jedoch nicht zum Erstellungszeitpunkt bereitgestellt werden, funktioniert dieser Ansatz nicht.

11
Adrian Shum

Ejb3Configuration wurde in 4.3.0 entfernt. Wenn Sie keinen Hibernate-Integrator erstellen möchten, können Sie die Eigenschaft hibernate.ejb.loaded.classes verwenden.

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

Dabei ist entities ein List<Class> von Entitätsklassen.

7
Ignacio Baca

Ich habe ein etwas anderes Setup, in dem ich persistence.xml in der WAR-Datei platziere, aber einige seiner Abhängigkeiten enthalten @Entity-Anmerkungen, die klassifiziert werden, um sie in die Persistenzeinheit aufzunehmen. 

Ich habe mein Problem gelöst, indem ich Maven so ähnlich wie Adrian Shum in # 3 beschrieben habe, das Element aber dazu verwendet habe, die Gläser aufzunehmen, die nach @Entity-Anmerkungen gescannt werden sollen. 

Ich habe für jede Abhängigkeit, einschließlich zusätzlicher Entitäten, eine Eigenschaft zu my-web/pom.xml hinzugefügt. Alle meine Gläser sind Teil eines Maven-Multiprojekts, daher sieht es für mich so aus. 

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

Danach füge ich der persistence.xml folgendes hinzu

<?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>

Zuletzt konfiguriere ich das Maven-Resource-Plugin in web/pom.xml, um die $ -Ausdrücke in persistence.xml durch die im POM festgelegten Eigenschaften zu ersetzen

<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

Ich habe das gleiche Problem erlebt und leider gibt es keine einfache Lösung. Im Grunde sieht es so aus, als wäre JPA nicht für diese Verwendung konzipiert. Eine der Lösungen besteht darin, pro Projekt der obersten Ebene (Anwendung) nur one persistence.xml zu haben. Es ähnelt der log4j-Konfiguration. Die persistence.xml muss alle Klassen auflisten (mit <class>) oder, wenn es sich nicht um eine Java SE-App handelt, JAR-Dateien (mit <jar-file>), die von der Anwendung verwendet werden. Auf diese Weise können Sie Entitäten aus mehreren Modulen (Gläsern) in eine einzige Persistenzeinheit setzen. Der Nachteil liegt auf der Hand: Sie müssen alles in einer Datei auflisten.

BEARBEITEN: Ich habe (möglicherweise) eine andere Lösung gefunden, die XML-Zuordnungsdateien verwendet. Sehen Sie sich das hier an: Mehrere Gläser, Lösung mit einer einzelnen Persistenzeinheit?

3
Adam Dyga

Sie können dieses Konzept verwenden: https://wiki.Eclipse.org/Packaging_and_Deploying_EclipseLink_JPA_Applications_ (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>

common-layer-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

Ich habe ein ähnliches Problem und gelöst mit Hibernate Integrator SPI:

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

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

Der Integrator wird als Java-Dienst bereitgestellt.

0
Markus Malkusch

Mögliches Duplikat, siehe my SO - Frage

Wir hatten das gleiche Problem und die einzige Möglichkeit, die wir fanden, bestand darin, alle Entitäten in einer persistence.xml für die endgültige (Web-) Anwendung zu sammeln. 

Gleichzeitig definieren wir in unseren Testressourcen separate persistence.xml-Dateien, damit wir Abnahmeprüfungen pro Modul durchführen können.

0
Pete