gpt4 book ai didi

php - 如何将 PHP PDO ODBC 与 SQL Server 和 Unicode 字符一起使用?

转载 作者:搜寻专家 更新时间:2023-10-31 21:29:05 26 4
gpt4 key购买 nike

如果没有一些手动编码,PHP PDO ODBC 似乎无法存储 NVARCHAR 字符 (UTF-16)。这似乎是整个 Internet 上一个非常普遍的“错误”,似乎没有人有明确的解决方案。

如何重现错误

  1. 尝试使用 PDO 插入以下日文字符:こんにちは (意思是你好)
  2. 以下内容将存储在您的数据库中:ã“ã‚“ã«ã¡ã¯
  3. 然后通过 PDO 检索它并在屏幕上打印它,你将得到:こんにちは

这不是很糟糕,但也不是很好。 PHP 可以工作,但是当您有其他不在 PHP 中的应用程序从您的数据库访问该信息时,它们将得到错误的字符串:ã“ã‚“ã«ã¡ã¯ .

理想情况下你会想要 こんにちは无处不在。

症状

PDO 似乎没有任何 NVARCHAR 的概念,也就是使用 16 位编码的字符。事实上,您通过 PDO 传递给 SQL SERVER 或从 SQL SERVER 检索的所有内容都将以 8 位为单位。如何“证明”呢?在这里:

  1. 您从日文字符串开始 こんにちは .

您首先必须知道 PHP 将字符串视为二进制,并且(如果这样设置)它将以 UTF-8 格式存储它们。

所以如果我们看一下 こんにちは 的二进制表示, 你会得到 E38193E38293E381ABE381A1E381AF这也是 SQL SERVER 将为您提供 ã“ã‚“ã«ã¡ã¯ 的二进制表示形式. (取决于你的整理)

  1. 接下来,让我们将其转换为 UTF-16,因为这是 NVARCHAR 的格式。

    $utf16_string = mb_convert_encoding('こんりちは', 'UTF-16LE');

以下将更改 こんにちは 在 PHP 中的二进制表示形式至 533093306B3061306F30这正是 こんにちは 的二进制表示在 SQL SERVER NVARCHAR 中。

  1. 接下来尝试通过 PDO 将其保存在 SQL 中,您将得到以下内容:S0“0k0a0o0

S0“0k0a0o0 的 SQL SERVER 二进制表示在 VARCHAR 中是 533093306B3061306F30这也是 こんにちは 的二进制表示在 NVARCHAR 中。

肮脏的解决方案

您可以使用以下内容通过 PDO ODBC 在 SQL SERVER 中保存和检索 unicode 数据,但它很难看...

  1. 您想将数据转换为与 SQL SERVER NVARCHAR 完全相同的二进制表示形式将存储它

    mb_convert_encoding('こんりちは', 'UTF-16LE');

  2. 您想在 SQL SERVER 端以二进制形式接收它,然后将其转换为 NVARCHAR。

    @binary VARBINARY(40)选择 @string = CONVERT(NVARCHAR(20), @binary);

  3. 此时你有 こんにちは在你的数据库中。要检索它,您需要将其作为二进制文件重新发送给 PHP

  4. 一旦您在 PHP 中获得二进制文件,PHP 就已经将其转换为十六进制字符串...因此,您想将十六进制字符串转换为二进制文件,然后将编码从 utf-16 更改为 utf -8

    $result = mb_convert_encoding(hex2bin($string), 'UTF-8', 'UTF-16LE');

你会带着你的 こんにちは 回来的当您将其回显到您的网页时。

基本上,这就是 SQL 驱动程序应该为我做的,而不是我手动做的。

是我忘记配置了什么还是必须手动配置?

最佳答案

不,我认为你没有忘记配置任何东西。事实上,关于 PHP 和 Microsoft ODBC 驱动程序之间长期存在的“问题”,您的解释是迄今为止我发现的最好的解释。考虑到 PDO_ODBC page,这些问题尤其令人费解。说:

On Windows, PDO_ODBC ... is the recommended driver for connecting to Microsoft SQL Server databases.

但是,在 Windows 上,他们还提供 PDO_SQLSRV实际上确实可以正常工作。

所以看起来 PDO_ODBC“没有任何 NVARCHAR 的概念”,而不是作为一个整体的 PDO。

(如果涉及 Unicode 字符,尝试将 PHP 与 Microsoft Access ODBC 结合使用时会出现类似问题)

结论:PHP 对 ODBC 的支持仍然有些困惑,至少在 Microsoft 数据库方面是这样。

关于php - 如何将 PHP PDO ODBC 与 SQL Server 和 Unicode 字符一起使用?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/32213506/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com