3

我正在使用 hibernate 4.1.5.Final 和 Spring 3.1.2 Release 和 Jboss 7.1 。我已经用 @NamedQuery 注释在一个类中编写了所有命名查询,但实体管理器没有创建命名查询。我正在发布堆栈跟踪和 context.xml

  09:58:49,695 ERROR [stderr] (http-localhost-127.0.0.1-8080-2) java.lang.IllegalArgumentException: Named query not found: validateLoginHash
    09:58:49,770 ERROR [stderr] (http-localhost-127.0.0.1-8080-2)   at org.hibernate.ejb.AbstractEntityManagerImpl.createNamedQuery(AbstractEntityManagerImpl.java:642)
    09:58:49,772 ERROR [stderr] (http-localhost-127.0.0.1-8080-2)   at sun.reflect.GeneratedMethodAccessor14.invoke(Unknown Source)
    09:58:49,774 ERROR [stderr] (http-localhost-127.0.0.1-8080-2)   at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
    09:58:49,777 ERROR [stderr] (http-localhost-127.0.0.1-8080-2)   at java.lang.reflect.Method.invoke(Method.java:597)
    09:58:49,779 ERROR [stderr] (http-localhost-127.0.0.1-8080-2)   at org.springframework.orm.jpa.ExtendedEntityManagerCreator$ExtendedEntityManagerInvocationHandler.invoke(ExtendedEntityManagerCreator.java:365)

    09:58:49,782 ERROR [stderr] (http-localhost-127.0.0.1-8080-2)   at $Proxy30.createNamedQuery(Unknown Source)

    09:58:49,784 ERROR [stderr] (http-localhost-127.0.0.1-8080-2)   at sun.reflect.GeneratedMethodAccessor14.invoke(Unknown Source)

    09:58:49,785 ERROR [stderr] (http-localhost-127.0.0.1-8080-2)   at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)

    09:58:49,788 ERROR [stderr] (http-localhost-127.0.0.1-8080-2)   at java.lang.reflect.Method.invoke(Method.java:597)

    09:58:49,790 ERROR [stderr] (http-localhost-127.0.0.1-8080-2)   at org.springframework.orm.jpa.SharedEntityManagerCreator$SharedEntityManagerInvocationHandler.invoke(SharedEntityManagerCreator.java:240)

    09:58:49,793 ERROR [stderr] (http-localhost-127.0.0.1-8080-2)   at $Proxy30.createNamedQuery(Unknown Source)

应用程序上下文.xml

<bean id="jpaDialect" class="org.springframework.orm.jpa.vendor.HibernateJpaDialect"/> 
    <bean id="entityManagerFactory"
        class="org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean">


        <property name="dataSource" ref="dataSource" />
        <property name="jpaDialect" ref="jpaDialect"/>
        <property name="packagesToScan" value="com.project.entities"/> 


        <property name="jpaVendorAdapter">
            <bean class="org.springframework.orm.jpa.vendor.HibernateJpaVendorAdapter">          
                <property name="showSql" value="false" />
                <property name="generateDdl" value="false" />
                <property name="databasePlatform" value="org.hibernate.dialect.MySQLDialect" />
            </bean>
        </property>

<!--        <property name="persistenceUnitName" value="Project" /> -->
        <property name="persistenceXmlLocation" value="classpath:META-INF/jpa-persistence.xml"/> 

        <property name="loadTimeWeaver">
            <bean
                class="org.springframework.instrument.classloading.InstrumentationLoadTimeWeaver" />
        </property>

    </bean>

     <bean id="dataSource" class="org.springframework.jndi.JndiObjectFactoryBean">
        <property name="jndiName" value="java:jboss/datasources/MySqlDS"/>
    </bean>


    <bean id="transactionManager" class="org.springframework.orm.jpa.JpaTransactionManager">
        <property name="entityManagerFactory" ref="entityManagerFactory" />
        <property name="dataSource" ref="dataSource" />
    </bean>

jpa-persistence.xml

<persistence>
    <persistence-unit name="Project" transaction-type="RESOURCE_LOCAL" >


        <provider>org.hibernate.ejb.HibernatePersistence</provider>
         <non-jta-data-source>java:jboss/datasources/MySqlDS</non-jta-data-source>
<!--         <properties>  -->
<!--           <property name="jboss.as.jpa.providerModule" value="hibernate3-bundled" />        -->
<!--           </properties>          -->

    </persistence-unit>

</persistence>

DBNamedQuery.java

