簡體   English   中英

MariaDB使用PHP PDO以與原始字段不同的值存儲varbinary字段

[英]MariaDB stores varbinary field with different value from the original field using PHP PDO

我正在使用PHP-PDO將使用RowVersion的SQL Server表從我們的ERP同步到MariaDB數據庫(托管)。

當我將值保存在本地(辦公室)MariaDB數據庫版本5.5.56中時,一切正常,數據已正確存儲。 當我執行相同的操作以將數據存儲在MariaDB 10.0.37版中的主機中時,rowversion字段將保存不同的值。

我嘗試使用PHP PDO,而不是從SQL Server,在辦公室MariaDb和遠程MariaDb之間復制數據,但我遇到了同樣的問題。 原始rowversion值與遠程rowversion值不同。

為了存儲行版本字段,我正在使用VARBINARY(8)。

例:

  • ERP SQL SERVER ROW:(ID,描述,行版本)。 值:1,AMARILLO,0x00000000025DB362 ERP ROW

  • MariaDb本地數據庫:存儲的值1,AMARILLO,00000000025db362 本地MariaDb行

  • MariaDb遠程數據庫:存儲的值:1,AMARILLO,00000000025d3f62 MariaDb遠程行

我不明白為什么遠程MariaDb保存不同的值。 兩個mariadb表相同,但是其中一個存儲一個值,另一個存儲不同的值。 有任何想法嗎? 可能是數據庫版本問題嗎?

PHP TEST代碼,在這種情況下,從本地MariaDb到遠程MariaDb:

    $sql = "SELECT * FROM colors";
    $sth = $this->Db->localdb->query($sql);
    $res = $sth->fetchAll(PDO::FETCH_ASSOC);

    $sql = "TRUNCATE TABLE colors";
    $this->Db->remotedb->exec($sql);

    $sql = "INSERT INTO colors (id,des,rowversion) VALUES (?,?,?)";
    $sthinsert = $this->Db->remotedb->prepare($sql);


    foreach ($res as $line)
    {
            echo "Inserting color {$line['id']}" . PHP_EOL;
            $sthinsert->execute(array(
                $line['id'],$line['des'],$line['rowversion']
            ));         
    }

表:

CREATE TABLE `colors` (
    id                              int NOT NULL,
    des                             varchar(30),
    rowversion                      varbinary(8),
    date                            timestamp NOT NULL DEFAULT NOW() ON UPDATE CURRENT_TIMESTAMP, 
    PRIMARY KEY (id)
) ENGINE=myisam DEFAULT CHARSET=utf8 COLLATE=utf8_spanish_ci COMMENT 'Colors';

更新並解決:

閱讀這篇文章后, PHP / PDO / MySQL:插入MEDIUMBLOB中存儲了錯誤的數據,我已經測試過要更改遠程數據庫中的SET NAMES。 那解決了問題。

我將此行添加到我的PHP程序中:

$this->Db->remotedb->exec("SET NAMES latin1 COLLATE latin1_general_ci");

現在的問題是,為什么數據庫(MariaDB)以一種方式工作而第二種以另一種方式工作。

Sqlserver正在使用Modern_Spanish_CI_AS排序規則。

本地mariadb正在使用utf8mb4_unicode_ci,並且我在PDO utf8中進行了設置

遠程mariadb位於utf8mb4_general_ci中,我也為utf8設置了PDO。

通過這些排序規則,來自SqlServer的數據存儲的方式有所不同。 設置新的排序規則即可解決。 如果PDO可以使用二進制數據而不進行任何解釋進行整理會更好。

第二次更新

我找到了一種更好的方法:

  • 我使用CHARSET = utf8mb4 COLLATE = utf8mb4_unicode_ci創建表

  • 我將PDO中的CHARSET更改為:

$this->Db->remotedb->exec("SET NAMES utf8mb4 COLLATE utf8mb4_unicode_ci");

這樣,就可以正確存儲rowversion和languague特定的字符。

干杯。

PDO嘗試使用指定的UTF-8編碼將二進制值轉換為字符串。 B3不是有效的代碼點,因此被替換為? -從字符串編碼為二進制編碼時,然后獲得3F作為替換字符的值?

為了防止PDO進行二進制到字符串的轉換,請參見以下SO帖子:

將圖像保存在mssql數據庫中為varbinary(max),無需進行轉換

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM