简体   繁体   中英

PDO_OCI - into a clob field

I want to insert some base64 encoded data (up to 500.000 characters per field) in an Oracle DB.

Since i havn't used Oracle with PHP before i started using PDO and set fields to CLOB.

Shortversion of my code ( class Db extends \\PDO ):

<?php

[..snip..]

        $dbh = new Db( "oci:dbname=" . DB_TNS, DB_USER, DB_PASS );
        $Query = ' INSERT INTO "SENTINEL"."SYSTEM_ERRORS" 
                ( BACKTRACE ) 
                VALUES
                ( :backtrace )
        ';  
        $stmt = $dbh->db_prepare( $Query );
        $stmt->bindParam( ':backtrace', $backtrace, \PDO::PARAM_LOB );
        $backtrace = $someobject->get_backtrace();
        $stmt->execute();
        print_r($stmt->errorInfo());
        $stmt->closeCursor();

I get:

Array ( [0] => HY000 [1] => 932 [2] => OCIStmtExecute: ORA-00932: Inkonsistente Datentypen: CLOB erwartet, BLOB erhalten (ext\\pdo_oci\\oci_statement.c:148) )

Anyone know how to solve that with PDO, so i don't have to use the oci driver?

I have found a solution here:

https://bugs.php.net/bug.php?id=57095

[2009-08-11 11:27 UTC] lehresman at gmail dot com wrote:

A coworker discovered the solution. When dealing with CLOBs in Oracle using PDO, don't treat it as a LOB. You need to bind it as a PDO::PARAM_STR, and give it the length of the string (that 4th parameter is the key, it fails with an error message about LONG type otherwise).

Here is an example of how to successfully insert into a CLOB in Oracle:

<?php

/*
CREATE TABLE clob_test (my_clob CLOB)
*/

$big_string = "";
for ($i=0; $i < 10000; $i++)
    $big_string .= rand(100000,999999)."\n";

try {
    $pdo = new PDO("oci:dbname=TESTDB", "TESTUSER", "TESTPW");
    $stmt = $pdo->prepare("INSERT INTO healthbit.clob_test (my_clob) VALUES (:cl)");
    $stmt->bindParam(":cl", $big_string, PDO::PARAM_STR, strlen($big_string));
    $pdo->beginTransaction();
    if (!$stmt->execute()) {
        echo "ERROR: ".print_r($stmt->errorInfo())."\n";
        $pdo->rollBack();
        exit;
    }
    $pdo->commit();

    $stmt = $pdo->prepare("SELECT my_clob FROM healthbit.clob_test");
    $stmt->execute();
    $row = $stmt->fetch();
    $str = "";
    while ($tmp = fread($row[0],1024))
        $str .= $tmp;
    echo strlen($str); // prints 70000
} catch (Exception $e) {
    echo "ERROR: ";
    echo $e->getMessage();
    $pdo->rollBack();
}

Works perfectly fine for me...

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM