我正在尝试使用网址https://data.norge.no/data/bibsys/bibsys-bibliotekbase-bibliografiske-data-sru上的通过URL(SRU)进行搜索和检索来从库api加载搜索结果
如果您看到那里的搜索结果链接,它看起来很像XML,但是当我尝试使用下面的代码使用xml时,它只会返回一个空对象
SimpleXMLElement {#546}
这是怎么回事?
我的laravel项目中的php函数:
public function bokId($bokid) {
$apiUrl = "http://sru.bibsys.no/search/biblio?version=1.2&operation=searchRetrieve&startRecord=1&maximumRecords=10&query=ibsen&recordSchema=marcxchange";
$filename = "bok.xml";
$xmlfile = file_get_contents($apiUrl);
file_put_contents($filename, $xmlfile); // xml file is saved.
$fileXml = simplexml_load_string($xmlfile);
dd($fileXml);
}
如果我这样做:
dd($xmlfile);
让我很困惑,我无法使用任何对象。我现在提供的代码以前运行良好。
答案 0 :(得分:1)
您提供的数据可能已更改格式,但是数据仍然存在,您仍然可以使用它。使用诸如dd()
之类的东西的主要问题是,它不能与SimpleXMLElements一起很好地工作,它倾向于对要查看的数据有自己的想法。
在这种情况下,名称空间是常见问题。但是,如果您看下面的代码,您会发现从特定名称空间获取数据的快速方法,然后您可以像往常一样轻松地进行访问。在这段代码中,我使用->children("srw", true)
来表示获取名称空间srw中的所有子元素(第二个参数表示这是前缀而不是URL)...
$apiUrl = "http://sru.bibsys.no/search/biblio?version=1.2&operation=searchRetrieve&startRecord=1&maximumRecords=10&query=ibsen&recordSchema=marcxchange";
$filename = "bok.xml";
$xmlfile = file_get_contents($apiUrl);
file_put_contents($filename, $xmlfile); // xml file is saved.
$fileXml = simplexml_load_string($xmlfile);
foreach ( $fileXml->children("srw", true)->records->record as $record) {
echo "recordIdentifier=".$record->recordIdentifier.PHP_EOL;
}
这将输出...
recordIdentifier=792012771
recordIdentifier=941956423
recordIdentifier=941956466
recordIdentifier=950546232
recordIdentifier=802109055
recordIdentifier=910941041
recordIdentifier=940589451
recordIdentifier=951721941
recordIdentifier=080703852
recordIdentifier=011800283
由于我不确定要检索哪些数据作为标题,因此我只想展示在有可能的情况下如何获取数据的想法。在此示例中,我使用XPath查找每个<srw:record>
元素并找到<marc:datafield tag="100"...>
元素以及其中的<marc:subfield code="a">
元素。这是使用//marc:datafield[@tag='100']/marc:subfield[@code='a']
完成的。您可能需要将@tag=
的位调整为after的数据字段,并将@code=
的位置调整为after的子字段。
$fileXml = simplexml_load_string($xmlfile);
$fileXml->registerXPathNamespace("marc","info:lc/xmlns/marcxchange-v1");
foreach ( $fileXml->children("srw", true)->records->record as $record) {
echo "recordIdentifier=".$record->recordIdentifier.PHP_EOL;
$data = $record->xpath("//marc:datafield[@tag='100']/marc:subfield[@code='a']");
$subData=$data[0]->children("marc", true);
echo "Data=".(string)$data[0].PHP_EOL;
}