如何使用value-of转换参数并选择

时间:2019-01-14 20:37:19

标签: xslt-1.0

我正在使用xslt将xml文档转换为另一个xml文档。

在下面的代码中,它仅获取第一个评论的电子邮件地址的值并将其用于所有评论,而不是获取每个评论的电子邮件地址。我知道使用//不好,但是当我仅使用Review / UserEmailAddress时,该值为空白,我不知道该怎么做。

这是我的输入xml:

<Product id="867776000050">
<ExternalId>867776000050</ExternalId>
<Reviews>
    <Review id="3924" removed="false">
         <UserProfileReference id="Haliley">
            <ExternalId>Haliley</ExternalId>
            <DisplayName>Haliley</DisplayName>
        </UserProfileReference>
        <UserEmailAddress>hbonb@yahoo.com</UserEmailAddress>
    </Review>
    <Review id="3919" removed="false">
        <UserProfileReference id="PaulineTincher">
            <ExternalId>PaulineTincher</ExternalId>
            <DisplayName>PaulineTincher</DisplayName>
        </UserProfileReference>
        <UserEmailAddress>pt59@msn.com</UserEmailAddress>
    </Review>
</Reviews>
</Product>

这是我的样式表:

<xsl:stylesheet version="1.0" 
     xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:output method="xml" omit-xml-declaration="no" indent="yes"/>
<xsl:strip-space elements="*"/>

<xsl:template match="node()|@*">
    <xsl:copy>
        <xsl:apply-templates select="node()|@*"/>
    </xsl:copy>
</xsl:template>

<xsl:template match="Review/UserProfileReference">
    <xsl:variable name="userid"><xsl:value-of select="ExternalId"/> 
    <xsl:value-of select="substring-before(//Review/UserEmailAddress, '@')"/></xsl:variable>
    <UserProfileReference id="{$userid}">
    <ExternalId><xsl:value-of select="ExternalId"/><xsl:value-of select="substring-before(//Review/UserEmailAddress, '@')"/></ExternalId>
    <DisplayName><xsl:value-of select="DisplayName"/></DisplayName>
    </UserProfileReference>
</xsl:template>

</xsl:stylesheet>

我试图通过将电子邮件地址的第一部分附加到现有值上来使UserProfileReference唯一。

在我的结果中,第一次查看的UserProfileReference id值正确无误,它会将UserEmailAddress的值附加到id上。

但是对于审阅2,它使用审阅1中的电子邮件地址,而不是审阅2。我花了很多时间在此上,无法弄清。请帮忙!

<?xml version="1.0" encoding="UTF-8"?>
<Product id="867776000050">
<ExternalId>867776000050</ExternalId>
<Reviews>
    <Review id="3924" removed="false">
    <UserProfileReference id="Halileyhbonb">
        <ExternalId>Halileyhbonb</ExternalId>
        <DisplayName>Haliley</DisplayName>
    </UserProfileReference>
    <UserEmailAddress>hbonb@yahoo.com</UserEmailAddress>
    </Review>
    <Review id="3919" removed="false">
    <UserProfileReference id="PaulineTincherhbonb">
        <ExternalId>PaulineTincherhbonb</ExternalId>
        <DisplayName>PaulineTincher</DisplayName>
    </UserProfileReference>
    <UserEmailAddress>pt59@msn.com</UserEmailAddress>
    </Review>
</Reviews>
</Product>

1 个答案:

答案 0 :(得分:0)

您使用的是错误的表达式://全局行动,因此//Review/UserEmailAddress返回一个节点集,其中包含所有Review/UserEmailAddress个可以全局找到的节点,并使用{{1 }}。因此,在两种情况下,它都是同一项目。

一种解决方案是使用类似substring-before(...)的相对路径(相对于上下文节点)。因此,替换出现的两个

../UserEmailAddress

使用

substring-before(//Review/UserEmailAddress, '@')

它将按预期运行。