2015-09-11 16 views
7

Vấn đề là tôi không thể lưu tập tin vào blob. Nó hoạt động mà không có bất kỳ lỗi, tập tin tạm thời được tạo ra và tôi có thể đọc từ nó. Tôi đã kiểm tra nếu nó đi đến ràng buộc - có nó đi với giá trị tài nguyên phải và với \PDO::PARAM_LOB kiểu dữ liệu.Lưu tập tin Yii2 vào Oracle BLOB

Tôi có một lớp ActiveRecord:

class News extends ActiveRecord 
{ 
    public function rules() 
    { 
     return [ 
      [ 
       ['image'], 
       'image', 
       'extensions' => 'png jpg', 
       'maxSize' => 1024 * 300, 
      ] 
     ]; 
    } 

    public function beforeSave($insert) 
    { 
     $fileInfo = UploadedFile::getInstance($this, 'image'); 
     $this->image = fopen($fileInfo->tempName, 'r+'); 
     return parent::beforeSave($insert); 
    } 

} 

Bảng:

CREATE TABLE NEWS 
(
    RN NUMBER(17,0) PRIMARY KEY NOT NULL, 
    IMAGE BLOB 
); 

Logs hiện truy vấn này:

INSERT INTO "NEWS" ("IMAGE") VALUES (:qp4) RETURNING "RN" INTO :qp8 

Vì vậy, nó không thực sự gắn nó hoặc những gì?

Trả lời

0

Dường như PDO_OCI đang hợp tác với Oracle trong kiểu cũ bằng cách nào, vì vậy bạn cần để bắt đầu một giao dịch chèn EMPTY_BLOB() đầu tiên, sau đó liên kết với biến con trỏ đến tập tin, thực hiện tuyên bố và cam kết.

Tôi đã thực hiện với bản cập nhật, vì tôi không muốn thực hiện truy vấn đầy đủ theo cách thủ công. Trước tiên, tôi viết con trỏ để ghi vào $this->file trong phương thức save() và gọi $model->save && $model->saveImage() trong bộ điều khiển.

public function saveImage() 
{ 
    if (!$this->file) { 
     return true; 
    } 
    $table = self::tableName(); 
    $rn = $this->rn; 
    $command = Yii::$app->getDb()->createCommand(
     "UPDATE $table SET IMAGE=EMPTY_BLOB() WHERE RN=:rn RETURNING IMAGE INTO :image" 
    ); 
    $command->bindParam(':rn', $rn, \PDO::PARAM_STR); 
    $command->prepare(); 
    $command->bindParam(':image', $this->file, \PDO::PARAM_LOB); 
    return $command->execute(); 
} 
3

Bạn chỉ cần sử dụng dữ liệu hình ảnh thay vì con trỏ tài nguyên, ví dụ: :

$this->image = file_get_contents($fileInfo->tempName); 

EDIT: xin lỗi bạn là đúng, bạn cần cung cấp một con trỏ tài nguyên để có thể ràng buộc param này sử dụng PARAM_LOB.

Như đã nêu trên php doc, bạn nên thử sử dụng transaction, ví dụ: :

News::getDb()->transaction(function($db) use ($model) { 
    $model->save(); 
}); 
+0

Nó mang lại cho tôi ORA-01.461: có thể ràng buộc một giá trị DÀI chỉ nhằm chèn vào một cột DÀI – UnstableFractal

+0

Đánh giá bởi 'mã nguồn UploadedFile' - không có lý do để làm việc này. Và, tốt, nó mang lại cho ORA-01465: số hex không hợp lệ – UnstableFractal

+0

Đó là một giao dịch cho tôi. – UnstableFractal