4

我正在使用 cURL 抓取 RSS 提要列表,然后我正在使用 SimpleXML 读取和解析 RSS 数据。然后将排序后的数据插入到 mySQL 数据库中。

但是,作为http://dansays.co.uk/research/MNA/rss.php上的通知,我遇到了几个字符显示不正确的问题。

例子:

âGuitar Hero: Van Halenâ Trailer And Tracklist Available

NV 10/10/09 – Salt Lake City, UT 10/11/09 – Denver, CO 10/13/09 –

在将数据插入数据库之前,我曾尝试在数据上使用 htmlentities 和 htmlspecialchars,但这似乎无助于解决问题。

我怎么可能解决我遇到的这个问题?

感谢您的任何建议。

更新

我已经尝试了 Greg 的建议,但问题仍然存在......

这是我用来在 PDO 中执行 SET NAMES 的代码:

$dbh = new PDO($dbstring, $username, $password); 

$dbh->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION); 

$dbh->query('SET NAMES "utf8"');

在对 simplexml 数据进行排序并插入数据库之前,我对它进行了一些回显,现在我认为这与 cURL 有关...

这是我为 cURL 提供的内容:

$ch = curl_init($url);

curl_setopt($ch, CURLOPT_RETURNTRANSFER, 0);

curl_setopt($ch, CURLOPT_HEADER, 0);

curl_setopt($ch, CURLOPT_ENCODING, 'UTF-8');

$data = curl_exec($ch);

curl_close($ch);

$doc = new SimpleXmlElement($data, LIBXML_NOCDATA);

问题解决了

我必须将 RSS/HTML 页面中的内容字符集设置为“UTF-8”才能解决此问题。我想这不是一个真正的解决方案,因为原始数据中仍然存在字符问题。期待在 PHP6 中对它的适当支持!

4

4 回答 4

3

您的页面以 UTF-8 格式提供,因此我将矛头指向数据库。

确保在任何 SELECT 或 INSERTS 之前连接是 UTF-8 - 在 MySQL 中:

SET NAMES "utf8"
于 2009-08-11T15:06:08.980 回答
3

关于CURLOPT_ENCODING的简短说明:它是Accept-Encoding标头,与字符编码完全不同。支持的接受编码是“identity”、“deflate”和“gzip”。

于 2012-01-03T12:25:27.913 回答
2

像所有调试一样,您首先要隔离问题:

我正在使用 cURL 抓取 RSS 提要列表, - 查看 RSS 提要中出现问题的 xml(提要不止一个,因此某些提要可能是正确的,而某些提要可能是错误的以不同的方式错误)

然后我正在使用 SimpleXML 读取和解析 RSS 数据。- 打印出 SimpleXML 读出的字段 - 是否正常或是否出现问题?

然后将排序后的数据插入到 mySQL 数据库中。- 打印出问题的数据的 hex(field)、length(field) 和 char_length(field)。

编辑

获取提要http://hangout.altsounds.com/external.php?type=RSS2,将其放入验证器http://validator.w3.org/feed/。他们将其内容类型声明为 iso-8859-1,但某些实际内容(例如引号)位于 cp1252 之类的内容中 - 例如,他们使用字节 0x93 来表示左引号 - http:// www.fileformat.info/info/unicode/char/201C/charset_support.htm

令人讨厌的是,这并没有出现在某些工具中 - Firefox 似乎猜测发生了什么并正确显示引号,更重要的是,SimpleXML 将 0x93 转换为 utf8,因此它显示为 0xc293,加剧了问题。

编辑 2

使该提要更正确地读取的一种解决方法是在传递给 Simple XML 之前将“ISO-8859-1”替换为“Windows-1252”。它不会 100% 工作,因为事实证明,提要的某些部分是 UTF8 格式的。

假设您无法让世界上的每个人都更正他们的提要,一般方法是将您需要的任何变通方法隔离到与发出格式错误数据的外部系统的接口,并将纯清晰的 utf8 传递给集线器你的系统。保存原始外部提要的已注明日期的副本,以便将来记住为什么需要解决方法,分离并注释实现解决方法的代码行,以便在外部组织更正其提要时以及何时更正其提要时易于获取和更改(或以不同的方式破坏它),并不时再次检查。不幸的是,您不是按照规范进行编程,而是按照错误的当前状态进行编程,因此没有永久的、干净的解决方案——您能做的最好的事情就是隔离、记录和监控。

于 2009-08-11T16:06:07.050 回答
1

它可能与 XML 序言有关,对于您链接到的特定提要,它看起来像这样:

<?xml version="1.0" encoding="ISO-8859-1" ?>

据我所知,SimpleXML 所基于的 libxml 正在寻找这种东西。我不确定 XML 文件,但我确信它使用 HTML 字符串查找META指定字符集的元素。

尝试剥离 XML 序言(我曾经通过剥离 HTML 标记解决了一个类似的问题)并且在将数据提供给 SimpleXMLElement 之前META不要忘记数据。utf8_encode()

于 2009-08-11T16:50:34.947 回答