[xsl] evaluation of predicate using | mistyped as ||

Subject: [xsl] evaluation of predicate using | mistyped as ||
From: "Martin Honnen martin.honnen@xxxxxx" <xsl-list-service@xxxxxxxxxxxxxxxxxxxxxx>
Date: Thu, 11 Apr 2024 20:08:33 -0000
I wrote a stylesheet where I wanted to use a template with a match
pattern doing a union

B  <xsl:template match="node()[descendant::foo | self::foo |
ancestor::foo]">
B B B  <xsl:copy>
B B B B B  <xsl:apply-templates/>
B B B  </xsl:copy>
B  </xsl:template>


but I managed to mistype the second union | as a concat || and I first didn't notice other than wondering why my code didn't work as intended:

B  <xsl:template match="node()[descendant::foo | self::foo ||
ancestor::foo]">
B B B  <xsl:copy>
B B B B B  <xsl:apply-templates/>
B B B  </xsl:copy>
B  </xsl:template>

Now I wonder on how node()[descendant::foo | self::foo || ancestor::foo]
is evaluated but I am not sure.

Any idea what is supposed to happen if a union operator | and a concat
operator || are used in that way in the same predicate of a pattern? I
guess a type error and the pattern matches generating the type error
would be ignored.

Any idea in which way/order

B descendant::foo | self::foo || ancestor::foo

would be evaluated?

For what it's worth, Saxon 12 for an input like

<root>
B  <div>
B B B  <foo>a</foo>
B B B  <bar>1</bar>
B B B  <foo>b</foo>
B B B  <baz>2</baz>
B  </div>
</root>

and a complete stylesheet like

<?xml version="1.0" encoding="utf-8"?>
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform";
B  version="3.0"
B  xmlns:xs="http://www.w3.org/2001/XMLSchema";
B  exclude-result-prefixes="#all">

B  <xsl:template match="node()[descendant::foo | self::foo ||
ancestor::foo]">
B B B  <xsl:copy>
B B B B B  <xsl:apply-templates/>
B B B  </xsl:copy>
B  </xsl:template>

B <xsl:mode on-no-match="shallow-skip"/>

</xsl:stylesheet>

gives a single warning

Warning at char 7 in xsl:template/@match on line 7 column 78 of sheet3.xsl:
B  XPTY0004B  An error occurred matching pattern {node()[descendant::foo
| self::foo ||
B  ancestor::foo]}: A sequence of more than one item is not allowed as
the first argument of
B  fn:concat() (<foo>, <foo>)


I can see how descendant::foo can select two foo elements but wouldn't that happen twice, namely for the "root" element and for the "div" element? Shouldn't there be two such warnings?

Current Thread