Получение значения элемента с помощью XSLT и удаление его - PullRequest
1 голос
/ 04 мая 2011

Я использую XSLT для очистки некоторых связанных с InDesign XML для использования в других системах. Мне нужно иметь возможность получить значение из тегов, вложенных в текстовое тело, а затем удалить их.

В частности, заголовок и подпись встроены в текстовое тело. Мне нужно уметь их извлекать и помещать в теги заголовка - я могу это сделать, но я не могу вытащить их из тела, пока я на этом.

Вот мой (упрощенный) XML:

<?xml version="1.0" encoding="UTF-8"?>
<k4Export xmlns="http://www.vjoon.com/K4Export/1.4.2">  
    <publication>
        <id>107233722</id>
        <name>NGM</name>
        <origin>origin</origin>
        <issue>
            <article>
                <textObjects>
                    <textObject>
                        <text>
                            <inlineTag name="Story">
                                <inlineTag name="body">
                                    <inlineTag name="headline">The Headline</inlineTag> Lorem ipsum dolor sit amet, 
                                    consectetur adipiscing elit. <em>Vivamus mollis</em> ligula quis mi
                                     blandit interdum. In rutrum imperdiet suscipit. Fusce interdum, 
                                    sem id scelerisque molestie, purus ligula fringilla sapien, nec
                                     auctor velit eros eget felis. Duis eu tellus purus. Donec id viverra
                                     neque.</inlineTag>

                                    <inlineTag name="body">Donec nec nulla neque, sit amet placerat 
                                        elit. Nulla pulvinar elit sapien. Donec venenatis, arcu sed
                                         pellentesque ultrices, neque mi sollicitudin elit, nec fermentum
                                         eros nibh aliquam leo. Nam lectus neque, dapibus in scelerisque
                                         in, fermentum nec ipsum.</inlineTag>

                                    <inlineTag name="body">Sed sed <strong>congue</strong> neque. Nulla
                                     nec ipsum vitae lacus consectetur convallis sed et nulla. Integer
                                     posuere viverra felis, at pulvinar risus scelerisque ac. Aliquam a
                                     orci ac est iaculis porta. Duis sollicitudin lectus sit amet velit
                                     condimentum lobortis.
                                    <inlineTag name="byline">-John Doe</inlineTag></inlineTag></inlineTag>
                        </text>
                    </textObject>
                </textObjects>
            </article>
        </issue>
    </publication>
</k4Export>

А вот XSLT, который я использую для преобразования. Я могу получить заголовок и подпись в заголовке, но я не могу извлечь его из содержания. Я нуб XSLT, поэтому любые советы будут оценены. Элементы textObject распространены по всему документу XML, поэтому я намеренно использую очень общие селекторы XPath, чтобы добраться до них.

<?xml version="1.0" encoding="UTF-8"?>

<xsl:stylesheet 
    xmlns:default="http://www.vjoon.com/K4Export/1.4.2" 
    xmlns:xsl="http://www.w3.org/1999/XSL/Transform" 
    version="2.0"
    exclude-result-prefixes="default">

    <!-- Output Content -->
    <xsl:template match="/">
        <html>
            <head>
                <title>Sample</title>
            </head>

            <body>

                <!-- Headline-->
                <xsl:variable name="headlines" select="//default:inlineTag[@name='headline']" />
                <xsl:choose>
                    <xsl:when test="$headlines">
                        <xsl:for-each select="$headlines">
                            <h1 class="headline"><xsl:value-of select="node()"/></h1>
                        </xsl:for-each>
                    </xsl:when>
                    <xsl:otherwise>
                        <h1 class="headline">Headline Absent</h1>
                    </xsl:otherwise>
                </xsl:choose>

                <!-- Bylines -->
                <xsl:variable name="bylines" select="//default:inlineTag[@name='byline']" />
                <xsl:choose>
                    <xsl:when test="$bylines">
                        <xsl:for-each select="$bylines">
                            <h2 class="byline"><xsl:value-of select="node()"/></h2>
                        </xsl:for-each>
                    </xsl:when>
                    <xsl:otherwise>
                        <h2 class="byline">Byline Absent</h2>
                    </xsl:otherwise>
                </xsl:choose>

                <div id="content">

                    <!-- body -->
                    <xsl:variable name="bodies" select="//default:inlineTag[@name='body']" />
                    <xsl:choose>
                        <xsl:when test="$bodies">
                            <xsl:for-each select="$bodies">
                                <p><xsl:value-of select="node()"/></p>
                            </xsl:for-each>
                        </xsl:when>
                    </xsl:choose>

                </div>

            </body>
        </html>

    </xsl:template>

</xsl:stylesheet>

1 Ответ

1 голос
/ 04 мая 2011

Я думаю, что вы хотите что-то вроде этого (обратите внимание, что <xsl:for-each> теперь заменен на <xsl:apply-templates> и существуют разные шаблоны для обработки элементов inlineTag с разными значениями их атрибута name. В частности, пусто -bodied-шаблоны не копируют соответствующий узел в вывод). Кроме этого, я не предпринимал никаких попыток перефакторинга или улучшения вашего кода - у него большой потенциал для улучшения.

Результат теперь не содержит ни заголовка, ни подписи .

<xsl:stylesheet      xmlns:default="http://www.vjoon.com/K4Export/1.4.2"      xmlns:xsl="http://www.w3.org/1999/XSL/Transform"      version="2.0"     exclude-result-prefixes="default">
    <!-- Output Content -->
    <xsl:template match="/">
        <html>
            <head>
                <title>Sample</title>
            </head>
            <body>
                <!-- Headline-->
                <xsl:variable name="headlines" select="//default:inlineTag[@name='headline']" />
                <xsl:choose>
                    <xsl:when test="$headlines">
                        <xsl:for-each select="$headlines">
                            <h1 class="headline">
                                <xsl:value-of select="node()"/>
                            </h1>
                        </xsl:for-each>
                    </xsl:when>
                    <xsl:otherwise>
                        <h1 class="headline">Headline Absent</h1>
                    </xsl:otherwise>
                </xsl:choose>
                <!-- Bylines -->
                <xsl:variable name="bylines" select="//default:inlineTag[@name='byline']" />
                <xsl:choose>
                    <xsl:when test="$bylines">
                        <xsl:for-each select="$bylines">
                            <h2 class="byline">
                                <xsl:value-of select="node()"/>
                            </h2>
                        </xsl:for-each>
                    </xsl:when>
                    <xsl:otherwise>
                        <h2 class="byline">Byline Absent</h2>
                    </xsl:otherwise>
                </xsl:choose>
                <div id="content">
                    <!-- body -->
                    <xsl:apply-templates select="//default:inlineTag[@name='body']" />
                </div>
            </body>
        </html>
    </xsl:template>

    <xsl:template match="default:inlineTag[@name='body']">
      <p>
        <xsl:apply-templates/>
      </p>
    </xsl:template>

    <xsl:template priority="10" match=
    "default:inlineTag[@name='byline' or @name='headline']"/>

</xsl:stylesheet>
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...