Je suis presque sûr que la réponse à cette question est non, mais comme la seule alternative est ce que je considère comme un code inélégant, j'ai pensé que je devais lancer cette question et voir si quelque chose me manque, tout en espérant que cela n'a pas été demandé.
Étant donné cette source XML :
<root>
<p>Hello world</p>
<move elem="content" item="test"/>
<p>Another text node.</p>
<content item="test">I can't <b>figure</b> this out.</content>
</root>
Je veux ce résultat :
<root>
<block>Hello world</block>
<newContent>I can't <hmmm>figure</hmmm> this out.</newContent>
<block>Another text node.</block>
</root>
Une description en langage ordinaire :
- Remplacer <move .../> par le résultat du traitement l'élément dont le nom correspond à l'attribut @elem de move et dont l'@item correspond à l'attribut @item de move (par exemple, dans ce cas, le contenu de l'élément [<content>] est traité de sorte que <b>est remplacé par <hmm>).
- Empêcher l'élément de l'étape 1 de soit écrit dans l'arbre de résultats dans son ordre original de document.
Le problème est que le document XML d'entrée sera considérablement plus complexe et variable. Et la feuille de style est un transformateur tiers que je développe. Le modèle que je devrais copier afin d'utiliser une solution basée sur le mode est d'une taille assez importante et cela me semble inélégant. Je sais, par exemple, que ceci pourrait fonctionner :
<xsl:template match="b">
<hmmm>
<xsl:apply-templates/>
</hmmm>
</xsl:template>
<xsl:template match="p">
<block>
<xsl:apply-templates/>
</block>
</xsl:template>
<xsl:template match="move">
<xsl:variable name="elem" select="@elem"/>
<xsl:variable name="item" select="@item"/>
<xsl:apply-templates select="//*[name()=$elem and @item=$item]" mode="copy-and-process"/>
</xsl:template>
<xsl:template match="content"/>
<xsl:template match="content" mode="copy-and-process">
<newContent><xsl:apply-templates/></newContent>
</xsl:template>
Ce que je voudrais faire, c'est que le <xsl:template> qui correspond à "content" soit sensible à ce que le nœud lui pousse. Ainsi, je peux avoir un <xsl:template match="content"/> qui n'est exécuté (et donc son nœud correspondant et ses enfants sont supprimés) que lorsque le nœud poussé est <Root> et non <move>. La vertu de cette méthode est que si le modèle pertinent de la feuille de style tierce est mis à jour, je n'ai pas à me soucier de mettre à jour une copie de la feuille de style qui traite le nœud <content>. Je suis presque sûr que ce n'est pas possible, mais j'ai pensé que cela valait la peine de poser la question.