我在OSGI环境下对JPA遇到问题。
有关环境和框架的一些信息:
在我的项目中,(几乎)同一实体类上需要两个不同的持久性单元,因为我需要用两个不同的Oracle模式编写。
所以我有两个这样的数据源(具有不同的参数):
<blueprint xmlns="http://www.osgi.org/xmlns/blueprint/v1.0.0">
<bean id="oraDataSource" class="org.apache.commons.dbcp2.BasicDataSource" destroy-method="close">
<property name="driverClassName" value="oracle.jdbc.OracleDriver" />
<property name="url" value="jdbc:oracle:thin:@******" />
<property name="username" value="***" />
<property name="password" value="***" />
<property name="validationQuery" value="SELECT 1 FROM DUAL" />
<property name="initialSize" value="5"/>
<property name="maxIdle" value="5"/>
<property name="maxTotal" value="20"/>
</bean>
<service interface="javax.sql.DataSource" ref="oraDataSource">
<service-properties>
<entry key="osgi.jndi.service.name" value="jdbc/oraDataSource"/>
</service-properties>
</service>
这是简化的persistence.xml:
<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<persistence version="2.0"
xsi:schemaLocation="http://java.sun.com/xml/ns/persistence http://java.sun.com/xml/ns/persistence/persistence_2_0.xsd"
xmlns="http://java.sun.com/xml/ns/persistence"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
<persistence-unit name="PU">
<provider>org.hibernate.jpa.HibernatePersistenceProvider</provider>
<non-jta-data-source>osgi:service/javax.sql.DataSource/(osgi.jndi.service.name=jdbc/oraDataSource)</non-jta-data-source>
<!-- orm class -->
.....
<class>my.path.jpa.model.Pratica</class>
<class>my.path.jpa.model.Tag</class>
......
<exclude-unlisted-classes>true</exclude-unlisted-classes>
<properties>
<property name="hibernate.dialect" value="org.hibernate.dialect.Oracle12cDialect"/>
<property name="hibernate.jdbc.use_streams_for_binary" value="false"/>
<!--<property name="hibernate.show_sql" value="true"/>-->
<property name="hibernate.hbm2ddl.auto" value="validate"/>
</properties>
</persistence-unit>
<persistence-unit name="SYM-PU">
<provider>org.hibernate.jpa.HibernatePersistenceProvider</provider>
<non-jta-data-source>osgi:service/javax.sql.DataSource/(osgi.jndi.service.name=jdbc/symOraDataSource)</non-jta-data-source>
<!-- orm class -->
.....
<class>my.path.jpa.model.Pratica</class>
<class>my.path.jpa.model.Tag</class>
......
<class>my.path.jpa.model.sym.PraticaSym</class>
<exclude-unlisted-classes>true</exclude-unlisted-classes>
<properties>
<property name="hibernate.dialect" value="org.hibernate.dialect.Oracle12cDialect"/>
<property name="hibernate.jdbc.use_streams_for_binary" value="false"/>
<!--<property name="hibernate.show_sql" value="true"/>-->
<property name="hibernate.hbm2ddl.auto" value="validate"/>
</properties>
</persistence-unit>
</persistence>
这是我的felix插件配置:
<plugin>
<groupId>org.apache.felix</groupId>
<artifactId>maven-bundle-plugin</artifactId>
<version>${maven.bundle.plugin.version}</version>
<extensions>true</extensions>
<configuration>
<instructions>
<Bundle-SymbolicName>${project.artifactId}</Bundle-SymbolicName>
<Meta-Persistence>META-INF/persistence.xml</Meta-Persistence>
<Export-Package>
my.path.jpa*
</Export-Package>
<Import-Package>
org.hibernate.proxy, javassist.util.proxy, oracle.jdbc, *
</Import-Package>
<DynamicImport-Package>oracle.jdbc.driver</DynamicImport-Package>
</instructions>
</configuration>
</plugin>
当我尝试安装包含此捆绑软件的功能时,出现以下错误仅第一次我尝试安装:
2019-10-07T18:50:19,315 | ERROR | CM Configuration Updater (ManagedService Update: pid=[org.apache.aries.jpa.SYM-PU]) | lix.cm.impl.ConfigurationManager 1284 | 9 - org.apache.felix.configadmin - 1.8.16 | [org.osgi.service.cm.ManagedService, id=2531, bundle=8564/mvn:org.apache.aries.jpa/org.apache.aries.jpa.container/2.6.1]: Unexpected problem updating configuration org.apache.aries.jpa.SYM-PU
org.hibernate.boot.registry.classloading.spi.ClassLoadingException: Unable to load class [my.path.jpa.model.Tag]
at org.hibernate.boot.registry.classloading.internal.ClassLoaderServiceImpl.classForName(ClassLoaderServiceImpl.java:348) [8587:org.hibernate.core:5.2.9.Final]
at org.hibernate.boot.model.source.internal.annotations.AnnotationMetadataSourceProcessorImpl.<init>(AnnotationMetadataSourceProcessorImpl.java:104) [8587:org.hibernate.core:5.2.9.Final]
at org.hibernate.boot.model.process.spi.MetadataBuildingProcess$1.<init>(MetadataBuildingProcess.java:147) [8587:org.hibernate.core:5.2.9.Final]
at org.hibernate.boot.model.process.spi.MetadataBuildingProcess.complete(MetadataBuildingProcess.java:141) [8587:org.hibernate.core:5.2.9.Final]
at org.hibernate.jpa.boot.internal.EntityManagerFactoryBuilderImpl.metadata(EntityManagerFactoryBuilderImpl.java:858) [8587:org.hibernate.core:5.2.9.Final]
at org.hibernate.jpa.boot.internal.EntityManagerFactoryBuilderImpl.build(EntityManagerFactoryBuilderImpl.java:885) [8587:org.hibernate.core:5.2.9.Final]
at org.hibernate.osgi.OsgiPersistenceProvider.createContainerEntityManagerFactory(OsgiPersistenceProvider.java:96) [8589:org.hibernate.osgi:5.2.9.Final]
at org.apache.aries.jpa.container.impl.ManagedEMF.createAndPublishEMF(ManagedEMF.java:129) [8564:org.apache.aries.jpa.container:2.6.1]
at org.apache.aries.jpa.container.impl.ManagedEMF.updated(ManagedEMF.java:125) [8564:org.apache.aries.jpa.container:2.6.1]
at org.apache.felix.cm.impl.helper.ManagedServiceTracker.updated(ManagedServiceTracker.java:189) [9:org.apache.felix.configadmin:1.8.16]
at org.apache.felix.cm.impl.helper.ManagedServiceTracker.updateService(ManagedServiceTracker.java:152) [9:org.apache.felix.configadmin:1.8.16]
at org.apache.felix.cm.impl.helper.ManagedServiceTracker.provideConfiguration(ManagedServiceTracker.java:85) [9:org.apache.felix.configadmin:1.8.16]
at org.apache.felix.cm.impl.ConfigurationManager$ManagedServiceUpdate.provide(ConfigurationManager.java:1479) [9:org.apache.felix.configadmin:1.8.16]
at org.apache.felix.cm.impl.ConfigurationManager$ManagedServiceUpdate.run(ConfigurationManager.java:1435) [9:org.apache.felix.configadmin:1.8.16]
at org.apache.felix.cm.impl.UpdateThread.run0(UpdateThread.java:141) [9:org.apache.felix.configadmin:1.8.16]
at org.apache.felix.cm.impl.UpdateThread.run(UpdateThread.java:109) [9:org.apache.felix.configadmin:1.8.16]
at java.lang.Thread.run(Thread.java:748) [?:?]
Caused by: java.lang.ClassNotFoundException: Could not load requested class : my.path.jpa.model.Tag
at org.hibernate.boot.registry.classloading.internal.ClassLoaderServiceImpl$AggregatedClassLoader.findClass(ClassLoaderServiceImpl.java:336) ~[?:?]
at java.lang.ClassLoader.loadClass(ClassLoader.java:424) ~[?:?]
at java.lang.ClassLoader.loadClass(ClassLoader.java:357) ~[?:?]
at java.lang.Class.forName0(Native Method) ~[?:?]
at java.lang.Class.forName(Class.java:348) ~[?:?]
at org.hibernate.boot.registry.classloading.internal.ClassLoaderServiceImpl.classForName(ClassLoaderServiceImpl.java:345) ~[?:?]
... 16 more
如果我重试安装该功能,一切正常!
问题始终在第二个持久性单元上。如果我尝试用第二个PU反转第一个,在persistence.xml中先声明SYM-PU而不是PU,则在PU上也会发生相同的问题。
谢谢您的回答。
我遇到了同样的问题,但仍然不知道如何解决。