XSLT 3.0 - 如何正确使用 apply-templates 和 copy-of?

问题描述 投票:0回答:1

我对 xslt 3.0 相当陌生,并且有一个需要使用它的问题。我非常接近,但我的输出正在打印我不想要的数据的纯文本副本。

我基本上必须将 T3 块与 T4 块合并,仅适用于具有员工 ID 且还必须获取标题数据的工作人员。

XSLT:

<?xml version="1.0" encoding="UTF-8"?>
<xsl:stylesheet
    xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
    xmlns:map="http://www.w3.org/2005/xpath-functions/map"
    xmlns:xs="http://www.w3.org/2001/XMLSchema"
    xmlns:bsvc="urn:com.workday/bsvc"
    xmlns:wd="urn:com.workday/bsvc"
    xmlns:functx = "http://www.functx.com"
    xmlns:env="http://schemas.xmlsoap.org/soap/envelope/" 
    xmlns:tdf="urn:com.workday/tdf" 
    xmlns:saxon="http://saxon.sf.net/"
    xmlns:is="java:com.workday.esb.intsys.xpath.ParsedIntegrationSystemFunctions" 
    xmlns:tv="java:com.workday.esb.intsys.TypedValue"
    xmlns:this="urn:this"
    exclude-result-prefixes="#all"
    version="3.0">
    
    <xsl:param name="p.file"/>
   
    <xsl:variable name="Linefeed" select="'&#xa;'"/>
    
    <xsl:mode streamable="yes" on-no-match="shallow-skip" use-accumulators="#all" />
    
     <xsl:output method="xml"/>
    
<xsl:function name="this:ApplyMap">
    <xsl:param name="externalValue"/>
    <xsl:param name="mapName"/>
    <xsl:variable name="internalValue">
        <xsl:value-of select="is:getIntegrationMapValue(string($mapName),string($externalValue))"/>
    </xsl:variable>
    <xsl:choose>
        <xsl:when test="$internalValue">
            <xsl:value-of select="$internalValue"/>
        </xsl:when>
        <xsl:otherwise>
            <xsl:value-of select="$externalValue"/>
        </xsl:otherwise>
    </xsl:choose>
</xsl:function>
    
  <xsl:key name="EmpLookup" match ="T3Record" use="string(CardholderId)"/>
    
<xsl:template match = "/">
    <Root>
    
        <xsl:apply-templates select="*"></xsl:apply-templates>
    
    </Root>
</xsl:template>
    
<xsl:template match = "Blocks">

    <xsl:iterate select="*">
        <xsl:param name="EmpLookupData"/>
        <xsl:choose>
        <xsl:when test="self::T3Block">
            <xsl:next-iteration>
                <xsl:with-param name="EmpLookupData" select="snapshot()"/>
            </xsl:next-iteration>
        </xsl:when>
        
        <xsl:when test="self::T4Block">
            <xsl:apply-templates select=".">
              <xsl:with-param name="EmpLookupData" select="$EmpLookupData" tunnel="yes"/>
            </xsl:apply-templates>
          </xsl:when>
        </xsl:choose>
      </xsl:iterate>
     
</xsl:template>



<xsl:template match="Blocks/T4Block">
    <bsvc:Credit_Card_Header__HV__Request xmlns:bsvc="urn:com.workday/bsvc">
    <wd:Card_Holder_Listing_File_Data>
         <xsl:apply-templates select="copy-of()" mode="in-memory"/>
         </wd:Card_Holder_Listing_File_Data>
    </bsvc:Credit_Card_Header__HV__Request>
</xsl:template>

