Copie filtrée copy/element
Bonjour,
A partir du fichier XML suivant :
Code:
1 2 3 4 5 6
| <?xml version="1.0" ?>
<?xml-stylesheet href="monfichier.xsl" type="text/xsl" ?>
<a>
<ab x="x"><b>Test</b><a>z</a></ab>
<z x="x"><a>z</a></z>
</a> |
Je cherche à obtenir une copie filtrée (le même fichier sans la déclaration xml-stylesheet et avec uniquement les éléments dont le nom contient “a”):
Code:
1 2 3 4 5
| <?xml version="1.0" encoding="ISO-8859-1"?>
<a>
<ab x="x"><a>z</a></ab>
</a> |
Pour ça, j’examine les différences entre deux solutions possibles, les instructions ‘copy’ et ‘element’ :
AVEC COPY :
Code:
1 2 3 4 5 6 7
| <xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" version="1.0">
<xsl:output method="xml" version="1.0" encoding="ISO-8859-1"/>
<xsl:variable name="var" select="//[contains(name(),'a')]"/>
<xsl:template match="/">
<xsl:copy select="$v"/>
</xsl:template>
</xsl:stylesheet> |
Avec un ‘if’ :
Code:
1 2 3 4 5 6 7 8
| <xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" version="1.0">
<xsl:output method="xml" version="1.0" encoding="ISO-8859-1"/>
<xsl:template match="/">
<xsl:if test="*[contains(name(),'a')]">
<xsl:copy select="."/>
</xsl:if>
</xsl:template>
</xsl:stylesheet> |
AVEC ELEMENT:
Code:
1 2 3 4 5 6 7
| <xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" version="1.0">
<xsl:output method="xml" version="1.0" encoding="ISO-8859-1"/>
<xsl:variable name="ele" select="//[contains(name(),'a')]"/>
<xsl:template match="/">
<xsl:element name="{$ele}"/>
</xsl:template>
</xsl:stylesheet> |
Malheureusement, les deux codes me renvoient la même erreur dans Firefox :
« Erreur lors du chargement de la feuille de style : Échec de l'analyse XPath : test de Name ou de Nodetype attendu: »
Je dois dire que je ne comprends pas !! :(
Merci pour vos lumières !
Filtre avec xsl:element (plutôt que xsl:copy)
Bonjour, le code que vous m’avez proposé permet effectivement de copier les balises ‘a’ avec ce résultat :
Code:
1 2 3 4 5 6
| <?xml version="1.0" encoding="windows-1252"?>
<a>
<a>z</a>
<a>z</a>
</a> |
L’idée est en fait de sélectionner les balises dont le nom contient ‘a’ (comme les balises ‘ab’) mais aussi d’exclure les balises qui seraient imbriquées dans des balises qui ne correspondraient pas à ce schéma.
J’ai pris le problème autrement avec :
Code:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16
| <?xml version="1.0" encoding="ISO-8859-1"?>
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:output method="xml" version="1.0" encoding="ISO-8859-1" indent="yes"/>
<xsl:template match="node()">
<xsl:copy>
<xsl:apply-templates select="node()|@*"/>
</xsl:copy>
</xsl:template>
<xsl:template match="text()">
<xsl:value-of select="."/>
</xsl:template>
<xsl:template match="@*">
<xsl:attribute name="{name()}"><xsl:value-of select="."/></xsl:attribute>
</xsl:template>
<xsl:template match="//*[not(contains(name(),'a'))]"></xsl:template>
</xsl:stylesheet> |
Ce qui me donne:
Code:
1 2 3 4 5 6 7 8 9 10
| <?xml version="1.0" encoding="windows-1252"?>
<?xml-stylesheet href="source4_fichiers/monfichier.xml" type="text/xsl"?>
<a>
<ab x="x">
<a>z</a>
</ab>
</a> |
Je voudrais utiliser xsl:element plutôt que xsl :copy afin de pouvoir ajouter de nouvelles informations et pas seulement en soustraire. J’ai donc essayé le même code avec une simple substitution des balises xsl:copy par des balises xsl:element :
Code:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16
| <?xml version="1.0" encoding="ISO-8859-1"?>
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:output method="xml" version="1.0" encoding="ISO-8859-1" indent="yes"/>
<xsl:template match="node()">
<xsl:element>
<xsl:apply-templates select="node()|@*"/>
</xsl:element>
</xsl:template>
<xsl:template match="text()">
<xsl:value-of select="."/>
</xsl:template>
<xsl:template match="@*">
<xsl:attribute name="{name()}"><xsl:value-of select="."/></xsl:attribute>
</xsl:template>
<xsl:template match="//*[not(contains(name(),'a'))]"></xsl:template>
</xsl:stylesheet> |
Mais cela me donne l’erreur suivante :
Code:
Erreur lors du chargement de la feuille de style : Échec de l'analyse d'une feuille de style XSLT.
Je ne comprends pas pourquoi il doit y avoir des contraintes de syntaxe différentes.
Merci pour vos lumières !
Filtre avec xsl:element (plutôt que xsl:copy)
Voilà qui fonctionne pas mal ! :ccool: Un grand merci à vous Thelvin !
Code:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16
| <?xml version="1.0" encoding="ISO-8859-1"?>
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:output method="xml" version="1.0" encoding="ISO-8859-1" indent="yes"/>
<xsl:template match="node()">
<xsl:element name="{name(.)}">
<xsl:apply-templates select="node()|@*"/>
</xsl:element>
</xsl:template>
<xsl:template match="text()">
<xsl:value-of select="."/>
</xsl:template>
<xsl:template match="@*">
<xsl:attribute name="{name()}"><xsl:value-of select="."/></xsl:attribute>
</xsl:template>
<xsl:template match="//*[not(contains(name(),'a'))]"></xsl:template>
</xsl:stylesheet> |
Filtre avec xsl:element (plutôt que xsl:copy)
Ok et en deux mots, à quoi est-ce que vous réserveriez l'usage de <xsl:element> ? dans quelles conditions/situations est-ce que vous l'utiliseriez? Quel est son intérêt et sa spécificité? Je me référais à cela : http://infohost.nmt.edu/tcc/help/pub...l-element.html Mais effectivement, cette page web ne motive pas ce choix.