@Entity
@NamedQueries( {

@NamedQuery(name = ... , query = ... ),
@NamedQuery(name = ..., query = ...),

.....More named queries

})

public class DBNamedQuery {


}
4

5 回答 5

4
I have written all named queries in a class with @NamedQuery annotation

您在上述声明中没有明确提到您所指的类的类型?您需要在 Entity 类(使用 @Entity 注释的类)中编写命名查询。

更新:我现在对你的课有点困惑DBNamedQuery。您说您正在使用一个类来放置所有命名查询。我的理解是您正在使用此类为应用程序的所有实体编写命名查询。如果这是正确的,你怎么能@Entity在你的类上使用注释,DBNamedQuery因为它不是真正的 jpa 实体?

包含@NamedQuery注释的类应该是托管实体。我怀疑你的课DBNamedQuery不是。

为了确定问题,我建议检查日志,如果这是一个被管理的实体。如果你不能这样做,那么EntityManger给你和 API 在运行时检查contains(java.lang.Object entity)

在相关说明中,如果您使用注释,则 JPA 命名查询是 jpa 实体的一部分。使用 xml 可以让您灵活地存储在单独的文件中。

于 2013-01-04T13:38:14.510 回答
2

嗨,我遇到了您的问题,而不是创建一个类,为什么不为 Queries.hbm.xml 之类的命名查询创建一个 xml 文件,如下所示

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE hibernate-mapping PUBLIC
"-//Hibernate/Hibernate Mapping DTD 3.0//EN"
"http://hibernate.sourceforge.net/hibernate-mapping-3.0.dtd">
<hibernate-mapping>
    <!-- Query For User TO -->
    <query name="loadUserByUsername">from User u where u.username = ?</query>
</hibernate-mapping>

将此 xml 文件保存在资源文件夹中,并在您的 applicationContext-enterprise-config.xml 文件中写入如下

<property name="mappingResources">
    <list>
        <value>/resources/hbms/Queries.hbm.xml</value>
    </list>
</property>

所以它会正常工作。

编辑 好这取决于您在 DAO 层中如何调用它。你必须打电话给=>

public int executeNamedQuery(String namedQuery, String namedParams[], Object params[]) throws DatabaseException {
        int result = 0;
        Session session = getSession();
        final String methodName = "executeNamedQuery";
        try {
            session.beginTransaction();
            Query q = session.getNamedQuery(namedQuery);
            if (namedParams != null) {
                for (int i = 0; i < namedParams.length; i++) {
                    q.setParameter(namedParams[i], params[i]);
                }
            }
            result = q.executeUpdate();
            session.getTransaction().commit();
            logger.debug("{} :: {} = {}", new Object[] { methodName, "No. of objects affected", result });
        } catch (HibernateException e) {
            session.getTransaction().rollback();

            final String message = "Couldn't execute the named query " + namedQuery;
            logger.error("{} :: {}", new Object[] { methodName, message, e });
            throw new DatabaseException(getClass(), methodName, message, e);
        } finally {
            closeSession();
        }
        return result;
    }

注:1)namedQuery 表示 Queries.hbm.xml 文件中查询的名称。2) namedParams[] 表示 Query 的参数名称。3) params 表示参数的值。

于 2013-01-09T11:58:17.240 回答
1

检查您的实体类是否在您在ApplicationContext.xml文件中配置DBNamedQuery的包中com.project.entities

于 2013-01-09T09:16:42.060 回答
1

我认为这是因为名称错过匹配。在 @NamedQuery 中声明的名称与称为该查询的名称不匹配。

例如

@NamedQuery(name = "AAAA", query = ... ) //must be same the name which call that query

public void some() {
   Query q = em.createNamedQuery("AAAA");
 }
于 2013-01-13T09:17:47.937 回答
0

在persistence.xml中添加注释扫描为我解决了这个问题

<property name="hibernate.archive.autodetection" value="class, hbm" />

即使我尝试在我的实体管理器中进行包扫描,如下所示也没有工作

  @Bean
       public LocalContainerEntityManagerFactoryBean entityManagerFactory() {
           LocalContainerEntityManagerFactoryBean em = new LocalContainerEntityManagerFactoryBean();
           em.setDataSource(getDataSource());
           //em.setPackagesToScan("com.comp.proj.domain");
           em.setPersistenceUnitName(PERSISTENCE_UNIT_NAME);
           em.setJpaVendorAdapter(new HibernateJpaVendorAdapter());
           return em;
       }
于 2017-08-21T22:21:37.980 回答