使用XSLT将XML转换为JSON,并添加2个方括号[[]]



请求共享用于xml到json转换的xslt代码。我们需要将xml转换为json。然后修剪OuterElement和多个方括号[[a( 修剪外部元素<ns0:PO_消息xmlns:ns0=";http://test.com/Test"gt;b( 最后2个行项目(ShipmentReference,ShipGroupList(,带有2个方形包装[[

输入xml文件:

<?xml version="1.0" encoding="UTF-8"?>
<ns0:PO_Message
xmlns:ns0="http://test.com/Test">
<domainId>MAIL</domainId>
<hubDomainId>MAIL</hubDomainId>
<isForReference>false</isForReference>
<status>releasedToVendor</status>
<docStatus>active</docStatus>
<editingStatus>confirmed</editingStatus>
<vpoNo>2826118</vpoNo>
<vpoDate>2021-02-23</vpoDate>
<instructions>METAL-No Size:1360600001-Article Number</instructions>
<businessRefNo>826118</businessRefNo>
<totalItems>1</totalItems>
<totalQty>160</totalQty>
<season>
<code>F21</code>
</season>
<custId>
<refNo>C000001</refNo>
</custId>
<vendorId>
<vendorCode>41843</vendorCode>
</vendorId>
<headerFactory>
<refNo>F000026</refNo>
<factCode>900088</factCode>
</headerFactory>
<vpoItemList>
<itemNo>19979-2021-0002-41843</itemNo>
<itemName>Base Camp 6 Footprint</itemName>
<customerItemNo>19979</customerItemNo>
<lotNo>1</lotNo>
<itemDesc>Base Camp 6 Footprint</itemDesc>
<shipQty>160</shipQty>
<planedQty>160</planedQty>
<qtyPerExportCarton>160</qtyPerExportCarton>
<qtyPerInnerCarton>160</qtyPerInnerCarton>
<factCode>900088</factCode>
<refNo>19979-2021-0002-41843-1</refNo>
<uom>
<code>PCS</code>
</uom>
<brand>
<code>MAIL</code>
</brand>
<itemId>
<itemNo>19979-2021-0002-41843</itemNo>
</itemId>
<portOfLanding>
<code>DLC Dalian</code>
</portOfLanding>
<vpoItemCsList>
<itemLotNo>19979-2021-0002-41843-Lot1</itemLotNo>
<vpoItemColorRef>METAL</vpoItemColorRef>
<vpoItemColorId>
<refNo>GUNMETAL</refNo>
<shortName>METAL</shortName>
</vpoItemColorId>
<vpoItemSizeId>
<refNo>No Size</refNo>
<displayName>No Size</displayName>
</vpoItemSizeId>
<itemId>
<iteamNo>19979-2021-0002-41843</iteamNo>
</itemId>
<lotNo>1</lotNo>
</vpoItemCsList>
<factId>
<factCode>900088</factCode>
</factId>
</vpoItemList>
<vpoShipDtlDtoGroupList>
<qty>160</qty>
<refNo>00001/19979-2021-0002-41843-1</refNo>
<vpoItemRef
xmlns:ns1="http://sap.com/xi/SAPGlobal/GDT">19979-2021-0002-41843-1
</vpoItemRef>
<vpoItemId>
<itemId>
<itemNo>19979-2021-0002-41843</itemNo>
</itemId>
</vpoItemId>
<vpoShipRef>00001</vpoShipRef>
<vpoShipId>
<shipmentNo>00001</shipmentNo>
<originalShipmentDate>2021-08-17</originalShipmentDate>
<shipmentDate>2021-08-23</shipmentDate>
<originalInDcDate>2021-09-15</originalInDcDate>
<inDcDate>2021-09-15</inDcDate>
<refNo>00001/19979-2021-0002-41843-1</refNo>
<shipMode>
<code>3</code>
</shipMode>
<finalDestination>
<code>0001</code>
</finalDestination>
<portOfLoading>
<code>DLC Dalian</code>
</portOfLoading>
</vpoShipId>
<shipMode>
<code>3</code>
</shipMode>
<portOfLoading>
<code>DLC Dalian</code>
</portOfLoading>
</vpoShipDtlDtoGroupList>
<vpoShipDtlCsGroupList>
<itemLotNo>19979-2021-0002-41843-Lot1</itemLotNo>
<shipmentNo>00001</shipmentNo>
<colorSizeQty>160</colorSizeQty>
<refNo>00001/19979-2021-0002-41843-1/GUNMETAL/No Size</refNo>
<vpoItemRef>19979-2021-0002-41843-1</vpoItemRef>
<vpoItemId>
<itemId>
<itemNo>19979-2021-0002-41843</itemNo>
</itemId>
</vpoItemId>
<vpoShipRef>00001/19979-2021-0002-41843-1</vpoShipRef>
<vpoItemColorRef>METAL</vpoItemColorRef>
<vpoItemSizeRef>No Size</vpoItemSizeRef>
<vpoShipDtlColorRef>1</vpoShipDtlColorRef>
<vpoShipDtlSizeRef>1</vpoShipDtlSizeRef>
</vpoShipDtlCsGroupList>
</ns0:PO_Message>

预期Json输出文件

{ "domainId" : "MAIL",
"hubDomainId" : "MAIL",
"isForReference" : "false",
"status" : "releasedToVendor",
"docStatus" : "active",
"editingStatus" : "confirmed",
"vpoNo" : "2118",
"vpoDate" : "2021-02-23",
"instructions" : "METAL-No Size:1360600001-Article Number",
"businessRefNo" : "2818",
"totalItems" : "1",
"totalQty" : "160",
"season" : 
{ "code" : "F21" },
"custId" : 
{ "refNo" : "C000001" },
"vendorId" : 
{ "vendorCode" : "41843" },
"headerFactory" : 
{ "refNo" : "F000026",
"factCode" : "900088" },
"vpoItemList" : 
[ 
{ "itemNo" : "19979-2021-0002-41843",
"itemName" : "Base Camp 6 Footprint",
"customerItemNo" : "19979",
"lotNo" : "1",
"itemDesc" : "Base Camp 6 Footprint",
"shipQty" : "160",
"planedQty" : "160",
"qtyPerExportCarton" : "160",
"qtyPerInnerCarton" : "160",
"factCode" : "900088",
"refNo" : "19979-2021-0002-41843-1",
"uom" : 
{ "code" : "PCS" },
"brand" : 
{ "code" : "Wide" },
"itemId" : 
{ "itemNo" : "19979-2021-0002-41843" },
"portOfLanding" : 
{ "code" : "DLC Dalian" },
"vpoItemCsList" : 
[ 
{ "itemLotNo" : "19979-2021-0002-41843-Lot1",
"vpoItemColorRef" : "METAL",
"vpoItemColorId" : 
{ "refNo" : "GUNMETAL",
"shortName" : "METAL" },
"vpoItemSizeId" : 
{ "refNo" : "No Size",
"displayName" : "No Size" },
"itemId" : 
{ "iteamNo" : "19979-2021-0002-41843" },
"lotNo" : "1" } ],
"factId" : 
{ "factCode" : "900088" } } ],
"vpoShipDtlDtoGroupList" : 
[ 
[ 
{ "qty" : "160",
"refNo" : "00001/19979-2021-0002-41843-1",
"vpoItemRef" : "19979-2021-0002-41843-1",
"vpoItemId" : 
{ "itemId" : 
{ "itemNo" : "19979-2021-0002-41843" } },
"vpoShipRef" : "00001",
"vpoShipId" : 

{ "shipmentNo" : "00001",
"originalShipmentDate" : "2021-08-17",
"shipmentDate" : "2021-08-23",
"originalInDcDate" : "2021-09-15",
"inDcDate" : "2021-09-15",
"refNo" : "00001/19979-2021-0002-41843-1",
"shipMode" : 
{ "code" : "3" },
"finalDestination" : 
{ "code" : "0001" },
"portOfLoading" : 
{ "code" : "DLC Dalian" } } ,
"shipMode" : 
{ "code" : "3" },
"portOfLoading" : 
{ "code" : "DLC Dalian" } } ] ],
"vpoShipDtlCsGroupList" : 
[ 
[ 
{ "itemLotNo" : "19979-2021-0002-41843-Lot1",
"shipmentNo" : "00001",
"colorSizeQty" : "160",
"refNo" : "00001/19979-2021-0002-41843-1/GUNMETAL/No Size",
"vpoItemRef" : "19979-2021-0002-41843-1",
"vpoItemId" : 
{ "itemId" : 
{ "itemNo" : "19979-2021-0002-41843" } },
"vpoShipRef" : "00001/19979-2021-0002-41843-1",
"vpoItemColorRef" : "METAL",
"vpoItemSizeRef" : "No Size",
"vpoShipDtlColorRef" : "1",
"vpoShipDtlSizeRef" : "1" } ] ] }

XLST代码:

<?xml version="1.0" encoding="utf-8"?>
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
version="3.0"
xmlns:xs="http://www.w3.org/2001/XMLSchema"
xmlns="http://www.w3.org/2005/xpath-functions"
exclude-result-prefixes="#all"
expand-text="yes">
<xsl:output method="text"/>
<xsl:template match="/*" priority="5">
<xsl:variable name="json-xml">
<map>
<xsl:apply-templates/>
</map>        
</xsl:variable>
<xsl:value-of select="xml-to-json($json-xml, map { 'indent' : true() })"/>
</xsl:template>

<xsl:template match="*[not(*)]">
<string key="{local-name()}">{.}</string>
</xsl:template>

<xsl:template match="*[(*) and . castable as xs:double]">
<number key="{local-name()}">{.}</number>
</xsl:template>

<xsl:template match="*[* and not(*[6])]">
<map key="{local-name()}">
<xsl:apply-templates/>
</map>
</xsl:template>

<xsl:template match="*[* and *[6]]">
<array key="{local-name()}">
<map>
<xsl:apply-templates/>
</map>
</array>
</xsl:template>

<xsl:template match="vpoShipDtlDtoGroupList | vpoShipDtlCsGroupList" priority="10">
<array key="{local-name()}">
<array>
<map>
<xsl:apply-templates/>
</map>          
</array>
</array>
</xsl:template>
</xsl:stylesheet>

谢谢,拉维

这基本上是从XML到xml-to-json函数所期望的XML格式的两步转换。你会使用

<?xml version="1.0" encoding="utf-8"?>
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
version="3.0"
xmlns:xs="http://www.w3.org/2001/XMLSchema"
xmlns="http://www.w3.org/2005/xpath-functions"
exclude-result-prefixes="#all"
expand-text="yes">
<xsl:output method="xml" indent="yes"/>
<xsl:mode on-no-match="shallow-skip"/>

<xsl:template match="/*">
<map>
<xsl:apply-templates/>
</map>
</xsl:template>

<xsl:template match="*[not(*)]">
<string key="{local-name()}">{.}</string>
</xsl:template>

<xsl:template match="*[not(*) and . castable as xs:double]">
<number key="{local-name()}">{.}</number>
</xsl:template>

<xsl:template match="*[* and not(*[2])]">
<map key="{local-name()}">
<xsl:apply-templates/>
</map>
</xsl:template>

<xsl:template match="*[* and *[2]]">
<array key="{local-name()}">
<map>
<xsl:apply-templates/>
</map>
</array>
</xsl:template>

<xsl:template match="ShipGroupList | ShipmentRefference" priority="10">
<array key="{local-name()}">
<array>
<map>
<xsl:apply-templates/>
</map>          
</array>
</array>
</xsl:template>
<xsl:template match="/" name="xsl:initial-template">
<xsl:next-match/>
<xsl:comment xmlns:saxon="http://saxon.sf.net/">Run with {system-property('xsl:product-name')} {system-property('xsl:product-version')} {system-property('Q{http://saxon.sf.net/}platform')}</xsl:comment>
</xsl:template>
</xsl:stylesheet>

对于第一步(https://xsltfiddle.liberty-development.net/asoTJB/0)例如

<?xml version="1.0" encoding="UTF-8"?>
<array xmlns="http://www.w3.org/2005/xpath-functions" key="PO_Message">
<map>
<string key="domainId">Mail</string>
<string key="hubId">Mail</string>
<array key="MailItemList">
<map>
<string key="itemNo">2021-0002</string>
<string key="itemName">Camp</string>
<map key="factId">
<number key="factCode">188</number>
</map>
</map>
</array>
<array key="ShipGroupList">
<array>
<map>
<number key="GroupList1">123</number>
<number key="qty">160</number>
<map key="shipMode">
<number key="code">3</number>
</map>
</map>
</array>
</array>
<array key="ShipmentRefference">
<array>
<map>
<number key="itemLotNo">199791</number>
<number key="shipmentNo">1</number>
</map>
</array>
</array>
</map>
</array>
<!--Run with SAXON HE 9.8.0.15 -->

然后,一个完整的样式表将使用变量中的第一步,并将xml-to-json函数应用于变量:

<?xml version="1.0" encoding="utf-8"?>
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
version="3.0"
xmlns:xs="http://www.w3.org/2001/XMLSchema"
xmlns="http://www.w3.org/2005/xpath-functions"
exclude-result-prefixes="#all"
expand-text="yes">
<xsl:output method="text"/>
<xsl:template match="/*" priority="5">
<xsl:variable name="json-xml">
<map>
<xsl:apply-templates/>
</map>        
</xsl:variable>
<xsl:value-of select="xml-to-json($json-xml, map { 'indent' : true() })"/>
</xsl:template>

<xsl:template match="*[not(*)]">
<string key="{local-name()}">{.}</string>
</xsl:template>

<xsl:template match="*[not(*) and . castable as xs:double]">
<number key="{local-name()}">{.}</number>
</xsl:template>

<xsl:template match="*[* and not(*[2])]">
<map key="{local-name()}">
<xsl:apply-templates/>
</map>
</xsl:template>

<xsl:template match="*[* and *[2]]">
<array key="{local-name()}">
<map>
<xsl:apply-templates/>
</map>
</array>
</xsl:template>

<xsl:template match="ShipGroupList | ShipmentRefference" priority="10">
<array key="{local-name()}">
<array>
<map>
<xsl:apply-templates/>
</map>          
</array>
</array>
</xsl:template>
</xsl:stylesheet>

https://xsltfiddle.liberty-development.net/asoTJB/1

最新更新