我在xml文档(称为result.xml)中有一个搜索结果,作为对容器文档(mycore.xml)的引用列表,它引用另一个文档中的"真实"内容文件(mets.xml)。当不仅要格式化第三级文档,而且要根据mets.xml文档中第三级文档(出版物datapublished年份)上的元素对整个结果进行排序时,就会出现问题。这里有一张粗略的图片:
/result/doc/@href --> document('mycore_1.xml')/mycore/file/@href -> document('mets_1.xml')/mets/dmdSec
/doc/@href --> document('mycore_2.xml')/mycore/file/@href -> document('mets_2.xml')/mets/dmdSec
我有一个使用XSLT 2.0函数的解决方案,但在XSLT 1.0中使用call或apply模板没有得到工作。不幸的是,在选择的CMS (typo3)中,我只能使用XSLT 1.0处理器。
result.xml
<result>
<doc href="mycore_1.xml"/>
<doc href="mycore_2"/>
...
</result>
mycore_1.xml
<mycore>
<file href="mets_1.xml">
</mycore>
mets_1.xml
<mets>
<dmdSec>
<mods>
<dataIssued>1980
</dateIssued>
<namePart>Jones
</namePart>
...
</mods>
</dmdSec>
</mets>
这里是XSLT 2.0的一个适合我的函数定义。
<!-- returns a node-set of all dmdSec -->
<xsl:function name="mets:fetchFiles">
<xsl:param name="docs"/>
<xsl:for-each select="$docs">
<xsl:for-each select="document(@href)/mycore/file">
<xsl:for-each select="document(@href)/mets/dmdSec">
<xsl:copy-of select="."/>
</xsl:for-each>
</xsl:for-each>
</xsl:for-each>
</xsl:function>
这里是调用和排序:
<xsl:for-each select="fetchFiles(result/doc)">
<xsl:sort select="mods/dateIssued"/>
<xsl:call-template name="theFormatting">
... <!-- format and output the dmdSec/mods -->
</xsl:call-template>
</xsl:for-each>
对我来说困难似乎是,函数中的copy-of返回a修改输入,但使用调用模板,我只是生成输出的副本。是否有一种方法可以替换输入以允许排序和格式化dmdSec元素和子元素?
如有任何回应将不胜感激!
Holger
如果你想在XSLT 1.0中实现XSLT 2.0函数,你可以把它作为模板,然后返回一个结果树片段,你可以把它转换成一个节点集(带exsl:node-set($rtf)
)进行排序。
但是坦白地说,我不明白你为什么要采取所有这些步骤,document
函数足够强大,可以处理多个节点并返回多个文档,所以你应该能够使用
<xsl:for-each select="document(document(result/doc/@href)/mycore/file/@href)/mets/dmdSec">
<xsl:sort select="mods/dateIssued"/>
...
</xsl:for-each>
我更喜欢并建议使用应用模板,例如
<xsl:apply-templates select="document(document(result/doc/@href)/mycore/file/@href)/mets/dmdSec">
<xsl:sort select="mods/dateIssued"/>
</xsl:apply-templates>
和
<xsl:template match="mets/dmdSec">
...
</xsl:template>