【问题标题】:Ignore DOCTYPE .dtd, but .dtd file must still exist忽略 DOCTYPE .dtd,但 .dtd 文件必须仍然存在
【发布时间】:2011-04-23 02:23:45
【问题描述】:

我有一个处理 HTTP 请求的 Web 服务。它接收到的文档有一个嵌入的 DOCTYPE,它指定了一个 .dtd 文件。我希望在更新的设备连接到我的服务时使用更新的 XML 模式验证文件。

我可以成功忽略 .dtd 文件中进行的验证,但 .dtd 文件必须存在于我的本地硬盘上。我想删除这些过时的文件,还没有找到办法。

我正在处理的示例 XML 文档:

<?xml version="1.0" encoding="us-ascii" standalone="no"?>
<!DOCTYPE SomeMessage SYSTEM "SomeMessage.dtd">
<SomeMessage>data</SomeMessage>

我用来打开文档的函数:

private void LoadXmlDoc(XmlTextReader myXmlTextReader)
{
    XmlReaderSettings readerSettings = new XmlReaderSettings();
    readerSettings.ValidationType = ValidationType.Schema;
    readerSettings.Schemas.Add(null, MyGoodSchemaFile);
    readerSettings.DtdProcessing = DtdProcessing.Ignore;
    readerSettings.XmlResolver = null; // Added as a test.

    readerSettings.ValidationEventHandler += ValidationEventHandle;
    XmlReader myXmlReader = XmlReader.Create(myXmlTextReader, readerSettings);

    XmlDocument myXmlDocument = new XmlDocument();
    myXmlDocument.XmlResolver = null; // Added as a test.
    myXmlDocument.Load(myXmlReader); // Exception thrown here!
}

捕获的异常:

System.IO.FileNotFoundException:找不到文件“c:\windows\system32\inetsrv\SomeMessage.dtd”。 文件名:'c:\windows\system32\inetsrv\SomeMessage.dtd' 在 System.IO.__Error.WinIOError(Int32 错误代码,字符串可能全路径)

未使用 SomeMessage.dtd 文件的内容——如我所愿,它被忽略。但是虚拟文件“c:\windows\system32\inetsrv\SomeMessage.dtd”必须存在,否则会抛出异常。

我在 Windows 7 上运行,使用 Visual Studio 2010 和 .Net 4.0

如何忽略嵌入的 .dtd 并且不需要在我的计算机上安装虚拟 .dtd 文件?

【问题讨论】:

  • 这是什么网络服务?自制还是 ASP.NET Web 服务 (.asmx)?是在寻找 DTD 的 Web 服务客户端吗?
  • 这是一个 .aspx 服务,带有一个 .aspx.cs C# 文件。不过,我认为这并不重要。我认为上面的代码 sn-p 读取的任何 XML 文档都具有带有 .dtd 行的 DOCTYPE,无论您在哪里执行它都会出现错误。

标签: c# xml dtd


【解决方案1】:

解决方法是将底层 XmlTextReader 的 XmlResolver 设置为 null。更改 XmlReaderSettings.XmlResolver=null 没有帮助,设置 XmlDocument.XmlResolver=null 也没有

这里是修正后的函数:

private void LoadXmlDoc(XmlTextReader myXmlTextReader)
{
    // The next line is the fix!!!
    myXmlTextReader.XmlResolver = null;  // Don't require file in system32\inetsrv

    XmlReaderSettings readerSettings = new XmlReaderSettings();
    readerSettings.ValidationType = ValidationType.Schema;
    readerSettings.Schemas.Add(null, MyGoodSchemaFile);
    readerSettings.DtdProcessing = DtdProcessing.Ignore;
    readerSettings.XmlResolver = null; // Doesn't help

    readerSettings.ValidationEventHandler += ValidationEventHandle;
    XmlReader myXmlReader = XmlReader.Create(myXmlTextReader, readerSettings);

    XmlDocument myXmlDocument = new XmlDocument();
    myXmlDocument.XmlResolver = null; // Doesn't help
    myXmlDocument.Load(myXmlReader); // Load doc, no .dtd required on local disk
}

【讨论】:

  • 你救了我的命!我开发了一个在基于表单的情况下完美运行的 dll。但在将其附加到 .NET Web 应用程序后,它在 dtd 上崩溃了。因此,只有在 Web 应用程序中使用时才需要这样做。谢谢!
猜你喜欢
  • 2010-10-09
  • 1970-01-01
  • 2010-09-14
  • 2023-03-22
  • 1970-01-01
  • 2021-08-20
  • 1970-01-01
相关资源
最近更新 更多