Мои знания по XSLT все еще находятся в зачаточном состоянии, но я многое понял. Учитывая набор узлов, я могу применить шаблон для выбора узлов, который изменяет формат дат. Примерно так:
<?xml version="1.0" encoding="UTF-8"?>
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:output method="text" omit-xml-declaration="yes"/>
<xsl:template match="/Data">
<xsl:apply-templates select="Worker"/>
</xsl:template>
<xsl:template match="Worker">
<xsl:value-of select="LINE_NO"/>
<xsl:text>,</xsl:text>
<xsl:value-of select="WD_BATCH_ID"/>
<xsl:text>,</xsl:text>
<xsl:apply-templates select="./DATE_WORKED"/>
<xsl:text>,</xsl:text>
<xsl:apply-templates select="./EFFECTIVE_DATE"/>
<xsl:text>,</xsl:text>
<xsl:value-of select="HOURS"/>
<xsl:text>
</xsl:text>
</xsl:template>
<xsl:template match="Worker/node()">
<xsl:value-of select="concat('20',substring-after(substring-after(.,'-'),'-'))"/>
<xsl:text>-</xsl:text>
<xsl:choose>
<xsl:when test="contains(., 'JAN')">01</xsl:when>
<xsl:when test="contains(., 'FEB')">02</xsl:when>
<xsl:when test="contains(., 'MAR')">03</xsl:when>
<xsl:when test="contains(., 'APR')">04</xsl:when>
<xsl:when test="contains(., 'MAY')">05</xsl:when>
<xsl:when test="contains(., 'JUN')">06</xsl:when>
<xsl:when test="contains(., 'JUL')">07</xsl:when>
<xsl:when test="contains(., 'AUG')">08</xsl:when>
<xsl:when test="contains(., 'SEP')">09</xsl:when>
<xsl:when test="contains(., 'OCT')">10</xsl:when>
<xsl:when test="contains(., 'NOV')">11</xsl:when>
<xsl:when test="contains(., 'DEC')">12</xsl:when>
<xsl:otherwise></xsl:otherwise>
</xsl:choose>
<xsl:text>-</xsl:text>
<xsl:value-of select="substring-before(.,'-')"/>
</xsl:template>
</xsl:stylesheet>
Этот XSLT представляет собой прорыв в моем понимании XSLT, поэтому я немного горжусь этим ;-) Мне нравится тот факт, что я могу применить формат даты шаблон для любого прямого потомка Worker
, и все, что мне нужно сделать, это назвать дочерний узел. Этот случай производит файл CSV.
Я бы хотел сделать что-то подобное, но скопируйте XML, и без необходимости указывать каждый копируемый узел, только те, которые я хочу иметь в этом шаблоне формата даты.
Есть ли удобный способ агностически сказать "скопировать любой данный узел в этом XML, и если узел с именем DATE_WORKED
применить этот шаблон при копировании? Альтернативно, если есть какой-то способ, которым XSL может магически идентифицировать любой дата и просто отформатировать ее ... это было бы круто.
У меня есть доступ к XSL 1, 2 и 3.0
Я имею в виду что-то вроде:
<?xml version="1.0" encoding="UTF-8"?>
<xsl:stylesheet version="2.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:template match="/ | @* | node()">
<xsl:copy>
<xsl:apply-templates select="//DATE_WORKED" />
</xsl:copy>
</xsl:template>
<xsl:template match="Worker/node()">
<xsl:value-of select="concat('20',substring-after(substring-after(.,'-'),'-'))"/>
<xsl:text>-</xsl:text>
<xsl:choose>
<xsl:when test="contains(., 'JAN')">01</xsl:when>
<xsl:when test="contains(., 'FEB')">02</xsl:when>
<xsl:when test="contains(., 'MAR')">03</xsl:when>
<xsl:when test="contains(., 'APR')">04</xsl:when>
<xsl:when test="contains(., 'MAY')">05</xsl:when>
<xsl:when test="contains(., 'JUN')">06</xsl:when>
<xsl:when test="contains(., 'JUL')">07</xsl:when>
<xsl:when test="contains(., 'AUG')">08</xsl:when>
<xsl:when test="contains(., 'SEP')">09</xsl:when>
<xsl:when test="contains(., 'OCT')">10</xsl:when>
<xsl:when test="contains(., 'NOV')">11</xsl:when>
<xsl:when test="contains(., 'DEC')">12</xsl:when>
<xsl:otherwise></xsl:otherwise>
</xsl:choose>
<xsl:text>-</xsl:text>
<xsl:value-of select="substring-before(.,'-')"/>
</xsl:template>
</xsl:stylesheet>
... который не копирует узлы и работает только с узлами "DATE_WORKED".
Да, я нашел такой ответ: Использование XSLT для копирования всех узлов в XML с поддержкой особых случаев Но для каждого узла, который я хочу отформатировать, потребуется создать дубликат шаблона.
Я работаю с XML, который выглядит следующим образом:
<?xml version='1.0' encoding='UTF-8'?>
<Data>
<Worker>
<LINE_NO>LineNo</LINE_NO>
<INT_ID>IntId</INT_ID>
<WD_BATCH_ID>WdBatchId</WD_BATCH_ID>
<WD_PAY_INPUT_ID>WdPayInputId</WD_PAY_INPUT_ID>
<DATE_WORKED>DateWorked</DATE_WORKED>
<EMPLOYEE_ID>EmployeeId</EMPLOYEE_ID>
<WEEK_END_DATE>WeekEndDate</WEEK_END_DATE>
<EFFECTIVE_DATE>EffectiveDate</EFFECTIVE_DATE>
<HOURS>Hours</HOURS>
<PAY_COMPONENT>PayComponent</PAY_COMPONENT>
<TK_COMMENTS>TkComments</TK_COMMENTS>
<SS_REQUEST_ID>SsRequestId</SS_REQUEST_ID>
<REQUEST_ID>RequestId</REQUEST_ID>
<PROCESS_STATUS>ProcessStatus</PROCESS_STATUS>
</Worker>
<Worker>
<LINE_NO>0001</LINE_NO>
<INT_ID>248697</INT_ID>
<WD_BATCH_ID>kns_timeoff20191215_7_78593974</WD_BATCH_ID>
<WD_PAY_INPUT_ID>248696</WD_PAY_INPUT_ID>
<DATE_WORKED>25-NOV-19</DATE_WORKED>
<EMPLOYEE_ID>101877</EMPLOYEE_ID>
<WEEK_END_DATE>01-DEC-19</WEEK_END_DATE>
<EFFECTIVE_DATE>15-DEC-19</EFFECTIVE_DATE>
<HOURS>9</HOURS>
<PAY_COMPONENT>Military AD</PAY_COMPONENT>
<TK_COMMENTS>.</TK_COMMENTS>
<SS_REQUEST_ID>78593755</SS_REQUEST_ID>
<REQUEST_ID>78593974</REQUEST_ID>
<PROCESS_STATUS>C</PROCESS_STATUS>
</Worker>
<Worker>
<LINE_NO>0002</LINE_NO>
<INT_ID>248701</INT_ID>
<WD_BATCH_ID>kns_timeoff20191215_7_78593974</WD_BATCH_ID>
<WD_PAY_INPUT_ID>248700</WD_PAY_INPUT_ID>
<DATE_WORKED>26-NOV-19</DATE_WORKED>
<EMPLOYEE_ID>101877</EMPLOYEE_ID>
<WEEK_END_DATE>01-DEC-19</WEEK_END_DATE>
<EFFECTIVE_DATE>15-DEC-19</EFFECTIVE_DATE>
<HOURS>9</HOURS>
<PAY_COMPONENT>Military AD</PAY_COMPONENT>
<TK_COMMENTS>.</TK_COMMENTS>
<SS_REQUEST_ID>78593755</SS_REQUEST_ID>
<REQUEST_ID>78593974</REQUEST_ID>
<PROCESS_STATUS>C</PROCESS_STATUS>
</Worker>
<Worker>
<LINE_NO>0003</LINE_NO>
<INT_ID>248699</INT_ID>
<WD_BATCH_ID>kns_timeoff20191215_7_78593974</WD_BATCH_ID>
<WD_PAY_INPUT_ID>248698</WD_PAY_INPUT_ID>
<DATE_WORKED>27-NOV-19</DATE_WORKED>
<EMPLOYEE_ID>101877</EMPLOYEE_ID>
<WEEK_END_DATE>01-DEC-19</WEEK_END_DATE>
<EFFECTIVE_DATE>15-DEC-19</EFFECTIVE_DATE>
<HOURS>9</HOURS>
<PAY_COMPONENT>Military AD</PAY_COMPONENT>
<TK_COMMENTS>.</TK_COMMENTS>
<SS_REQUEST_ID>78593755</SS_REQUEST_ID>
<REQUEST_ID>78593974</REQUEST_ID>
<PROCESS_STATUS>C</PROCESS_STATUS>
</Worker>
<Worker>
<LINE_NO>0004</LINE_NO>
<INT_ID>1082611</INT_ID>
<WD_BATCH_ID>kns_wd20191215_8_78593974</WD_BATCH_ID>
<WD_PAY_INPUT_ID>WK1.1082611</WD_PAY_INPUT_ID>
<DATE_WORKED>01-DEC-19</DATE_WORKED>
<EMPLOYEE_ID>101877</EMPLOYEE_ID>
<WEEK_END_DATE>01-DEC-19</WEEK_END_DATE>
<EFFECTIVE_DATE>15-DEC-19</EFFECTIVE_DATE>
<HOURS>7</HOURS>
<PAY_COMPONENT>EWWHRWK1</PAY_COMPONENT>
<TK_COMMENTS>.</TK_COMMENTS>
<SS_REQUEST_ID>78593755</SS_REQUEST_ID>
<REQUEST_ID>78593974</REQUEST_ID>
<PROCESS_STATUS>C</PROCESS_STATUS>
</Worker>
</Data>