使用xslt

时间:2017-04-11 20:24:07

标签: json xml xslt xslt-1.0

尝试使用通用xslt

将xml转换为json

输入xml:

<Response>
<Info>
    <Domain/>
    <Source/>
</Info>
<OrderDetails itemNo="1 ">
    <OrderNum>0002060412</OrderNum>
    <sourceType>UTD</sourceType>
    <organization>UTD09</organization>
    <AmtAdjust>Not Known-Need Coding</AmtAdjust>
</OrderDetails>
<OrderDetails itemNo="2 ">
    <OrderNum>0002060415</OrderNum>
    <sourceType>UTD</sourceType>
    <organization>UTD09</organization>
    <AmtAdjust>Not Known-Need Coding</AmtAdjust>
</OrderDetails>
<OrderDetails itemNo="3 ">
    <OrderNum>0002060413</OrderNum>
    <sourceType>UTD</sourceType>
    <organization>UTD09</organization>
    <AmtAdjust>Not Known-Need Coding</AmtAdjust>
</OrderDetails>
<OrderDetails itemNo="5 ">
    <OrderNum>0060064425</OrderNum>
    <sourceType>UTD</sourceType>
    <organization>UTD09</organization>
    <TickNums>
        <TktNum>11776564428635</TktNum>
    </TickNums>
    <LineDetail>
        <itemNum>000010</itemNum>
        <type>ftr</type>
        <amnt>100.000000000 </amnt>
        <qty>1.000 </qty>
        <center>0002/0002</center>
    </LineDetail>
    <LineDetail>
        <itemNum>000020</itemNum>
        <type>ert</type>
        <amnt>30.000000000 </amnt>
        <qty>1.000 </qty>
        <center>0002/0002</center>
    </LineDetail>
    <LineDetail>
        <itemNum>000030</itemNum>
        <type>VAT</type>
        <amnt>10.000000000 </amnt>
        <qty>1.000 </qty>
        <center>0002/0002</center>
    </LineDetail>
    <LineDetail>
        <itemNum>000040</itemNum>
        <type>C2</type>
        <amnt>20.000000000 </amnt>
        <qty>1.000 </qty>
        <center>0002/0002</center>
    </LineDetail>
    <AmtAdjust>Not Known-Need Coding</AmtAdjust>
</OrderDetails>
<OrderDetails itemNo="6 ">
    <OrderNum>0060064427</OrderNum>
    <sourceType>UTD</sourceType>
    <organization>UTD09</organization>
    <TickNums>
        <TktNum>11234569354874</TktNum>
    </TickNums>
    <TickNums>
        <TktNum>45465749854377</TktNum>
    </TickNums>
    <LineDetail>
        <itemNum>000010</itemNum>
        <type>BR</type>
        <amnt>100.000000000 </amnt>
        <qty>1.000 </qty>
        <center>0002/0002</center>
    </LineDetail>
    <LineDetail>
        <itemNum>000020</itemNum>
        <type>ytr</type>
        <amnt>100.000000000 </amnt>
        <qty>1.000 </qty>
        <center>0002/0002</center>
    </LineDetail>
    <LineDetail>
        <itemNum>000030</itemNum>
        <type>COMM</type>
        <amnt>200.000000000 </amnt>
        <qty>1.000 </qty>
        <center>0002/0002</center>
    </LineDetail>
    <AmtAdjust>Not Known-Need Coding</AmtAdjust>
</OrderDetails>

