未定义命名空间前缀。如何自动定义/忽略错误?

时间:2021-06-29 10:20:59

I made a PHP script which parses XML file and when I try to parse it, an error comes out:

我创建了一个解析XML文件的PHP脚本,当我尝试解析它时,出现错误:

2: DOMDocument::load(): Namespace prefix edf for represent on info is not defined in /users/zzz/testing/meta.xml, line: 2

2:DOMDocument :: load():用于表示信息的命名空间前缀edf未在/users/zzz/testing/meta.xml中定义,第2行:

I've been searching for a fix but I couldn't find any, so I'm posting here. As you can see I'm using DOMDocument class.

我一直在寻找修复,但我找不到,所以我在这里发帖。正如您所看到的,我正在使用DOMDocument类。

My code for parsing XML looks like:

我解析XML的代码如下:

$dom = new DOMDocument();
$metaXML = $dom->load($path."/meta.xml");

The path and all is correct, I'm sure. When I remove the prefix, it works fine. The XML looks like:

我确定,路径和所有都是正确的。当我删除前缀,它工作正常。 XML看起来像:

<meta>
    <info gamemodes="race" type="map" edf:represent="false"></info>
</meta>

The edf:represent="false" causes an error. I don't want to manually delete edf namespace prefix, because this is not the only XML file I want to parse. There are hundreds of them and the number is rising.

edf:represent =“false”会导致错误。我不想手动删除edf名称空间前缀,因为这不是我想要解析的唯一XML文件。有数百个,而且数量正在上升。

So, my question is, how can I ignore this error (only for XML namespace thing) or how can I define/remove namespace prefix via DOMDocument class?

所以,我的问题是,如何忽略此错误(仅适用于XML命名空间)或如何通过DOMDocument类定义/删除命名空间前缀?

2 个解决方案

#1


3  

This is an warning not an error. So the XML still can be used, but it is broken. The best solution would be to repair the XML - defining the namespace.

这是一个警告而不是错误。所以XML仍然可以使用,但它已被破坏。最好的解决方案是修复XML - 定义命名空间。

Defining the namesapce will not work automatically. The namespace prefix is only an alias the actual namespace is the value of the xmlns attribute. The alias is only valid for the element and its descendants. The script/application that generates the XML has to be repaired so that it adds the namespace definition.

定义namesapce不会自动运行。名称空间前缀只是一个别名,实际名称空间是xmlns属性的值。别名仅对元素及其后代有效。必须修复生成XML的脚本/应用程序,以便添加命名空间定义。

<meta xmlns:edf="urn:example">
    <info gamemodes="race" type="map" edf:represent="false"></info>
</meta>

The parser will resolve the namespace. You can read "edf:represent" as "{urn:example}represent".

解析器将解析命名空间。您可以将“edf:represent”视为“{urn:example}表示”。

However you can block the parsing errors and warnings using libxml_use_internal_errors().

但是,您可以使用libxml_use_internal_errors()阻止解析错误和警告。

$xml = <<<'XML'
<meta>
    <info gamemodes="race" type="map" edf:represent="false"></info>
</meta>
XML;

libxml_use_internal_errors(TRUE);

$dom = new DOMDocument();
$dom->loadXml($xml);

echo $dom->saveXml();

Output:

<?xml version="1.0"?>
<meta>
    <info gamemodes="race" type="map" represent="false"/>
</meta>

With libxml_get_errors() you can implement your own error handling.

使用libxml_get_errors(),您可以实现自己的错误处理。

As you can see in the output, the XML parser removed the namespace prefix. This means that "represent" is now an attribute without an namespace, it changed its identity. Be really careful with that, represent and {urn:example}represent are two different names, you loose relevant context information.

正如您在输出中看到的那样,XML解析器删除了名称空间前缀。这意味着“表示”现在是没有命名空间的属性,它改变了它的身份。要非常小心,代表和{urn:example}代表两个不同的名称,你松开相关的上下文信息。

#2


2  

The XML file itself is not well-formed because it uses an undeclared namespace prefix. Either remove the undeclared namespace prefix, or declare it, e.g:

XML文件本身格式不正确,因为它使用未声明的命名空间前缀。删除未声明的命名空间前缀,或声明它,例如:

<meta xmlns:edf="http://www.example.com/">
    <info gamemodes="race" type="map" edf:represent="false"></info>
</meta>

Update: You cannot perform this operation using an XML library because the XML is not well-formed. You have to either do it manually or operate on the file programmatically as text, not XML. Once you make your text be well-formed XML, you'll be able to use standard XML libraries to process it.

更新:您无法使用XML库执行此操作,因为XML格式不正确。您必须手动执行此操作或以编程方式将文件作为文本操作,而不是XML。一旦使文本成为格式良好的XML,您就可以使用标准XML库来处理它。

Here's a programmatic, text-based edit suggestion by @Daniel:

这是@Daniel的程序化,基于文本的编辑建议:


If you need to correct this lack of formatting across many files, consider using a tool like 'sed' to replace your meta tag with the corrected version. For example, to replace all instances of <meta with <meta xmlns:edf="http://www.example.com/", within a folder. You could use this command

