Re: [xsl] build a select clause or dynamic URI's

Subject: Re: [xsl] build a select clause or dynamic URI's
From: "M. David Peterson" <m.david@xxxxxxxxxx>
Date: Tue, 09 Nov 2004 16:21:46 -0800
Andy Dent wrote:

I summarise what I need as wanting to go from a string value in an
attribute to having the nodeset it refers to. So, given an href like
"../../../gml:position" I can write a generic template to invoke the
original gml:position template.

Unfortunately you can't create dynamic XPath expression in XSLT (1.0 or 2.0). The best you can do is use recursive named templates to strip away a string one '/' at a time and then attempt to crawl forward or backwards through your source XML by matching the string to an element name in your XML data using the name() or local-name() functions... Heres an old post that utitlizes this concept to build a Yahoo-style directory by using the directory path passed to the stylesheet as a parameter... http://www.biglist.com/lists/xsl-list/archives/200405/msg00288.html


I wouldnt put too much weight on the above link as this example has a definite starting point and a structure that is somewhat predictable and its sounds as if your example could potentially be linking to node all over the place with no real sense of order which would be a shear nightmare to try and implement recursive named templates in any sense of accuracy.... not to mention the performance crunch... Ouch!


I've experimented with the document function and just had someone else suggest it may help but I'm not sure how to use document to refer to a different location in the current source.

You can use the document function to either reference external documents or as a self reference... to self reference you use an empty string as such....


document('')

and then reference the document starting at the root and moving forward... the easiest and shortest way to get inside of your stylesheet is to use the wild card reference as your first step and then access the correct child elements of xsl:stylesheet from there:

document('')/*/xsl:template[@match = 'foo']

But given this knowledge I have my doubts that its going to be all that helpful to you as it doesnt seem that you want to reference the actual stylesheet itself... or maybe you do and I'm just misunderstanding your needs.


Say we have some XML with a relative ref back in the file, like: <featureMember> <GeochemSpecimen gml:id="WA_1_139459"> <gml:name>139459</gml:name> <gml:position xlink:href="urn:x-seegrid:definition:gml:NilReason:unknown"/> <material>rock</material> <relatedObservation> <GeochemMeasurement gml:id="WA_1_139459_Ag">

<gml:position xlink:href="../../../gml:position"/>


The only real chance you have of being able to do any sort of pseudo dynamic XPath expression is if, for example, there is only one ancestor gml:position for any given element. If this were the case you could use a recursive template to strip away the the dots and slashes (for that matter you could use the translate function to replace the . and / with nothing and then simply use the ancestor axis and the name() or local-name() functions to access the ancestor with a name or local-name = to the remaining string.... e..g <xsl:apply-templates select="ancestor::*[name() = translate(@xlink:href, './', '')]"/>. Still not an ideal situation I realize but if there is limitations to the ancestor count of a particular elements name then you may have a fighting chance with something like this...

Hope this helps get some ideas flowing for you!

Best regards,

<M:D/>

Current Thread