我的常见xslt:

  <?xml version="1.0"?>
    <xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
    <xsl:output method="text"/>

    <xsl:template match="/">{
        <xsl:apply-templates select="*"/>}
    </xsl:template>

    <!-- Object or Element Property-->
    <xsl:template match="*">
        "<xsl:value-of select="name()"/>" :<xsl:call-template name="Properties">
            <xsl:with-param name="parent" select="'Yes'"> </xsl:with-param>
        </xsl:call-template>
    </xsl:template>

    <!-- Array Element -->
    <xsl:template match="*" mode="ArrayElement">
        <xsl:call-template name="Properties"/>
    </xsl:template>

    <!-- Object Properties -->
    <xsl:template name="Properties">
        <xsl:param name="parent"></xsl:param>
        <xsl:variable name="childName" select="name(*[1])"/>
        <xsl:choose>            
            <xsl:when test="not(*|@*)"><xsl:choose><xsl:when test="$parent='Yes'"> <xsl:text>&quot;</xsl:text><xsl:value-of select="."/><xsl:text>&quot;</xsl:text></xsl:when>
                    <xsl:otherwise>"<xsl:value-of select="name()"/>":"<xsl:value-of  select="."/>"</xsl:otherwise>
                </xsl:choose>           
            </xsl:when>                
            <xsl:when test="count(*[name()=$childName]) > 1">{ "<xsl:value-of  select="$childName"/>" :[<xsl:apply-templates select="*" mode="ArrayElement"/>] }</xsl:when>
            <xsl:otherwise>{
                <xsl:apply-templates select="@*"/>
                <xsl:apply-templates select="*"/>
                }</xsl:otherwise>
        </xsl:choose>
        <xsl:if test="following-sibling::*">,</xsl:if>
    </xsl:template>

    <!-- Attribute Property -->
    <xsl:template match="@*">"<xsl:value-of select="name()"/>" : "<xsl:value-of select="."/>",
    </xsl:template>
    </xsl:stylesheet>

但输出如下:

{    
    "Response" :{            
    "Info" :{            
    "Domain" :"",
    "Source" :""
            },
    "OrderDetails" :{
            "itemNo" : "1 ",
    "OrderNum" :"0002060412",
    "sourceType" :"UTD",
    "organization" :"UTD09",
    "AmtAdjust" :"Not Known-Need Coding"
            },
    "OrderDetails" :{
            "itemNo" : "2 ",
    "OrderNum" :"0002060415",
    "sourceType" :"UTD",
    "organization" :"UTD09",
    "AmtAdjust" :"Not Known-Need Coding"
            },
    "OrderDetails" :{
            "itemNo" : "3 ",
    "OrderNum" :"0002060413",
    "sourceType" :"UTD",
    "organization" :"UTD09",
    "AmtAdjust" :"Not Known-Need Coding"
            },
    "OrderDetails" :{
            "itemNo" : "5 ",
    "OrderNum" :"0060064425",
    "sourceType" :"UTD",
    "organization" :"UTD09",
    "TickNums" :{            
    "TktNum" :"11776564428635"
            },
    "LineDetail" :{            
    "itemNum" :"000010",
    "type" :"ftr",
    "amnt" :"100.000000000 ",
    "qty" :"1.000 ",
    "center" :"0002/0002"
            },
    "LineDetail" :{            
    "itemNum" :"000020",
    "type" :"ert",
    "amnt" :"30.000000000 ",
    "qty" :"1.000 ",
    "center" :"0002/0002"
            },
    "LineDetail" :{            
    "itemNum" :"000030",
    "type" :"VAT",
    "amnt" :"10.000000000 ",
    "qty" :"1.000 ",
    "center" :"0002/0002"
            },
    "LineDetail" :{            
    "itemNum" :"000040",
    "type" :"C2",
    "amnt" :"20.000000000 ",
    "qty" :"1.000 ",
    "center" :"0002/0002"
            },
    "AmtAdjust" :"Not Known-Need Coding"
            },
    "OrderDetails" :{
            "itemNo" : "6 ",
    "OrderNum" :"0060064427",
    "sourceType" :"UTD",
    "organization" :"UTD09",
    "TickNums" :{            
    "TktNum" :"11234569354874"
            },
    "TickNums" :{

    "TktNum" :"45465749854377"
            },
    "LineDetail" :{            
    "itemNum" :"000010",
    "type" :"BR",
    "amnt" :"100.000000000 ",
    "qty" :"1.000 ",
    "center" :"0002/0002"
            },
    "LineDetail" :{            
    "itemNum" :"000020",
    "type" :"ytr",
    "amnt" :"100.000000000 ",
    "qty" :"1.000 ",
    "center" :"0002/0002"
            },
    "LineDetail" :{            
    "itemNum" :"000030",
    "type" :"COMM",
    "amnt" :"200.000000000 ",
    "qty" :"1.000 ",
    "center" :"0002/0002"
            },
    "AmtAdjust" :"Not Known-Need Coding"
            }
            }}

