postgresql - 输入不是 UTF-8 编码

标签 postgresql perl dbi mojolicious

我的数据库支持 utf8:

                                   List of databases
   Name    |     Owner     | Encoding |  Collate   |   Ctype    |
-----------+---------------+----------+------------+------------+
 tucha     | tucha_cleaner | UTF8     | en_US.utf8 | en_US.utf8 | 

当我连接到它时,我设置了client_encoding:

my $hm_schema = App::Schema->connect( $dsn, $user, $pass, {
        AutoCommit => 1,
        RaiseError => 1,
        client_encoding => 'UTF8',
    }
);

据我所知,返回值是 UTF8:

DBG>$value
["Нд", "Пн", "Вт", "Ср", "Чт", "Пт", "Сб"]

DBG>use Devel::Peek

DBG>Devel::Peek::Dump $value
SV = PVMG(0xfe41c20) at 0xfe079b0
  REFCNT = 1
  FLAGS = (POK,IsCOW,pPOK,UTF8)
  IV = 0
  NV = 0
  PV = 0xfe27550 "[\"\320\235\320\264\", \"\320\237\320\275\", \"\320\222\321\202\", \"\320\241\321\200\", \"\320\247\321\202\", \"\320\237\321\202\", \"\320\241\320\261\"]"\0 [UTF8 "["\x{41d}\x{434}", "\x{41f}\x{43d}", "\x{412}\x{442}", "\x{421}\x{440}", "\x{427}\x{442}", "\x{41f}\x{442}", "\x{421}\x{431}"]"]
  CUR = 56
  LEN = 58
  COW_REFCNT = 4
undef

但是当我尝试通过 Mojo::JSON 中的 decode_json 解码该字符串时,我得到了错误:

DBG> decode_json $value
ERROR: Input is not UTF-8 encoded at ...

为什么会出现该错误以及如何解决?

最佳答案

字符串的前 5 个字符如下(十六进制):

5B 22 41D 434 22

UTF-8 等字符编码是使用字节表示代码点的方法,其中两个字符不是字节,因此您的字符串不可能使用 UTF-8 进行 JSON 编码。

看来您有一个已解码的字符串。字符编码已被删除以生成一串 Unicode 代码点。如果那是你所拥有的,请替换

JSON::decode_json($json_utf8)
JSON::MaybeXS::decode_json($json_utf8)
JSON::PP::decode_json($json_utf8)
JSON::XS::decode_json($json_utf8)
Cpanel::JSON::XS::decode_json($json_utf8)

JSON->new->decode($json_ucp)    -or-    JSON::from_json($json_ucp)
JSON::MaybeXS->new->decode($json_ucp)
JSON::PP->new->decode($json_ucp)
JSON::XS->new->decode($json_ucp)
Cpanel::JSON::XS->new->decode($json_ucp)

顺便说一下,除非您想查看 Perl 内部结构,否则 Devel::Peek 不是完成这项工作的正确工具。您应该改用 Data::Dumper 或类似工具。

use Data::Dumper qw( Dumper );
# This is the same string as in the OP.
my $value = qq{["\x{41d}\x{434}", "\x{41f}\x{43d}", "\x{412}\x{442}", "\x{421}\x{440}", "\x{427}\x{442}", "\x{41f}\x{442}", "\x{421}\x{431}"]};
local $Data::Dumper::Useqq = 1;
print(Dumper($value));

输出:

$VAR1 = "[\"\x{41d}\x{434}\", \"\x{41f}\x{43d}\", \"\x{412}\x{442}\", \"\x{421}\x{440}\", \"\x{427}\x{442}\", \"\x{41f}\x{442}\", \"\x{421}\x{431}\"]";

关于postgresql - 输入不是 UTF-8 编码,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/51619258/

相关文章:

javascript - 尝试使用 ErrorDocument 处理请求时遇到 500 Internal Server Error 错误

Perl 的 SQLite3 : {NAME} not working?

ruby - 为什么我的简单 Ruby SQLite3 示例失败了?

postgresql - 如果这些行中的任何一行在另一列中包含某个值,我如何从 postgres 表中删除在一列中具有相同值的行?

postgresql - PostgreSQL和Golang之间的数据类型

ruby-on-rails - Rails 数据库,为什么在开发和生产中使用相同的 DBMS?

perl - ListUtil.c : loadable library and perl binaries are mismatched (got handshake key 0xdb00080, 需要 0xdb80080)

linux - 从名称包含特定字符串的目录树中删除文件的最快方法

MySQL "command out of sync"

sql - 转置 PostgreSQL 表或聚合函数什么都不做