【问题标题】:EclipseLink: Wrong number or types of arguments calling a Stored ProcedureEclipseLink:调用存储过程的参数数量或类型错误
【发布时间】:2011-07-01 08:01:46
【问题描述】:

我将 EclipseLink 用于涉及 EJB 3 和 Oracle 存储过程的 Web 项目。我们还处于起步阶段,所以我设置了一个简单的测试程序,这是签名:

p_test.testProcedure(as_param in varchar2)

这是我用来调用该过程的代码,类似于 Eclipsepedia 上的 Using Basic Query API 文章:

JpaEntityManager jem = (JpaEntityManager) em.getDelegate();

StoredProcedureCall call = new StoredProcedureCall();
call.setProcedureName("p_test.testProcedure");

call.addNamedArgument("param", "param", String.class);

DataReadQuery query = new DataReadQuery();
query.setCall(call);

query.addArgument("param", String.class);

Vector<String> values = new Vector<String>();
values.add("test");

jem.getActiveSession().executeQuery(query, values);

我不断收到此错误:

Exception [EclipseLink-4002] (Eclipse Persistence Services - 2.1.1.v20100817-r8050):
org.eclipse.persistence.exceptions.DatabaseException Internal Exception: 
java.sql.SQLException: ORA-06550: line 1, column 7: PLS-00306: wrong number or types of 
arguments in call to 'TESTPROCEDURE' ORA-06550: line 1, column 7: PL/SQL: Statement
ignored Error Code: 6550 Call: BEGIN p_test.testProcedure(param=>?); END; bind => [test] Query: DataReadQuery()

我也尝试将调用参数类型设置为 java.sql.Types.VARCHAR 并且根本没有,没有效果。

有人知道我做错了什么吗?谢谢大家。

【问题讨论】:

    标签: java oracle stored-procedures jpa eclipselink


    【解决方案1】:

    看起来您在 addNamedArgument 方法中指定的 procedureParameterName 与在存储过程中指定的不同,即“param”与“as_param”。尝试将您的逻辑更改为以下内容:

    call.addNamedArgument("as_param", "param", String.class);
    

    此方法将参数名称映射到您对 query.addParameter 的调用中使用的名称与存储过程中定义的名称之间。

    【讨论】:

    • 立即尝试:错误现在是java.sql.SQLException: ORA-00900: invalid SQL statement Error Code: 0 Call: BEGIN p_test.testProcedure(as_param=&gt;?); END; bind =&gt; [test] Query: DataReadQuery()
    • 您是否验证了存储过程正确执行,即直接从 SQL*Plus 或其他 SQL 客户端执行?
    【解决方案2】:

    来自 TopLink 文档

    addNamedArgument

    public void addNamedArgument(java.lang.String procedureParameterName,
                                 java.lang.String argumentFieldName)
    

    PUBLIC:定义参数 存储过程和 要替换的字段/参数名称 为了它。过程参数名称是 过程参数的名称 预期的。 argumentFieldName 是 要用于的字段或参数名称 传递给程序。如果这些名字 是相同的(因为它们通常是) 这个方法可以用 单个参数。

    public void addNamedArgumentValue(java.lang.String procedureParameterName,
                                      java.lang.Object argumentValue)
    
     call.addNamedArgumentValue("param",(Object)values );
    

    【讨论】:

    • 这也在 EclipseLink 文档中。试过了,我现在得到java.sql.SQLException: ORA-00900: invalid SQL statement Error Code: 0 Call: BEGIN p_test.testProcedure(as_param=&gt;?); END; bind =&gt; [test] Query: DataReadQuery(),与下面相同,但代码不同。
    【解决方案3】:

    结合以上两个答案和我自己的智慧解决了。

    首先,我使用 #1 建议的 addNamedArgumentValue asu。 其次,我按照#2 的建议使用了正确的过程参数名称。 最后,我直接使用了jem.executeNonSelectingCall(call),它成功了。 (也带有 OUT 参数)。

    所以他们都投了赞成票!

    【讨论】:

      猜你喜欢
      • 2021-11-30
      • 1970-01-01
      • 2011-12-26
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2016-07-01
      相关资源
      最近更新 更多