是否有一种简单的方法可以使用SimpleXML xpath解析标记名称中包含冒号的标记?
示例:
<v12:ProcessShipmentResponse>SUCCESS</v12:ProcessShipmentResponse>
这是我用来解析非命名空间但用命名空间标记打破的标记的代码。
$xml = simplexml_load_string($responseXMLL, NULL, NULL, 'http://schemas.xmlsoap.org/soap/envelope/');
foreach ($xml->xpath('soapenv:Body') as $body) {
$custInfoArr['status'] = (string) $body->v12:ProcessShipmentReply->v12:HighestSeverity;
$custInfoArr['trackingCode'] = (string) $body->v12:ProcessShipmentReply->v12:CompletedShipmentDetail->v12:CompletedPackageDetails->v12:TrackingIds->v12:TrackingNumber;
$custInfoArr['labelCode'] = (string) $body->v12:ProcessShipmentReply->v12:CompletedShipmentDetail->v12:CompletedPackageDetails->v12:Label->v12:Parts->v12:Image;
}
答案 0 :(得分:0)
看看this。
public bool SimpleXMLElement::registerXPathNamespace(string $prefix,string $ns);
来自php手册:
为下一个XPath查询创建前缀/ ns上下文。特别是, 如果给定XML文档的提供者改变了,那么这很有用 名称空间前缀。 registerXPathNamespace将为其创建前缀 关联的命名空间,允许一个人访问其中的节点 名称空间,无需更改代码以允许新的 前提是由提供商决定的。
答案 1 :(得分:0)
以前曾多次询问过这个问题。这些不是“冒号标签”,它们是XML命名空间,需要在任何解析器中进行特殊处理。
对于SimpleXML,这是由->children()
和->attributes()
方法提供的。
您可以依赖别名/前缀不改变(不保证这一点,因为XML文档的“语义”不会改变)并使用true
作为第二个参数(在您的情况下) $body->children('v12', TRUE)
)或为名称空间URI设置一个常量(保证不会更改)并传递(在您的情况下为define('XMLNS_FEDEX_V12', 'http://fedex.com/ws/ship/v12'); /* ... */ $body->children(XMLNS_FEDEX_V12)
)。
答案 2 :(得分:-1)
需要注册这样的名称空间。这是一个工作示例,以防有人需要它。
$xml = simplexml_load_string($result, NULL, NULL, 'http://schemas.xmlsoap.org/soap/envelope/');
$xml->registerXPathNamespace('env', 'http://schemas.xmlsoap.org/soap/envelope/');
$xml->registerXPathNamespace('v12', 'http://fedex.com/ws/ship/v12');
$bodies = $xml->xpath('env:Body');
foreach($bodies as $body){
$reply = $body->children('v12', TRUE)->ProcessShipmentReply;
$custInfoArr['status'] = (string) $reply->HighestSeverity;
$custInfoArr['trackingCode'] = (string) $reply->CompletedShipmentDetail->CompletedPackageDetails->TrackingIds->TrackingNumber;
$custInfoArr['labelCode'] = (string) $reply->CompletedShipmentDetail->CompletedPackageDetails->Label->Parts->Image;
}