【问题标题】:Delphi - Can TXMLDocument be configured to ignore incorrect DTD entities?Delphi - 可以将 TXMLDocument 配置为忽略不正确的 DTD 实体吗?
【发布时间】:2017-07-07 01:09:32
【问题描述】:

我正在使用 RAD Studio XE7 编写 Delphi 代码。在我的一个项目中,我需要解析几个 SVG 文件以在屏幕上绘制它们的内容。为此,我使用 TXMLDocument 解析器。

我的一个源 SVG 包含以下 XML 数据:

<?xml version="1.0" encoding="utf-8"?>
<!-- Generator: Adobe Illustrator 17.0.1, SVG Export Plug-In . SVG Version: 6.00 Build 0)  -->
<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd">
<svg version="1.1" id="Calque_1" xmlns:x="&ns_extend;" xmlns:i="&ns_ai;" xmlns:graph="&ns_graphs;"
 xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px" width="32px" height="32px"
 viewBox="0 0 32 32" enable-background="new 0 0 32 32" xml:space="preserve">
<metadata>
    <sfw  xmlns="&ns_sfw;">
        <slices></slices>
        <sliceSourceBounds  height="21.334" width="32" bottomLeftOrigin="true" y="1.833" x="-4.501"></sliceSourceBounds>
    </sfw>
</metadata>
<path fill="#29ABE2" d="M4,8h24v13.333h2.667v-16H1.334v16h2.667L4,8L4,8z M21.333,22.667c-0.256,0.536-1.527,0.967-2.667,1.181V24
h-5.333v-0.152c-1.14-0.215-2.411-0.645-2.667-1.181H-0.001V24c0,1.467,4,2.667,4,2.667h24c0,0,4-1.2,4-2.667v-1.333H21.333
L21.333,22.667z M26.667,25.333h-1.333V24h1.333V25.333z"/>
</svg>

我知道上述 XML 的内容不完整,格式良好的 SVG 应该包含这个 XML 数据:

<?xml version="1.0" encoding="utf-8"?>
<!-- Generator: Adobe Illustrator 17.0.1, SVG Export Plug-In . SVG Version: 6.00 Build 0)  -->
<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd" [
    <!ENTITY ns_extend "http://ns.adobe.com/Extensibility/1.0/">
    <!ENTITY ns_ai "http://ns.adobe.com/AdobeIllustrator/10.0/">
    <!ENTITY ns_graphs "http://ns.adobe.com/Graphs/1.0/">
    <!ENTITY ns_vars "http://ns.adobe.com/Variables/1.0/">
    <!ENTITY ns_imrep "http://ns.adobe.com/ImageReplacement/1.0/">
    <!ENTITY ns_sfw "http://ns.adobe.com/SaveForWeb/1.0/">
    <!ENTITY ns_custom "http://ns.adobe.com/GenericCustomNamespace/1.0/">
    <!ENTITY ns_adobe_xpath "http://ns.adobe.com/XPath/1.0/">
]>
<svg version="1.1" id="Calque_1" xmlns:x="&ns_extend;" xmlns:i="&ns_ai;" xmlns:graph="&ns_graphs;"
 xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px" width="32px" height="32px"
 viewBox="0 0 32 32" enable-background="new 0 0 32 32" xml:space="preserve">
<metadata>
    <sfw  xmlns="&ns_sfw;">
        <slices></slices>
        <sliceSourceBounds  height="21.334" width="32" bottomLeftOrigin="true" y="1.833" x="-4.501"></sliceSourceBounds>
    </sfw>
</metadata>
<path fill="#29ABE2" d="M4,8h24v13.333h2.667v-16H1.334v16h2.667L4,8L4,8z M21.333,22.667c-0.256,0.536-1.527,0.967-2.667,1.181V24
h-5.333v-0.152c-1.14-0.215-2.411-0.645-2.667-1.181H-0.001V24c0,1.467,4,2.667,4,2.667h24c0,0,4-1.2,4-2.667v-1.333H21.333
L21.333,22.667z M26.667,25.333h-1.333V24h1.333V25.333z"/>
</svg>

但是,就我而言,DTD 实体是无关紧要的(我对它们什么都不做),只有 svg 标签中的部分让我感兴趣。但是,如果我尝试加载这样的 XML,TXMLDocument 解析器会引发“对未定义实体 'ns_extend' 的引用”异常,并拒绝加载 SVG。

所以我的问题是,有没有办法通知 TXMLDocument 解析器如果 DTD 实体损坏应该被简单地忽略,并强制解析器继续静默读取文档?或者这样做的唯一方法是预处理 XML,并检测和删除此类损坏?

(注意:如果可能的话,我想避免预先处理。SVG 可能来自任何地方,其中一些可能包含小的或严重的损坏,我希望尽可能以最通用的方式处理最大值。开始为所有可能的特殊情况添加特殊规则是一种痛苦的方式。如果 TXMLDocument 解析器能够忽略这种错误,我会非常喜欢。)

【问题讨论】:

  • 在解析之前添加所需的实体引用怎么样?
  • 如果可能的话,我想避免预先处理。 SVG 可能来自任何地方,其中一些可能包含小的或严重的损坏,我希望尽可能以最通用的方式处理最大值。开始为所有可能的特殊情况添加特殊规则是一种痛苦的方式。如果 TXMLDocument 解析器能够忽略这种错误,我会非常喜欢。
  • XML 解析是一项严格的操作,AFIAK 没有选项可以忽略文档类型和命名空间。您将不得不预处理 XML...
  • 好的,所以我会先检查我的来源。谢谢

标签: delphi exception entity dtd txmldocument


【解决方案1】:

使用 TXMLDocument 他们无法忽略 DOCTYPE,唯一的方法是在使用 TXMLDocument 解析之前编辑 xml 文件并手动从中删除

<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd" [
    <!ENTITY ns_extend "http://ns.adobe.com/Extensibility/1.0/">
    <!ENTITY ns_ai "http://ns.adobe.com/AdobeIllustrator/10.0/">
    <!ENTITY ns_graphs "http://ns.adobe.com/Graphs/1.0/">
    <!ENTITY ns_vars "http://ns.adobe.com/Variables/1.0/">
    <!ENTITY ns_imrep "http://ns.adobe.com/ImageReplacement/1.0/">
    <!ENTITY ns_sfw "http://ns.adobe.com/SaveForWeb/1.0/">
    <!ENTITY ns_custom "http://ns.adobe.com/GenericCustomNamespace/1.0/">
    <!ENTITY ns_adobe_xpath "http://ns.adobe.com/XPath/1.0/">
]>

然而,它们是与 Txmldocument 完全相似的其他一些 xml 解析器(相同的方法名称和属性名称,完全相似,无需重做代码),其工作速度比 TXMLDocument 快 100 倍,并且使用更少的内存(Txmldocument 是你能找到的越糟糕) .. 并且忽略 DTD :)

【讨论】:

  • 感谢您的回复。您能否提供上面提到的替代解析器的名称?
  • 尝试例如 TalXmlDocument (sourceforge.net/projects/alcinoe),它们是 TxmlDocument 内部的演示,您可以看到自己的 txmldocument 有多糟糕。他们还有很多其他的 xml 解析器,几乎所有的都比 Txmldocument 好
猜你喜欢
  • 2012-08-14
  • 2011-01-16
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2021-09-13
  • 2021-11-22
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多