如何使用 pdo 将字符串数组传递给 php 中的 plsql 例程

Posted

技术标签:

【中文标题】如何使用 pdo 将字符串数组传递给 php 中的 plsql 例程【英文标题】:How to pass an array of strings to a plsql routine in php with pdo 【发布时间】:2016-04-08 05:48:27 【问题描述】:

我在 Windows 上使用带有 PDO 扩展的 php 5.5。到目前为止,即使使用 plsql 脚本,oracle 的一切都可以正常工作。以下是我的 plsql 包和我的 php 代码的简化代码。

基本上我只想将数组$remarks 交给plsql 过程VARRAY_TEST。这与函数的逻辑无关,而与 pdo 调用本身有关。

TYPE remarkarray IS VARRAY(64) of varchar2;


PROCEDURE VARRAY_TEST
(
  remarks     IN  remarkarray,
  examplemsg  OUT varchar2 
)
AS

BEGIN

  for remarkcounter in remarks.first ..remarks.last loop
    examplemsg := examplemsg || ' ' || remarks(remarkcounter);
  end loop;

END VARRAY_TEST;

现在是我的 PHP-PDO 代码。

$exampleMsg = "";
$remarks = ["hoho", "haha"];
$query = $this->prepare("begin MY_PACKAGE.VARRAY_TEST(:remarks, :exampleMsg); end;");

try

    $query->bindParam(':remarks', $remarks, PDO::PARAM_STR);
    $query->bindParam(':exampleMsg', $exampleMsg, PDO::PARAM_STR, 200);
    $query->execute();
    var_dump($exampleMsg);

catch(Exception $ex)

    var_dump($ex);

不幸的是,抛出了以下异常:

class PDOException#50 (9) 
...
  string(257) "SQLSTATE[HY000]: General error: 6550 OCIStmtExecute: ORA-06550: row 1, column 7:
  PLS-00306: Wrong number or types of arguments in call 'VARRAY_TEST'
  ORA-06550: Zeile 1, Spalte 7: PL/SQL: Statement ignored (ext\pdo_oci\oci_statement.c:148)"
...

有人知道如何解决这个问题吗?也非常感谢解决方法。

提前致谢。

编辑:

目前尝试没有成功:

$query->bindParam(':remarks'... 中完全删除了最后一个/第三个参数

class PDOException#50 (9) 
...
  string(257) "SQLSTATE[HY000]: General error: 6550 OCIStmtExecute: ORA-06550: row 1, column 7:
  PLS-00306: Wrong number or types of arguments in call 'VARRAY_TEST'
  ORA-06550: Zeile 1, Spalte 7: PL/SQL: Statement ignored (ext\pdo_oci\oci_statement.c:148)"
...

添加了PDO::PARAM_STMT 而不是PDO::PARAM_STR 导致

class PDOException#50 (9) 
...
  string(144) "SQLSTATE[HY000]: General error: 1008 OCIStmtExecute: ORA-01008: Not all variables seem to have a bound value (ext\pdo_oci\oci_statement.c:148)"
...

【问题讨论】:

如果从第一个绑定中删除 PDO::PARAM_STR 会有什么变化吗? 是的,我做到了,不幸的是没有成功。我添加了一个编辑部分来反映所有试验。但是感谢您的评论。 【参考方案1】:

http://php.net/manual/en/function.oci-bind-array-by-name.php

$c = oci_connect('hr', 'hrpwd', '//localhost/XE'); 
$a = array('abc', 'def', 'ghi', 'jkl'); 
$s = oci_parse($c, "begin mypkg.myinsproc(:p1); end;"); 
oci_bind_array_by_name($s, ":p1", $a, count($a), -1, SQLT_CHR); 
oci_execute($s); 

希望这会有所帮助。

【讨论】:

谢谢,但我已经知道该方法,但由于我们使用的是 PDO,因此它不能解决我的问题。如果您可以向我展示一种混合 PDO 和 OCI 扩展的优雅方式,我当然会接受这个答案。 知道了。感谢您的澄清。请参阅我的新答案。 PDO-OCI 没有“结构数组或静态数组”的实现。【参考方案2】:

我查看了 PDO OCI 的源文件,*.c 来自 https://pecl.php.net/package/PDO_OCI

据我所知,PDO 不支持数组。 顺便说一句,最新的 PDO_OCI 版本 1.0 可以追溯到 2005-11-26 在该页面中,11 年前。

查看 OCI 文档 https://docs.oracle.com/cd/B28359_01/appdev.111/b28395/oci05bnd.htm#r7c1-t10 ,绑定“结构数组或静态数组”需要 OCIBindArrayOfStruct() 调用。 PDO_OCI的源代码*.c没有这个函数的调用。

【讨论】:

感谢您指出您搜索资源的方式。

以上是关于如何使用 pdo 将字符串数组传递给 php 中的 plsql 例程的主要内容,如果未能解决你的问题,请参考以下文章

如何使用 PDO 从 PHP 中的单个 select 语句将孩子分配给父母?

如何从python脚本将数组传递给php?

如何使用 PHP 和 Ajax 将数组传递给 Javascript?

将字符串数组作为 POST 传递给 PHP

将参数从php中的数组传递给构造函数[重复]

如何将字符串数组动态传递给Java中的SQL“IN”子句? [复制]