我需要将平面xml转换为层次结构xml结构。目标元素需要映射到与源xml不同的级别。我将多次循环XML以创建目标xml。使用带有属性名称的//似乎也不是一个好主意,因为xml可能很大并且可能导致性能问题。
我想了解xslt是否可以用更好的方式编写;
我试图在下面展示一个简单的例子。
任何想法或帮助表示赞赏。
输入xml:
<result>
<program>
<c i='0' d='Policy'>
<c i='14' d='LOB'>
<m i='CR TOT TERR TERM PREM' d='CR TOT TERR TERM PREM' v='-17277' />
<m i='CR TOT TERR NET PREM' d='CR TOT TERR NET PREM' v='-14935' />
<m i='CR TOT TERR GAP PREM' d='CR TOT TERR GAP PREM' v='294' />
<m i='CR TOT TERR FINAL ADJ PREM' d='CR TOT TERR FINAL ADJ PREM'
v='-17571' />
<m i='CR QUOTE OPTION ID' d='CR QUOTE OPTION ID'
v='Quote0001' />
<m i='CR TOT TERR COMMISSION' d='CR TOT TERR COMMISSION' v='-2635.65' />
<m i='CR TOT TERR ACTUAL PREM' d='CR TOT TERR ACTUAL PREM' v='-17571' />
<m i='CR TOT TERM PREM' d='CR TOT TERM PREM' v='-881154' />
<m i='CR TOT TAXES AND SRCHRG' d='CR TOT TAXES AND SRCHRG' v='-892.14' />
<m i='CR TOT STATE SRCHRG' d='CR TOT STATE SRCHRG' v='-896.14' />
<m i='CR TOT PREM ADJ' d='CR TOT PREM ADJ' v='0' />
<m i='CR TOT PREM' d='CR TOT PREM' v='-897026.14' />
<m i='CR TOT NET PREM' d='CR TOT NET PREM' v='-761713' />
<m i='CR TOT GAP PREM' d='CR TOT GAP PREM' v='14980' />
<m i='CR TOT FINAL ADJ PREM' d='CR TOT FINAL ADJ PREM' v='-896134' />
<m i='CR TOT COMMISSION' d='CR TOT COMMISSION' v='-134420.1' />
<m i='CR TOT ADDL COV TERM PREM' d='CR TOT ADDL COV TERM PREM' v='-879465' />
<m i='CR TOT ADDL COV NET PREM' d='CR TOT ADDL COV NET PREM' v='-760253.59999999998' />
<m i='CR TOT ADDL COV GAP PREM' d='CR TOT ADDL COV GAP PREM' v='14951' />
<m i='CR TOT ADDL COV FINAL ADJ PREM' d='CR TOT ADDL COV FINAL ADJ PREM'
v='-894416' />
<m i='CR TOT ADDL COV COMMISSION' d='CR TOT ADDL COV COMMISSION'
v='-134162.40000000002' />
<m i='CR TOT ADDL COV ACTUAL PREM' d='CR TOT ADDL COV ACTUAL PREM'
v='-894416' />
<m i='CR TOT ACTUAL PREM' d='CR TOT ACTUAL PREM' v='-896134' />
<m i='CR STATE SRCHRG NAME' d='CR STATE SRCHRG NAME' v='FL Comml Prop Fire Marshall' />
<m i='CR FL POLICY SRCHRG NAME' d='CR FL POLICY SRCHRG NAME' v='FL Emergency Mgmt Praparedness' />
<m i='CR FL POLICY SRCHRG' d='CR FL POLICY SRCHRG' v='4' />
<m i='CR EMPL THEFT ANNUAL RATE' d='CR EMPL THEFT ANNUAL RATE' v='1.144' />
<m i='CR EMPL THEFT ANNUAL PREM' d='CR EMPL THEFT ANNUAL PREM' v='15401' />
</c>
</c>
</program>
</result>
XSLT:
<?xml version="1.0"?>
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" version="2.0" xmlns="urn:company:esb:services:Pricing:v01">
<xsl:output method="xml" version="1.0" encoding="UTF-8" indent="yes">
</xsl:output>
<xsl:strip-space elements="*"/>
<xsl:template match="/result/program/c">
<xsl:element name="pricing-response">
<dummy>
<policy>
<xsl:for-each select="c">
<xsl:variable name='strComp'>
<xsl:value-of select='@i'/>
</xsl:variable>
<xsl:if test="@d ='CrimeLine' ">
<policy-output>
<xsl:for-each select="m">
<xsl:variable name='strComp'>
<xsl:value-of select='@i'/>
</xsl:variable>
<xsl:if test="$strComp ='CR QUOTE OPTION ID' ">
<quote-option-id>
<xsl:value-of select='@v'/>
</quote-option-id>
</xsl:if>
<xsl:if test="$strComp ='CR TOT TAXES AND SRCHRG' ">
<total-taxsurcharge-amt>
<amount>
<xsl:value-of select='@v'/>
</amount>
</total-taxsurcharge-amt>
</xsl:if>
<xsl:if test="$strComp ='CR TOT PREM' ">
<total-premium-amt>
<amount>
<xsl:value-of select='@v'/>
</amount>
</total-premium-amt>
</xsl:if>
</xsl:for-each>
<taxsurcharge-summary>
<taxsurcharge>
<taxsurcharge-identifier>State</taxsurcharge-identifier>
<xsl:for-each select="m">
<xsl:variable name='strComp'>
<xsl:value-of select='@i'/>
</xsl:variable>
<xsl:if test="$strComp ='CR TOT STATE SRCHRG' ">
<taxsurcharge-amt>
<amount>
<xsl:value-of select='@v'/>
</amount>
</taxsurcharge-amt>
</xsl:if>
<xsl:if test="$strComp ='CR STATE SRCHRG NAME' ">
<taxsurcharge-name>
<xsl:value-of select='@v'/>
</taxsurcharge-name>
</xsl:if>
<xsl:if test="$strComp ='CR STATE SRCHRG CODE' ">
<taxsurcharge-code>
<xsl:value-of select='@v'/>
</taxsurcharge-code>
</xsl:if>
</xsl:for-each>
</taxsurcharge>
</taxsurcharge-summary>
</policy-output>
</xsl:if>
</xsl:for-each>
</policy>
</dummy>
</xsl:element>
</xsl:template>
</xsl:stylesheet>
输出xml:
<?xml version="1.0" encoding="UTF-8"?>
<pricing-response xmlns="urn:company:esb:services:Pricing:v01">
<dummy>
<policy>
<policy-output>
<quote-option-id>Quote0001</quote-option-id>
<total-taxsurcharge-amt>
<amount>-892.14</amount>
</total-taxsurcharge-amt>
<total-premium-amt>
<amount>-897026.14</amount>
</total-premium-amt>
<taxsurcharge-summary>
<taxsurcharge>
<taxsurcharge-identifier>State</taxsurcharge-identifier>
<taxsurcharge-amt>
<amount>-896.14</amount>
</taxsurcharge-amt>
<taxsurcharge-name>FL Comml Prop Fire Marshall</taxsurcharge-name>
</taxsurcharge>
</taxsurcharge-summary>
</policy-output>
</policy>
</dummy>
</pricing-response>
答案 0 :(得分:0)
实际上,XSLT的新手,特别是来自通用语言的新手,通常会将XML文档视为可迭代的,其中节点必须使用for:each
和if
逻辑进行迭代,以便转换原始源。但是,在XSLT中,需要在模板中考虑重新创建树。
考虑以下内容,您可以向下走到第二个c
级别的级别,然后使用XPath调用有条件地检索值。如果没有默认名称空间,脚本会短得多,根目录urn:company:esb:services:Pricing:v01
需要每个新分配节点上的<xsl:element ... namespace=...>
。
<?xml version="1.0" encoding="UTF-8"?>
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:output indent="yes" method="xml" version="1.0" encoding="UTF-8"/>
<xsl:strip-space elements="*"/>
<xsl:template match="/result/program/c">
<pricing-response xmlns="urn:company:esb:services:Pricing:v01">
<dummy>
<policy>
<xsl:apply-templates select="c"/>
</policy>
</dummy>
</pricing-response>
</xsl:template>
<xsl:template match="c">
<xsl:element name="policy-output" namespace="urn:company:esb:services:Pricing:v01">
<xsl:element name="quote_option" namespace="urn:company:esb:services:Pricing:v01">
<xsl:value-of select="m[@i='CR QUOTE OPTION ID']/@v"/>
</xsl:element>
<xsl:element name="total-taxsurcharge-amt" namespace="urn:company:esb:services:Pricing:v01">
<xsl:element name="amount" namespace="urn:company:esb:services:Pricing:v01">
<xsl:value-of select="m[@i='CR TOT TAXES AND SRCHRG']/@v"/>
</xsl:element>
</xsl:element>
<xsl:element name="total-premium-amt" namespace="urn:company:esb:services:Pricing:v01">
<xsl:element name="amount" namespace="urn:company:esb:services:Pricing:v01">
<xsl:value-of select="m[@i='CR TOT PREM']/@v"/>
</xsl:element>
</xsl:element>
<xsl:element name="taxsurcharge-summary" namespace="urn:company:esb:services:Pricing:v01">
<xsl:element name="taxsurcharge" namespace="urn:company:esb:services:Pricing:v01">
<xsl:element name="taxsurcharge-identifier" namespace="urn:company:esb:services:Pricing:v01">State</xsl:element>
<xsl:element name="taxsurcharge-amt" namespace="urn:company:esb:services:Pricing:v01">
<xsl:element name="amount" namespace="urn:company:esb:services:Pricing:v01">
<xsl:value-of select="m[@i='CR TOT STATE SRCHRG']/@v"/>
</xsl:element>
</xsl:element>
<xsl:element name="taxsurcharge-name" namespace="urn:company:esb:services:Pricing:v01">
<xsl:value-of select="m[@i='CR STATE SRCHRG NAME']/@v"/>
</xsl:element>
</xsl:element>
</xsl:element>
</xsl:element>
</xsl:template>
</xsl:stylesheet>