У нас есть формат XML, который на самом деле представляет собой просто HTML с некоторыми дополнительными шаблонами. Он определяет, какие элементы HTML доступны для редактирования, а какие атрибуты являются редактируемыми.
Вот пример
<img src="images/placeholder.jpg"
alt="Placeholder"
width="600"
height="250"
border="0">
<var attr="src" />
<var attr="height" ok="150-300" />
</img>
XML так, что шаблоны легче писать, но мне нужно преобразовать его в действительный (ish) HTML. Для этого я хочу свернуть это в:
<img src="images/placeholder.jpg"
alt="Placeholder"
width="600"
height="250"
border="0"
editable="src height"
constraints="height:150-300">
Я могу сделать это для <img>
, но проблема в том, что теги <var>
могут фактически появляться как дочерние элементы любого элемента на странице. Во всех случаях алгоритм преобразования его в атрибуты один и тот же, но я не могу понять, как это сделать, это указать шаблон XSLT, который может соответствовать родительскому элементу тега <var>
. Я пытался match="var/.."
, но это оказалось недействительным.
Альтернативой может быть сопоставление <var>
s и добавление их в качестве атрибутов их родителям, но я считаю, что на этом этапе обработки этот конкретный корабль уже проплыл.
Это выполнимо?
Thankies
Ответ!
Я объединил более полный ответ с полезным и точным ответом Димитра, чтобы получить следующее:
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" version="1.0">
<xsl:template match="*[var]">
<xsl:copy >
<xsl:attribute name="editable">
<xsl:for-each select="var[@attr]">
<xsl:value-of
select="concat(@attr,
substring(' ',
1 div (position()!=last())))"/>
</xsl:for-each>
</xsl:attribute>
<xsl:attribute name="constraints">
<xsl:for-each select="var[@ok]">
<xsl:value-of
select="concat(@attr,':',@ok,
substring(';',
1 div (position()!=last())))"/>
</xsl:for-each>
</xsl:attribute>
<xsl:apply-templates select="@*"/>
</xsl:copy>
</xsl:template>
<xsl:template match="var">
</xsl:template>
<xsl:template match="@*|node()">
<xsl:copy>
<xsl:apply-templates select="@*|node()"/>
</xsl:copy>
</xsl:template>
</xsl:stylesheet>
К сожалению, точный ответ, который дал Алехандро, сразу не сработал (но до сих пор не уверен, почему), но эта комбинация его ответа и ответа Дмитрия, похоже, хорошо сработала:)