Java JPA 2.1带PostgreSQL和REF_游标的StoredProcedureQuery
我在PostgreSQL数据库中创建了一个函数,我想使用JPA2.1的StoredProcedureQuery方法调用它 以下是我的PostgreSQL查询:Java JPA 2.1带PostgreSQL和REF_游标的StoredProcedureQuery,java,hibernate,postgresql,jpa,Java,Hibernate,Postgresql,Jpa,我在PostgreSQL数据库中创建了一个函数,我想使用JPA2.1的StoredProcedureQuery方法调用它 以下是我的PostgreSQL查询: CREATE OR REPLACE FUNCTION get_values(date text) returns refcursor AS $$ DECLARE tuples refcursor; BEGIN OPEN tuples FOR SELECT user, COUNT(*)
CREATE OR REPLACE FUNCTION get_values(date text) returns refcursor
AS $$
DECLARE tuples refcursor;
BEGIN OPEN tuples FOR
SELECT user, COUNT(*)
FROM my_table
WHERE date_ = date
GROUP BY user;
return tuples;
END;
$$
LANGUAGE plpgsql
这只是一个简单的查询,用于统计特定日期的用户数。这只是一个测试StoredProcedureQueries如何工作的演示查询。事实上,当仅通过postgreSQL使用时,它就可以正常工作
现在,让我们试着使用JPA 2.1和Javaland将其称为:
StoredProcedureQuery storedProcedure = em.createStoredProcedureQuery("get_values");
storedProcedure.registerStoredProcedureParameter(2, String.class, ParameterMode.IN);
storedProcedure.registerStoredProcedureParameter(1, Object.class, ParameterMode.REF_CURSOR);
storedProcedure.setParameter(2, "2015-02-01");
storedProcedure.execute();
执行此操作时,我返回以下异常:
org.hibernate.HibernateException: PostgreSQL supports only one REF_CURSOR parameter, but multiple were registered
只声明了一个ref游标!事实上,如果我只是为WHERE date=date注册一个REF\u CURSOR参数和一个Postgresql函数值的硬代码,那么这个调用就可以正常工作
因此,使用ref_光标向storedprocedurequery添加任何附加参数似乎都会破坏该功能。仅ref_游标参数就可以正常工作
有人知道为什么会发生这种情况吗??为什么在我的PostgreSQL函数的StoredProcedureQuery中添加参数会破坏它?
它工作时的示例:
CREATE OR REPLACE FUNCTION get_values(date text) returns refcursor
AS $$
DECLARE tuples refcursor;
BEGIN OPEN tuples FOR
SELECT user, COUNT(*)
FROM my_table
WHERE date_ = '2015-02-01'
GROUP BY user;
return tuples;
END;
$$
LANGUAGE plpgsql
在爪哇岛:
StoredProcedureQuery storedProcedure = em.createStoredProcedureQuery("get_values");
storedProcedure.registerStoredProcedureParameter(1, Object.class, ParameterMode.REF_CURSOR);
storedProcedure.execute();
简短回答:颠倒对注册表存储过程参数()的两次调用顺序。: 详细回答:我在中做了一些挖掘,发现每个
registerStoredProcedureParameter()
调用都会创建一个实例,该实例会被添加到列表中并传递。您将注意到,此类存储参数的位置,该位置独立于其在列表中的位置
稍后,此列表为,并假设REF\u CURSOR
参数将在第一行,如果REF\u CURSOR
参数不是第一个,则抛出错误消息,而不管参数编号是什么
这不是一种很好的做事方式(IMHO),但至少解决方法很简单:如果您交换通话顺序,您应该会没事。让我试试这个,然后再回复您!
storedProcedure.registerStoredProcedureParameter(1, Object.class, ParameterMode.REF_CURSOR);
storedProcedure.registerStoredProcedureParameter(2, String.class, ParameterMode.IN);