我期待的出局是

    {
    "Response": {
        "Info": {
            "Domain": "",
            "Source": ""
        },
        "OrderDetails": [
            {
                "itemNo": "1 ",
                "OrderNum": "0002060412",
                "sourceType": "UTD",
                "organization": "UTD09",
                "AmtAdjust": "Not Known-Need Coding"
            },
            {
                "itemNo": "2 ",
                "OrderNum": "0002060415",
                "sourceType": "UTD",
                "organization": "UTD09",
                "AmtAdjust": "Not Known-Need Coding"
            },
            {
                "itemNo": "3 ",
                "OrderNum": "0002060413",
                "sourceType": "UTD",
                "organization": "UTD09",
                "AmtAdjust": "Not Known-Need Coding"
            },
            {
                "itemNo": "5 ",
                "OrderNum": "0060064425",
                "sourceType": "UTD",
                "organization": "UTD09",
                "TickNums": {
                    "TktNum": ["11776564428635"]
                },
                "LineDetail": [
                    {
                        "itemNum": "000010",
                        "type": "ftr",
                        "amnt": "100.000000000 ",
                        "qty": "1.000 ",
                        "center": "0002/0002"
                    },
                    {
                        "itemNum": "000020",
                        "type": "ert",
                        "amnt": "30.000000000 ",
                        "qty": "1.000 ",
                        "center": "0002/0002"
                    },
                    {
                        "itemNum": "000030",
                        "type": "VAT",
                        "amnt": "10.000000000 ",
                        "qty": "1.000 ",
                        "center": "0002/0002"
                    },
                    {
                        "itemNum": "000040",
                        "type": "C2",
                        "amnt": "20.000000000 ",
                        "qty": "1.000 ",
                        "center": "0002/0002"
                    }
                ],
                "AmtAdjust": "Not Known-Need Coding"
            },
            {
                "itemNo": "6 ",
                "OrderNum": "0060064427",
                "sourceType": "UTD",
                "organization": "UTD09",
                "TickNums": {
                    "TktNum": [
                        "11234569354874",
                        "45465749854377"
                    ]
                },
                "LineDetail": [
                    {
                        "itemNum": "000010",
                        "type": "BR",
                        "amnt": "100.000000000 ",
                        "qty": "1.000 ",
                        "center": "0002/0002"
                    },
                    {
                        "itemNum": "000020",
                        "type": "ytr",
                        "amnt": "100.000000000 ",
                        "qty": "1.000 ",
                        "center": "0002/0002"
                    },
                    {
                        "itemNum": "000030",
                        "type": "COMM",
                        "amnt": "200.000000000 ",
                        "qty": "1.000 ",
                        "center": "0002/0002"
                    }
                ],
                "AmtAdjust": "Not Known-Need Coding"
            }
        ]
    }
}

但是输入xml无法更改以添加更多字段来填充数组。那么如何使用现有的xslt更像通用的。

1 个答案:

答案 0 :(得分:1)

如果样式表要为TktNums生成一个数组,那么它需要一些额外的信息,这些信息超出了输入XML的可用范围。它需要某种指令来告诉它TktNums可以重复,即使它在这个特定的输入中没有重复。您可以将这些信息放在样式表中,但这会妨碍您使样式表完全通用的目标。或者,您可以从架构或您自己发明的某种配置文件中获取它。但它必须来自某个地方。

在LineDetail的情况下,您可以根据子元素重复的事实生成一个数组。但是,如果LineDetail只出现一次输入实例,那么这会给你带来问题。

基本上,这不是编码问题,而是设计/规范问题。