tomcat-taglibs-user mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From Flavio Tordini <f.tord...@kataweb.it>
Subject Re: using Node variables with JSTL XML tags
Date Thu, 09 Sep 2004 09:13:45 GMT
hi Kris,
I think Xalan does the right thing evaluating

nodes = XPathAPI.selectNodeList(node, "/@name");

starting from the document root. The real problem is not being able to 
make *relative* XPath queries (without the starting slash). This seems 
to be a major flaw in the JSTL spec.

Since node variables set with x:set (obviously) work, I looked at the 
Jakarta impl sources to discover how x:set does the job. Basically it's 
a big *hack*:

- x:set evaluates the XPath expression with Xalan the wraps the Nodelist 
result into a org.apache.taglibs.standard.tag.common.xml.JSTLNodeList class.

- when x:out evaluates the XPath expression it checks for the $variable 
type:
   - if it is a JSTLNodeList containing 1 element of type 	 
org.w3c.dom.Node, it creates a new Document, imports the Node and then 
       (here comes the hack) it prepends "/*" to the user specified XPath:

xpath="/*" + xpath;
(org.apache.taglibs.standard.tag.common.xml.XPathUtil line 683)

   - if the $variable is a org.w3.dom.Node it is used as it is as the 
XPath Context as expected.

why this different treatment? obviously because of the Xalan behaviour 
that Kris explained. I think the same hack should be applied to Node 
variables so they work just like the impl-specific JSTLNodeList.

Any ideas? Any chance to let the developers know? They don't seem to be 
on this list at all...

flavio




Kris Schneider wrote:
> It seems like an issue with Xalan's XPath implementation. The Standard 1.1
> taglib uses Xalan while Standard 1.0 uses Jaxen/SAXPath. Here's an example app
> that mimics what it sounds like Flavio is trying to do:
> 
> import java.io.*;
> import javax.xml.parsers.*;
> import org.apache.xpath.*;
> import org.w3c.dom.*;
> import org.xml.sax.*;
> 
> public class XPathNode {
> 
>     private static final String XML =
>         "<root name=\"root\"><child name=\"child\"><grandchild
> name=\"grandchild\"></grandchild></child></root>";
> 
>     public static void main(String[] args) throws Exception {
>         DocumentBuilderFactory dbf = DocumentBuilderFactory.newInstance();
>         DocumentBuilder db = dbf.newDocumentBuilder();
>         Document doc = db.parse(new InputSource(new StringReader(XML)));
>         Element root = doc.getDocumentElement();
>         Node node = root.getFirstChild();
>         NodeList nodes = null;
> 
>         nodes = XPathAPI.selectNodeList(doc, "/root/child/@name");
>         printNodes(nodes);
> 
>         nodes = XPathAPI.selectNodeList(node, "/@name");
>         printNodes(nodes);
> 
>         nodes = XPathAPI.selectNodeList(node, "./@name");
>         printNodes(nodes);
>     }
> 
>     public static void printNodes(NodeList nodes) {
>         System.out.println("nodes:");
>         for (int i = 0, n = nodes.getLength(); i < n; i++) {
>             Node node = nodes.item(i);
>             System.out.println("\t" + node);
>         }
>     }
> }
> 
> Which results in:
> 
> nodes:
>     name="child"
> nodes:
> nodes:
>     name="child"
> 
> Notice that for the XPath evaluation to work with "node", I had to prepend "."
> to the expression. I'm not sure if it's possible to construct something similar
> with the "select" attribute of JSTL's x tags...
> 
> Quoting "Johnson, Chris" <chrisjohnson@ti.com>:
> 
> 
>>I see.  I ran across a similar problem with JDOM Xpath, although they
>>solved it in a newer version, but totally screwed up the API and some
>>other stuff, so it killed the fix for me.
>>
>>I had performance problems with the xml jstl tags (forEach), so I've
>>since moved on to using xslt.  They're clearly not in a big hurry to fix
>>these (what we would consider big) problems.
>>
>>Chris
>>
>>-----Original Message-----
>>From: Flavio Tordini [mailto:f.tordini@kataweb.it] 
>>Sent: Wednesday, September 08, 2004 10:36 AM
>>To: Tag Libraries Users List
>>Subject: Re: using Node variables with JSTL XML tags
>>
>>
>>hi chris,
>>thank you for your answer. The problem is i'm actually passing a *Node* 
>>to the tag, not a Document. So I'd like to evaluate the XPath starting 
>>from that Node, not from the root of the Document the Node belongs to.
>>
>>I also tried:
>><x:forEach select="$node">
>>   <x:out select="@name"/>
>></x:forEach>
>>
>>and it works. But it's kind of a hack. I'm not searching for a 
>>workaround, I need a clean solution since i'm working on a project that 
>>aims to simplify JSP development with the aid of the JSTL + plus a 
>>custom Servlet, and I cannot expect people to use this "forEach" hack.
>>
>>flavio
>>
>>Johnson, Chris wrote:
>>
>>>It seems that what 1.1 is doing is more correct.
>>>
>>>How do you expect jstl to find your sub node without telling it how to
>>
>>>get there?  That's how it works in directories on a computer (unix or 
>>>pc).  The only way that I know of to go to a subnode without providing
>>
>>>the full path is by using the // operator, like: 
>>>select="$doc//subnode". Otherwise, the only way (that I know of) to 
>>>"cd" to a subnode, and therefore not have to give the full path is by 
>>>using x:forEach.
>>>
>>>Chris
>>>
>>>-----Original Message-----
>>>From: Flavio Tordini [mailto:f.tordini@kataweb.it]
>>>Sent: Wednesday, September 08, 2004 9:37 AM
>>>To: Tag Libraries Users List
>>>Subject: Re: using Node variables with JSTL XML tags
>>>
>>>
>>>hi all,
>>>In the list archive, I found that the same question has been asked in
>>>June e never answered:
>>>
>>>http://www.mail-archive.com/taglibs-user@jakarta.apache.org/msg07315.h
>>>tm
>>>l
>>>
>>>should I post to the dev mailing list?
>>>should I report a bug?
>>>
>>>please someone answer!
>>>
>>>flavio
>>>
>>>Flavio Tordini wrote:
>>>
>>>
>>>>hi all,
>>>>I'm experimenting with the JSTL XML tags. I have a org.w3c.dom.Node 
>>>>variable and I'm trying to use the JSTL with it. Something like:
>>>>
>>>><x:out select="$node/@name"/>
>>>>
>>>>The odd thing is that the XPath expression is evaluated relative the 
>>>>document root, not to the specified node. The following works:
>>>>
>>>><x:out select="$node/full/path/to/node/@name"/>
>>>>
>>>>I cannot find an explanation in the JSTL 1.1 spec. The only thing I 
>>>>found is in section 11.1.3:
>>>>
>>>>"An XPath expression must also treat variables that resolve to 
>>>>implementations of standard DOM interfaces as representing nodes of
>>>
>>>the
>>>
>>>
>>>>type bound to that interface by the DOM specification."
>>>>
>>>>Is this behaviour by design? Is it compliant with the spec?
>>>>
>>>>Thank you in advance,
>>>>flavio
> 
> 

---------------------------------------------------------------------
To unsubscribe, e-mail: taglibs-user-unsubscribe@jakarta.apache.org
For additional commands, e-mail: taglibs-user-help@jakarta.apache.org


Mime
View raw message