<xsl:template match="Header" mode="in-memory">
    

    <wd:Card_Holder_Listing_File_Name><xsl:value-of select="concat(ProcessorPlatformRef,'-',CompanyId,'-',SequenceNum,'-',RecordTypeCode,'-',IssuerIdNum,'-',ProcessorIdNum,'-',VisaRegionId)"/></wd:Card_Holder_Listing_File_Name>
    <wd:Card_Holder_Listing_File_Date><xsl:value-of select="concat(substring(ProcessingDate,5,4),'-',substring(ProcessingDate,1,2),'-',substring(ProcessingDate,3,2))"/></wd:Card_Holder_Listing_File_Date>
 </xsl:template>

        
    <xsl:template match="T4Record[EmployeeId]" mode = "in-memory">

        <xsl:param name="EmpLookupData" tunnel="yes"/>
        
        <xsl:variable name="org" select="key('EmpLookup', CardholderId, $EmpLookupData)"/>
             
        <wd:Credit_Card_Data>
                    <wd:Expense_Credit_Card_ID><xsl:value-of select="$org/AcctNum"/></wd:Expense_Credit_Card_ID>
                    <wd:Corporate_Credit_Card_Account_Reference>
                        <wd:ID wd:type="Corporate_Credit_Card_Account_ID"><xsl:value-of select="this:ApplyMap(CompanyId,'Billing_Account')"/></wd:ID>
                    </wd:Corporate_Credit_Card_Account_Reference>                   
                                                        
                    <wd:Last_4_Digits_of_Credit_Card_Number><xsl:value-of select="substring($org/AcctNum,string-length($org/AcctNum) - 3)"/></wd:Last_4_Digits_of_Credit_Card_Number>
                    <wd:Credit_Card_Expiration_Date><xsl:value-of select="concat(substring($org/CardExpDate,5,4),'-',substring($org/CardExpDate,1,2),'-',substring($org/CardExpDate,3,2))"/></wd:Credit_Card_Expiration_Date>
                    <wd:Cardmember_Embossed_Name><xsl:value-of select="$org/EmbossLine1"/></wd:Cardmember_Embossed_Name>
                    <wd:Document_Status_Reference>
                        <wd:ID wd:type="Document_Status_ID">ACTIVE</wd:ID>
                    </wd:Document_Status_Reference>
                    <wd:Cardholder_ID>                      
                        <xsl:value-of select="EmployeeId"/>
                    </wd:Cardholder_ID> 
        </wd:Credit_Card_Data>
        <xsl:value-of select="$Linefeed"/>

    </xsl:template>
    
    

 </xsl:stylesheet>

所需输出:请注意,由于 Matt Carp 没有员工 ID,因此我不希望他出现在输出中。然而我上面的代码似乎在一个字符串中打印出了他的所有 T4 块,如下所示:4xyz333MATTHEWCARP

<?xml version='1.0' encoding='utf-8'?>
<Root>
    <bsvc:Credit_Card_Header__HV__Request xmlns:bsvc="urn:com.workday/bsvc">
        <wd:Card_Holder_Listing_File_Data xmlns:wd="urn:com.workday/bsvc">
            
            <wd:Card_Holder_Listing_File_Name>987-xyz-0-04-1423-200-1</wd:Card_Holder_Listing_File_Name>
            <wd:Card_Holder_Listing_File_Date>2024-08-02</wd:Card_Holder_Listing_File_Date>
            <wd:Credit_Card_Data>
                <wd:Expense_Credit_Card_ID>222</wd:Expense_Credit_Card_ID>
                <wd:Corporate_Credit_Card_Account_Reference>
                    <wd:ID wd:type="Corporate_Credit_Card_Account_ID">111</wd:ID>
                </wd:Corporate_Credit_Card_Account_Reference>
                <wd:Last_4_Digits_of_Credit_Card_Number>6756</wd:Last_4_Digits_of_Credit_Card_Number>
                <wd:Credit_Card_Expiration_Date>2027-06-30</wd:Credit_Card_Expiration_Date>
                <wd:Cardmember_Embossed_Name>PAUL MITCHELL</wd:Cardmember_Embossed_Name>
                <wd:Document_Status_Reference>
                    <wd:ID wd:type="Document_Status_ID">ACTIVE</wd:ID>
                </wd:Document_Status_Reference>
                <wd:Cardholder_ID>12345</wd:Cardholder_ID>
            </wd:Credit_Card_Data>
        </wd:Card_Holder_Listing_File_Data>
    </bsvc:Credit_Card_Header__HV__Request>
