19

我试图将我的命名查询放在我的 orm.xml 中(放入 META-INF 和 persistence.xml),但我的 orm.xml 似乎被 hibernate/jpa 忽略了。

当我尝试使用 em.createNamedQuery("myQuery") 创建命名查询时,它返回找不到此查询。

我使用注释,我想在 orm.xml 中外部化我的命名查询(仅此而已)。

这是我的persistence.xml:

<?xml version="1.0" encoding="UTF-8"?>
<persistence xmlns="http://java.sun.com/xml/ns/persistence" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://java.sun.com/xml/ns/persistence http://java.sun.com/xml/ns/persistence/persistence_1_0.xsd" version="1.0">

<persistence-unit name="default" transaction-type="RESOURCE_LOCAL">
    <mapping-file>META-INF/orm.xml</mapping-file>

    <class>com.mysite.Account</class>

    <properties>
        <property name="hibernate.cache.provider_class" value="net.sf.ehcache.hibernate.EhCacheProvider" />
        <property name="hibernate.cache.use_query_cache" value="true" />
        <property name="hibernate.cache.use_second_level_cache" value="true" />
        <property name="hibernate.show_sql" value="true" />
        <property name="hibernate.format_sql" value="true" />
        <property name="use_sql_comments" value="false" />
        <property name="hibernate.dialect" value="org.hibernate.dialect.MYSQLDialect" />
        <property name="hibernate.c3p0.min_size" value="5" />
        <property name="hibernate.c3p0.max_size" value="20" />
        <property name="hibernate.c3p0.timeout" value="300" />
        <property name="hibernate.c3p0.max_statements" value="50" />
        <property name="hibernate.c3p0.idle_test_period" value="3000" />

        <property name="hibernate.search.default.directory_provider" value="org.hibernate.search.store.FSDirectoryProvider" />
    </properties>

</persistence-unit>

</persistence>

这是我的 orm.xml

<?xml version="1.0" encoding="UTF-8"?>
<entity-mappings xmlns="http://java.sun.com/xml/ns/persistence/orm" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://java.sun.com/xml/ns/persistence/orm http://java.sun.com/xml/ns/persistence/orm_1_0.xsd" version="1.0">

<package>com.mysite</package>

<entity class="Account">
    <sql-result-set-mapping name="nicknames">
        <column-result name="nickname" />
    </sql-result-set-mapping>
    <table name="Account" />
    <named-native-query name="myQuery" result-set-mapping="nicknames">
        <query><![CDATA[select a.nickname from Account a]]>
    </query>
    </named-native-query>
</entity>
</entity-mappings>

我做错了什么?为什么我的 orm.xml 被忽略了?

谢谢

4

4 回答 4

9

好的,我终于明白了!

我将我的 orm.xml 保存在 META-INF 目录中。当我将此文件移动到包含域对象的包中时(例如在我的示例中:com.mysite),不会忽略 orm.xml 并全部运行。

我还需要更改映射文件(persistence.xml)中的路径:com/mysite/orm.xml

于 2010-03-04T14:50:50.430 回答
5

你的 orm.xml 有一个小错误,它破坏了整个事情。关键是元素声明的顺序应该符合各自的 XML 模式(特别是http://java.sun.com/xml/ns/persistence/orm_1_0.xsd)。这很容易通过支持 xml 模式的验证器运行 xml 代码来检查。下面是你的 orm.xml 的更正版本,它必须作为一个魅力。

<?xml version="1.0" encoding="UTF-8"?>
<entity-mappings xmlns="http://java.sun.com/xml/ns/persistence/orm"
                 xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
                 xsi:schemaLocation="
                     http://java.sun.com/xml/ns/persistence/orm
                     http://java.sun.com/xml/ns/persistence/orm_1_0.xsd"
                 version="1.0">

    <package>com.mysite</package>

    <entity class="Account">
        <table name="Account" />
        <named-native-query name="myQuery" result-set-mapping="nicknames">
            <query><![CDATA[
            select a.nickname from Account a
            ]]></query>
        </named-native-query>
        <sql-result-set-mapping name="nicknames">
            <column-result name="nickname" />
        </sql-result-set-mapping>
    </entity>
</entity-mappings>
于 2011-10-27T19:39:14.240 回答
2

如前所述

当我尝试使用 em.createNamedQuery("myQuery") 创建命名查询时,它返回找不到此查询

你说的对。但是您忘记了以下内容

如果将命名查询定义放在元素内,而不是根,它会以实体类的名称为前缀

因此,您需要将您的 namedQuery 称为

 em.createNamedQuery("Account.myQuery")

我很好奇:您的 Account 类是否存储在根类路径中???如果没有,你已经修复了它丢失的包。假设 Account 类存储在 br.com.hibernate.model.domain.Account 中。所以你应该将你的实体声明为

<entity class="br.com.hibernate.model.domain.Account" instead

您需要将您的 namedQuery 称为

em.createNamedQuery("br.com.hibernate.model.domain.Account.myQuery") instead

只是一个建议:当您使用 Hibernate 作为您的持久性提供者时,您不需要在 persistence.xml 文件中定义您的实体类。

问候,

于 2010-03-04T05:05:48.350 回答
0

“META-INF/orm.xml”是任何符合 JPA 的实体管理器都会查看的默认映射文件。

事实上,如果您的映射文件是“META-INF/orm.xml”,您甚至不需要在您的 persistence.xml 中定义它。

这是休眠配置手册对此的说明:

类元素指定您将映射的符合 EJB3 的 XML 映射文件。该文件必须在类路径中。根据 EJB3 规范,Hibernate EntityManager 将尝试加载位于 META_INF/orm.xml 的 jar 文件中的映射文件。当然,任何显式映射文件也会被加载。事实上,您可以在映射文件元素中提供任何 XML 文件,即。hbm 文件或 EJB3 部署描述符。

参考:休眠配置

于 2011-03-28T02:23:37.333 回答