如果您需要纠正许多文件中缺少格式化的问题,请考虑使用“sed”之类的工具将您的元标记替换为更正后的版本。例如,要在文件夹中替换

sed -i -- 's/<meta/<meta\ xmlns\:edf\=\"http\:\/\/www.example.com\/\"/g' *

See https://unix.stackexchange.com/questions/112023/how-can-i-replace-a-string-in-a-files for more infomation on how to use sed.

有关如何使用sed的更多信息,请参阅https://unix.stackexchange.com/questions/112023/how-can-i-replace-a-string-in-a-files。


Well-formed XML should always be parsed using an XML parser, but sometimes a quick-and-dirty fix such as the above can help get us there.

格式良好的XML应始终使用XML解析器进行解析,但有时如上所述的快速而肮脏的修复可以帮助我们实现目标。

#1


3  

This is an warning not an error. So the XML still can be used, but it is broken. The best solution would be to repair the XML - defining the namespace.

这是一个警告而不是错误。所以XML仍然可以使用,但它已被破坏。最好的解决方案是修复XML - 定义命名空间。

Defining the namesapce will not work automatically. The namespace prefix is only an alias the actual namespace is the value of the xmlns attribute. The alias is only valid for the element and its descendants. The script/application that generates the XML has to be repaired so that it adds the namespace definition.

定义namesapce不会自动运行。名称空间前缀只是一个别名,实际名称空间是xmlns属性的值。别名仅对元素及其后代有效。必须修复生成XML的脚本/应用程序,以便添加命名空间定义。

<meta xmlns:edf="urn:example">
    <info gamemodes="race" type="map" edf:represent="false"></info>
</meta>

The parser will resolve the namespace. You can read "edf:represent" as "{urn:example}represent".

解析器将解析命名空间。您可以将“edf:represent”视为“{urn:example}表示”。

However you can block the parsing errors and warnings using libxml_use_internal_errors().

但是,您可以使用libxml_use_internal_errors()阻止解析错误和警告。

$xml = <<<'XML'
<meta>
    <info gamemodes="race" type="map" edf:represent="false"></info>
</meta>
XML;

libxml_use_internal_errors(TRUE);

$dom = new DOMDocument();
$dom->loadXml($xml);

echo $dom->saveXml();

Output:

<?xml version="1.0"?>
<meta>
    <info gamemodes="race" type="map" represent="false"/>
</meta>

With libxml_get_errors() you can implement your own error handling.

使用libxml_get_errors(),您可以实现自己的错误处理。

As you can see in the output, the XML parser removed the namespace prefix. This means that "represent" is now an attribute without an namespace, it changed its identity. Be really careful with that, represent and {urn:example}represent are two different names, you loose relevant context information.

正如您在输出中看到的那样,XML解析器删除了名称空间前缀。这意味着“表示”现在是没有命名空间的属性,它改变了它的身份。要非常小心,代表和{urn:example}代表两个不同的名称,你松开相关的上下文信息。

#2


2  

The XML file itself is not well-formed because it uses an undeclared namespace prefix. Either remove the undeclared namespace prefix, or declare it, e.g:

XML文件本身格式不正确,因为它使用未声明的命名空间前缀。删除未声明的命名空间前缀,或声明它,例如:

<meta xmlns:edf="http://www.example.com/">
    <info gamemodes="race" type="map" edf:represent="false"></info>
</meta>

Update: You cannot perform this operation using an XML library because the XML is not well-formed. You have to either do it manually or operate on the file programmatically as text, not XML. Once you make your text be well-formed XML, you'll be able to use standard XML libraries to process it.

更新:您无法使用XML库执行此操作,因为XML格式不正确。您必须手动执行此操作或以编程方式将文件作为文本操作,而不是XML。一旦使文本成为格式良好的XML,您就可以使用标准XML库来处理它。

Here's a programmatic, text-based edit suggestion by @Daniel:

这是@Daniel的程序化,基于文本的编辑建议:


If you need to correct this lack of formatting across many files, consider using a tool like 'sed' to replace your meta tag with the corrected version. For example, to replace all instances of <meta with <meta xmlns:edf="http://www.example.com/", within a folder. You could use this command

如果您需要纠正许多文件中缺少格式化的问题,请考虑使用“sed”之类的工具将您的元标记替换为更正后的版本。例如,要在文件夹中替换

sed -i -- 's/<meta/<meta\ xmlns\:edf\=\"http\:\/\/www.example.com\/\"/g' *

See https://unix.stackexchange.com/questions/112023/how-can-i-replace-a-string-in-a-files for more infomation on how to use sed.

有关如何使用sed的更多信息,请参阅https://unix.stackexchange.com/questions/112023/how-can-i-replace-a-string-in-a-files。


Well-formed XML should always be parsed using an XML parser, but sometimes a quick-and-dirty fix such as the above can help get us there.

格式良好的XML应始终使用XML解析器进行解析,但有时如上所述的快速而肮脏的修复可以帮助我们实现目标。