Erlang:奇怪的输出格式

Erlang: strange output formatting

Windows 7 x64,Erlang-OTP 17。 我写了这样的简单模块:

-module (somequery).
-export ([fbquery/2]).

fbquery(P1,P2) ->  
    inets:start(),
    ssl:start(),
    token = "78a8shd67tyajsndweiu03hr83h19j",
    Encoded = {"Authorization","Basic " ++ base64:encode_to_string(lists:append([token,":",""]))},
    ContentType = "application/xml",
    Headers = [Encoded, {"Content-Type",ContentType}],
    Options = [{body_format,binary}],
    {ok, File}=file:read_file(P1),
    Res = httpc:request(post, {"https://datapi.com/api/xml4-8", Headers, ContentType, File}, [], Options),
    file:write_file(P2, io_lib:fwrite("~p.\n", [Res])).

它在交互和编译中都有效,Res term 显示数据

59> Res.                                                                                                     
{ok,{{"HTTP/1.1",200,"OK"},
     [{"connection","keep-alive"},
      {"date","Tue, 05 May 2015 10:58:53 GMT"},
      {"server","nginx"},
      {"vary","Accept-Encoding"},
      {"content-length","5508"},
      {"content-type","application/xml; charset=utf-8"},
      {"x-frame-options","SAMEORIGIN"},
      {"p3p",
       "CP=\"To see our privacy policy, go here: http://www.datapi.com/policies/privacy\""},
      {"strict-transport-security","max-age=31536000"}],
     <<"<?xml version=\"1.0\" encoding=\"utf-8\"?>\n<response xmlns=\"http://www.datapi.com/api/\" status=\""...>>}}

但在输出文件(P2 参数)中我看到了这个

{ok,{{"HTTP/1.1",200,"OK"},
     [{"connection","keep-alive"},
      {"date","Tue, 05 May 2015 10:58:53 GMT"},
      {"server","nginx"},
      {"vary","Accept-Encoding"},
      {"content-length","5508"},
      {"content-type","application/xml; charset=utf-8"},
      {"x-frame-options","SAMEORIGIN"},
      {"p3p",
       "CP=\"To see our privacy policy, go here: http://www.datapi.com/policies/privacy\""},
      {"strict-transport-security","max-age=31536000"}],
     <<60,63,120,109,108,32,118,101,114,115,105,111,110,61,34,49,46,48,34,32,
       101,110,99,111,100,105,110,103,61,34,117,116,102,45,56,34,63,62,10,60,
       114,101,115,112,111,110,115,101,32,120,109,108,110,115,61,34,104,116,
       116,112,58,47 ... MORE NUMBERS HERE ....101,62,10>>}}.

真奇怪,我记得在完全交互模式下我没有遇到过这样的问题。有什么建议吗?


UPD:这很有趣,但只有当接收到 XML 包含非 ASCII(非拉丁语?)字符时才会出现问题。在其他情况下,文件中的所有 XML 都是正确的。

那是因为运行时不确定您的终端是否可以显示非 ASCII unicode。所有字符串都只是整数列表,所有二进制文件都只是分成 8 位字节的长字符串。因此,您看到的数字 您想要查看的数据,只是它的原始形式。

要以您想要的方式显示它,请尝试使用像 io:format/2 这样的显示函数,并使用 ~tp 替换而不是 ~p 替换。在你的情况下,写入文件,你可能需要做:

write(Filename, UTF8_data) ->
    file:write_file(Filename, unicode:characters_to_binary(UTF8_data, utf8)).

read(Filename) ->
    case file:read_file(Filename) of
        {ok, Data} -> {ok, unicode:characters_to_list(Data, utf8)};
        Other      -> Other
    end.

请参阅文档中的 Using Unicode in Erlang。它比以前好多了,但仍然有点烦人(所以用一些函数包装它,比如上面的 read/1 和 write/2)。

就是说... Windows 在涉及 unicode(和一般编码)时有其独特的愚蠢形式,我的大部分 Erlang 经验都是在 Linux 和 BSD 上——我在 Windows 上做的唯一事情是 Wx 中的客户端 GUI。