XML 分析器错误:未定义实体

2022-08-30 13:09:44

我已经搜索了这个问题的stackoverflow,并确实找到了一些主题,但我觉得在这个问题上没有一个可靠的答案。

我有一个用户提交的表单,字段的值存储在 XML 文件中。XML 设置为使用 UTF-8 进行编码。

用户时不时地会从某个地方复制/粘贴文本,这就是我得到“实体未定义错误”的时候。

我意识到XML只支持少数几个实体,除此之外的任何东西都是无法识别的 - 因此解析器错误。

根据我收集到的信息,我看到了几个选项:

  1. 我可以找到并替换所有空间,并将它们与实际空间交换。  
  2. 我可以将有问题的代码放在 CDATA 部分中。
  3. 我可以在 XML 文件中包含这些实体。

我对XML文件所做的是,用户可以将内容输入到表单中,它存储在XML文件中,然后该内容在网页上显示为XHTML(使用SimpleXML解析)。

在这三个选项中,或者我不知道的任何其他选项中,处理这些实体的最佳方式是什么?

谢谢,瑞安

更新

我要感谢大家的大力反馈。我实际上确定了导致我的实体错误的原因。所有的建议都让我更深入地研究了它!

一些文本框是普通的旧文本框,但我的文本区域使用TinyMCE进行了增强。事实证明,在仔细观察时,PHP警告总是引用TinyMCE增强文本区域的数据。后来我在PC上注意到所有字符都被取出(因为它无法读取它们),但是在MAC上,您可以看到引用该字符的unicode编号的小方框。它首先出现在MAC上的正方形的原因是因为我使用utf8_encode来编码不在UTF中的数据,以防止其他解析错误(这也与TinyMCE有关)。

所有这一切的解决方案非常简单:

我在我的tinyMCE.init中添加了这行。现在,所有角色都以他们应该的方式出现。entity_encoding : "utf-8"

我想我唯一不明白的是为什么字符在放入文本框时仍然显示,因为没有任何东西将它们转换为UTF,但是对于TinyMCE来说,这是一个问题。


答案 1

我同意这纯粹是一个编码问题。在PHP中,这就是我解决这个问题的方法:

  1. 在将 html 片段传递给构造函数之前,我使用 .SimpleXMLElementhtml_entity_decode

  2. 然后使用 进一步对其进行编码。utf8_encode()

$headerDoc = '<temp>' . utf8_encode(html_entity_decode($headerFragment)) . '</temp>'; 
$xmlHeader = new SimpleXMLElement($headerDoc);

现在,上面的代码不会引发任何未定义的实体错误。


答案 2

您可以对文本进行 HTML 解析,并仅使用相应的数字实体(如:→)重新转义文本。无论如何,仅使用未经清理的用户输入是一个坏主意。&nbsp;&#160;

XML 中允许使用所有数字实体,只有从 HTML 中已知的命名实体不起作用(、 、 、 、 、 除外)。&amp;&quot;&lt;&gt;&apos;

但是大多数时候,您只需将实际字符(→)写入XML文件,因此根本不需要使用实体引用。如果您使用DOM API来操作您的XML(您应该这样做!),这是您最安全的选择。&ouml;ö

最后(这是懒惰的开发人员解决方案),您可以构建一个损坏的XML文件(即格式不正确,存在实体错误),然后通过整洁进行必要的修复。这可能有效或失败,这取决于整个事情的破碎程度。根据我的经验,整洁是非常聪明的,可以让你逃脱很多。


推荐