0
votes

I have the following xml.

<?xml version="1.0" encoding="UTF-8"?>
<root xmlns="urn:iso:std:iso:20022:tech:xsd:pain.001.001.03"
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
    <a>124!</a>
    <b>$ Dolar</b>
    <c> # number</c>
    <d bu='5'>space space</d>
    <e>
        <one>! one</one>
        <two>two @</two>
        <three>
            <four>$ four</four>
            <five>% five</five>
                <six thisIsSix='six' sevrn='red'>
                    <seven>7</seven>
                </six>
        </three>
    </e>
    <f>@ at</f>
</root>

I use the following xsl to remove special characters

<?xml version="1.0" encoding="UTF-8"?>
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
    xmlns:xs="http://www.w3.org/2001/XMLSchema" exclude-result-prefixes="xs" version="2.0">

    <xsl:output indent="yes" media-type="xml"/>

    <xsl:template match="/">
        <xsl:copy>
            <xsl:apply-templates select="node()"/>
        </xsl:copy>
    </xsl:template>


    <xsl:template match="*">
        <xsl:element name="{local-name()}" namespace="{namespace-uri()}">
            <xsl:if test="@*">
                <xsl:for-each select="@*">
                    <xsl:attribute name="{./local-name()}" select="."/>
                </xsl:for-each>
            </xsl:if>
            <xsl:choose>
                <xsl:when test="./*">
                        <xsl:apply-templates select="node()"/>
                </xsl:when>
                <xsl:otherwise>
                        <xsl:copy
                            select="normalize-space(replace(., '[^A-Za-z0-9.@:\-_ ]', ' '))"/>
                </xsl:otherwise>
            </xsl:choose>
        </xsl:element>
    </xsl:template>

</xsl:stylesheet>

It works well when I run this in oxygen xml editor. when I deploy this to a target system it complains about:

  1. Attribute 'select' is not allowed to appear in element 'xsl:copy'.
  2. When I run this - Errors were reported during stylesheet compilation Required item type of @select attribute of xsl:apply-templates is node(); supplied value has item type xs:string

How can I refactor this?

Thank you

1

1 Answers

0
votes

Write a template for text nodes:

<xsl:template match="text()"><xsl:value-of select="normalize-space(replace(., '[^A-Za-z0-9.@:\-_ ]', ' '))"/></xsl:template>

handle the rest by the identity transformation

<xsl:template match="@* | node()">
  <xsl:copy>
    <xsl:apply-templates select="@* | node()">
  </xsl:copy>
</xsl:template>