2015-07-24 1 views
0

принимая во внимание следующие входных XML:XSLT 1.0, XML в CSV: как получить заголовки из атрибутов и дочерние узлы

<LIST> 
    <DIRECTORIES> 
     <DIRECTORY ID="000001"> 
      <NAME>folder</NAME> 
      <LOCATION>C:\here</LOCATION> 
     </DIRECTORY> 
     <DIRECTORY ID="000002"> 
      <COLOR>blue</COLOR> 
      <LOCATION>C:\here</LOCATION> 
      <DATE>01-25-2015</DATE> 
     </DIRECTORY> 
    <DIRECTORIES> 
    <FILES> 
     <FILE ID="000001"> 
      <NAME>file</NAME> 
      <TYPE>rt</TYPE> 
      <SERVICE>inf</SERVICE> 
     </FILE> 
     <FILE ID="000002"> 
      <NAME>f</NAME> 
     </FILE> 
    </FILES> 
<LIST> 

я хотел бы получить содержание каталогов, с одной головой на ребенок отчетливую справочника узел и атрибуты. В этом примере, желаемый результат будет:

ID, NAME, LOCATION, COLOR, DATE 
000001, folder, C:\here,, 
000002,,C:\here,blue,01-25-2015 

Есть много вопросов, касающихся XML для преобразования CSV, так что я пытался настроить решение предлагается в другой, но безуспешно. Вот мой XSLT:

<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"> 
    <xsl:output method="text"/> 
    <xsl:variable name="delimiter" select="','"/> 

    <xsl:key name="directoryFields" match="/LIST/DIRECTORIES/DIRECTORY/*" use="local-name()"/> 

    <xsl:variable name="dirFields" 
     select="/LIST/DIRECTORIES/DIRECTORY/*[generate-id()=generate-id(key('directoryFields', local-name())[1])]" /> 

    <xsl:template match="/"> 
    <xsl:for-each select="$dirFields"> 
     <xsl:value-of select="local-name()" /> 
     <xsl:if test="position() &lt; last()"> 
     <xsl:value-of select="$delimiter" /> 
     </xsl:if> 
    </xsl:for-each> 
    <xsl:text>&#10;</xsl:text> 
    <xsl:apply-templates select="*/*" /> 
    </xsl:template> 

    <xsl:template match="*"> 
    <xsl:variable name="this" select="." /> 
    <xsl:for-each select="$dirFields"> 
     <xsl:value-of select="$this/*[local-name() = local-name(current())]" /> 
     <xsl:if test="position() &lt; last()"> 
     <xsl:value-of select="$delimiter" /> 
     </xsl:if> 
    </xsl:for-each> 
    <xsl:text>&#10;</xsl:text> 
    </xsl:template> 
</xsl:stylesheet> 

ответ

1

Ну:

<xsl:apply-templates select="*/*" /> 

должны быть:

<xsl:apply-templates select="LIST/DIRECTORIES/DIRECTORY" /> 

То, что вы выбираете LIST/DIRECTORIES. И вы не можете использовать */*/*, потому что это также выбирает узлы FILE.

Кроме того, необходимо удалить эту строку:

<xsl:value-of select="/LIST/DIRECTORIES/DIRECTORY"/> 

добавляемые

Для того, чтобы включать в себя идентификатор, необходимо добавить следующее:

<xsl:value-of select="concat(@ID, $delimiter)" /> 

к обработке шаблонов DIRE CTORY, прежде чем переходить к обработке полей.

+0

Упс для этой последней строки, это был тест, который я забыл удалить. Это не полностью решает мою проблему, но это помогает. – Kilazur

+0

@ Kilazur "* Это не полностью решает мою проблему *« Почему бы и нет? –

+0

Это не говорит мне, как объединить атрибуты и дочерние узлы вместе как список полей CSV. – Kilazur

Смежные вопросы