</Root>

示例 XML:

<Root>
    <Set>
  
        <Blocks>
            
            <T3Block>
                <Header>
                    <CompanyId>xyz</CompanyId>
                    <SequenceNum>0</SequenceNum>
                    <ProcessingDate>08022024</ProcessingDate>
                    <RecordTypeCode>03</RecordTypeCode>
                    <RecordCount>0</RecordCount>
                    <TotalAmount>0</TotalAmount>
                    <LoadFileFormat>4.0</LoadFileFormat>
                    <IssuerIdNum>1423</IssuerIdNum>
                    <ProcessorIdNum>200</ProcessorIdNum>
                    <VisaRegionId>1</VisaRegionId>
                    <ProcessorPlatformRef>987</ProcessorPlatformRef>
                </Header>
                <T3Record>
                    <LoadTransCode>4</LoadTransCode>
                    <CardholderId>222</CardholderId>
                    <AcctNum>111</AcctNum>
                    <EffectiveDate>06052003</EffectiveDate>
                    <CardExpDate>06302027</CardExpDate>
                    <CorpPaymentIndicator>0</CorpPaymentIndicator>
                    <StatusCode>2</StatusCode>
                    <AcctTypeFlag>2</AcctTypeFlag>
                    <EmbossLine1>PAUL MITCHELL </EmbossLine1>
                </T3Record>
                <T3Record>
                    <LoadTransCode>4</LoadTransCode>
                    <CardholderId>333</CardholderId>
                    <AcctNum>111</AcctNum>
                    <EffectiveDate>01212004</EffectiveDate>
                    <CardExpDate>03312027</CardExpDate>
                    <CorpPaymentIndicator>0</CorpPaymentIndicator>
                    <StatusCode>2</StatusCode>
                    <AcctTypeFlag>2</AcctTypeFlag>
                    <EmbossLine1>MATTHEW A CARP</EmbossLine1>
                </T3Record>
</T3Block>
<T4Block>
                <Header>
                    <CompanyId>xyz</CompanyId>
                    <SequenceNum>0</SequenceNum>
                    <ProcessingDate>08022024</ProcessingDate>
                    <RecordTypeCode>04</RecordTypeCode>
                    <RecordCount>0</RecordCount>
                    <TotalAmount>0</TotalAmount>
                    <LoadFileFormat>4.0</LoadFileFormat>
                    <IssuerIdNum>1423</IssuerIdNum>
                    <ProcessorIdNum>200</ProcessorIdNum>
                    <VisaRegionId>1</VisaRegionId>
                    <ProcessorPlatformRef>987</ProcessorPlatformRef>
                </Header>
                <T4Record>
                    <LoadTransCode>4</LoadTransCode>
                    <CompanyId>xyz</CompanyId>
                    <CardholderId>222</CardholderId>
                    <FirstName>PAUL</FirstName>
                    <LastName>MITCHELL</LastName>
                    <EmployeeId>12345</EmployeeId>
                </T4Record>
                <T4Record>
                    <LoadTransCode>4</LoadTransCode>
                    <CompanyId>xyz</CompanyId>
                    <CardholderId>333</CardholderId>
                    <FirstName>MATTHEW</FirstName>
                    <LastName>CARP</LastName>
                   
                </T4Record>
</T4Block>
</Blocks>
    </Set>
</Root>
xslt-3.0 in-memory shallow-copy template-matching apply-templates
1个回答
0
投票

声明一下就足够了

<xsl:mode name="in-memory" on-no-match="shallow-skip"/>

© www.soinside.com 2019 - 2024. All rights reserved.