http://www.boxcounter.com/?action=show&id=98
这个星期在琢磨BT下载,用的是一套开源的库-libtorrent,接口不错,帮助文档也挺详细,照着文档和测试例子很快就封好了我需要的功能,但是也遇到了很郁闷的问题:中文支持。
LibTorrent为了支持多平台,使用了Boost做为基础,Boost的UNICODE支持做的挺好的,LibTorrent内部也用宏做了Unicode开关,但是又有很多地方直接写死成std::string .....
说回我遇到的问题:
当我的模块存放在包含中文字符的路径下时,新创建的下载目录(由LibTorrent内部进行创建)是乱码。在纯英文路径下,则工作正常。
分析:
.torrent文件里存放的很多信息是以UTF8编码的方式来存储的,LibTorrent进行解析的时候,将这些UTF8编码存放到了storage::m_files,这个成员的类型是std::string 里,然后在需要的时候转换回wchar_t(具体的可以参考 src/storage.cpp 中的safe_convert(...) 函数相关的操作。
我遇到的BUG就是出在这个转换上,我传入的存放路径包含中文字符,LibTorrent从.torrent中读取相对文件路径是UTF8,LibTorrent将这两块进行拼接,然后再调用safe_convert(...)进行转换,这个函数一看到gbk(gb2312?)和UTF8的组合,傻眼了,于是,一个完美的乱码目录就此诞生。
方案一,将我传入的存放路径和.torrent中的相对文件路径分别进行转换,然后再进行拼接。(此笨办法由鄙人设计~,请勿鄙视)
方案二:在源头进行修改,当LibTorrent读取、解析.torrent文件中包含的文件相对路径时(src/file_storage.cpp文件中),进行转换(UTF8 -> gb????)。(目前我的模块使用的方法,一次性解决问题,由黄师父提出)。
刚看了最新的0.14.5版本,该问题仍然存在,希望它能早日全面支持UNICODE。这篇文章专门打了标签,希望能给遇到同样问题的朋友一些帮助 :)
搜索相关资料时,看到不少人都遇到这个问题,有人提出修改safe_convert,并提供了代码,我试过了,对于混合编码的转换无效。这种方法的思路是很好的,也是一次性解决了问题,只是我对不同codepage 的转换不熟,试了半天也没试出个行得通的办法~~~
最后严重感谢黄师父,陪我熬到3点解决了这个问题,赐予我轻松愉快的周末~