Very reassuring -- I hope you're having a great 2022 so far Eliot!
Cheers, Wendell
On Tue, Jan 4, 2022 at 3:53 PM Eliot Kimber
eliot(_dot_)kimber(_at_)servicenow(_dot_)com <
xsl-list-service(_at_)lists(_dot_)mulberrytech(_dot_)com> wrote:
Note that this function:
<xsl:function name="mine:is-trim-element" as="xs:boolean">
<xsl:param name="elt" as="node()"/>
<xsl:value-of select="exists($elt[self::desc or self::dt or
self::endnote or self::entry or self::example-title or self::glossterm or
self::li or self::msg-severity or self::p or self::shortdesc or self::title
or self::value-allowed or self::value-default or self::value-type])"/>
</xsl:function>
Should use xsl:sequence instead of value-of as you want to return a
Boolean value.
By using value-of you are effectively constructing a Boolean (result of
exists()) then converting that to a text node (result of value-of) and then
XSLT implicitly converts that back to a Boolean using the string value of
the text node.
In general, you almost always want xsl:sequence unless what you really
want is a text node (for example, because you’re contributing to the
content of a result element).
[Wendell beat me to this suggestion but I’d already written it:]
As for the question of determining the type: I think I would follow
Dimitre’s advice and use templates :
<xsl:function name=”mine:is-trim-element” as=”xs:boolean”>
<xsl:param name="elt" as="node()"/>
<xsl:apply-templates select=”$elt” mode=” mine:is-trim-element”/>
</xsl:function>
<xsl:template mode=” mine:is-trim-element” as=”xs:Boolean”
match=”desc | endnote | dt”
>
<xsl:sequence select=”true()”/>
</xsl:template>
<xsl:template mode=” mine:is-trim-element” as=”xs:Boolean” priority=”-1”
match=”*”>
<xsl:sequence select=”false()”
</xsl:template>
This makes the logic for determining type extensible using normal
extension mechanisms.
Cheers,
E.
_____________________________________________
*Eliot Kimber*
Sr Staff Content Engineer
O: 512 554 9368
M: 512 554 9368
servicenow.com <https://www.servicenow.com>
LinkedIn <https://www.linkedin.com/company/servicenow> | Twitter
<https://twitter.com/servicenow> | YouTube
<https://www.youtube.com/user/servicenowinc> | Facebook
<https://www.facebook.com/servicenow>
*From: *Chris Papademetrious
christopher(_dot_)papademetrious(_at_)synopsys(_dot_)com <
xsl-list-service(_at_)lists(_dot_)mulberrytech(_dot_)com>
*Date: *Tuesday, January 4, 2022 at 2:37 PM
*To: *xsl-list(_at_)lists(_dot_)mulberrytech(_dot_)com
<xsl-list(_at_)lists(_dot_)mulberrytech(_dot_)com>
*Subject: *Re: [xsl] Using node-set variables in predicates (another node
comparison question)
*[External Email]*
Hi Dimitre,
That is good advice about functions – I will keep it in mind!
Hi everyone,
So I ran into a limitation of using document node-set variables in
template match expressions:
<!-- put document nodes in $trim-elements -->
<xsl:variable name="trim-elements"
select="//(desc|dt|entry|glossterm|li|p|shortdesc|title)"/>
<!-- reference elements in $trim-elements -->
<xsl:template match="text()
[matches(., '^\s+')]
[ancestor::*[. intersect
$trim-elements][not(descendant::*[. intersect $trim-elements])]]
[not(ancestor-or-self::node()
[ancestor::*[. intersect
$trim-elements][not(descendant::*[. intersect $trim-elements])]]
[preceding-sibling::node()])]">
When I constructed a temporary <p> node in a variable:
xsl:variable name="temporary-p">
<p><xsl:copy-of select=”…blah blah…”></p>
</xsl:variable>
then called <xsl:apply-templates> to apply the template:
<xsl:apply-templates select="$temporary-p"/>
the template did not get applied. This makes perfect sense – my temporary
<p> variable does not contain any document nodes at all, so the template
match expression would never match!
But with Dimitre’s advice about functions fresh in my mind, I converted my
document-node variable into a node-type function:
<xsl:function name="mine:is-trim-element" as="xs:boolean">
<xsl:param name="elt" as="node()"/>
<xsl:value-of select="exists($elt[self::desc or self::dt or
self::endnote or self::entry or self::example-title or self::glossterm or
self::li or self::msg-severity or self::p or self::shortdesc or self::title
or self::value-allowed or self::value-default or self::value-type])"/>
</xsl:function>
Now I can use the function instead of the variable in the match expression:
<xsl:template match="text()
[matches(., '^\s+')]
[ancestor::*[mine:is-trim-element(.)][not(descendant::*[mine:is-trim-element(.)])]]
[not(ancestor-or-self::node()
[ancestor::*[mine:is-trim-element(.)][not(descendant::*[mine:is-trim-element(.)])]]
[preceding-sibling::node()[not(mine:is-invisible(.))]])]">
and the template applies as expected to my temporary variable!
Follow-up question – is there some syntactic sugar that would allow me to
write
self::(a|b|c)
instead of
(self::a or self::b or self::c)
or some other way of testing the element type in $elt altogether? I have
another function that matches several dozen element types, and a more
compact representation would be nice. I thought about matching local-name()
against a list of tag names using “intersect”, but that is not much shorter
and it seems operationally clunkier.
Thanks, this has been an enjoyable exercise for learning!
- Chris
XSL-List info and archive
<https://urldefense.com/v3/__http:/www.mulberrytech.com/xsl/xsl-list__;!!N4vogdjhuJM!QoTfzk5BnM0e2UXvfQdi8oQSTETaMkscgawE6XS1ls6pK21OytP7rdlPobZYmhyWkmh8Ow$>
EasyUnsubscribe
<https://urldefense.com/v3/__http:/lists.mulberrytech.com/unsub/xsl-list/3453418__;!!N4vogdjhuJM!QoTfzk5BnM0e2UXvfQdi8oQSTETaMkscgawE6XS1ls6pK21OytP7rdlPobZYmhxv1pEexw$>
(by email)
XSL-List info and archive <http://www.mulberrytech.com/xsl/xsl-list>
EasyUnsubscribe <http://lists.mulberrytech.com/unsub/xsl-list/174322> (by
email <>)
--
...Wendell Piez... ...wendell -at- nist -dot- gov...
...wendellpiez.com... ...pellucidliterature.org... ...pausepress.org...
...github.com/wendellpiez... ...gitlab.coko.foundation/wendell...
--~----------------------------------------------------------------
XSL-List info and archive: http://www.mulberrytech.com/xsl/xsl-list
EasyUnsubscribe: http://lists.mulberrytech.com/unsub/xsl-list/1167547
or by email: xsl-list-unsub(_at_)lists(_dot_)mulberrytech(_dot_)com
--~--