2

I have XPath expressions of the type //*[@id='test-id' and @some-other-attribute='some-value’]. I want to convert it into //*[@resourceId='android:id/test-id' and @some-other-attribute='some-value’].

I can't seem to find any library function to do that. I don't want to resort to regex find and replace on the string - looking for a structured way to do it. Appreciate any pointer.

NOTE: I am not looking to evaluate an XPath expression against an XML file. I am looking to modify the XPath expression itself, without resorting to string replace.

Update:

Following kjhughes@ recommendation, I got to the following code to get a parse tree of the xpath expression.

Processor proc = new Processor(false);
XPathCompiler p = new XPathCompiler(proc);
XPathExecutable exec = p.compile("//*[@id='test-id' and @some-other-attribute='some-value']");
exec.getUnderlyingExpression().getInternalExpression().explain(new StandardLogger());

This produces:

<filterExpression>
   <slash simple-step="true">
      <root/>
      <axis name="descendant" nodeTest="element()"/>
   </slash>
   <operator op="and">
      <operator op="=" cardinality="one-to-one">
         <data>
            <axis name="attribute" nodeTest="attribute(Q{}id)"/>
         </data>
         <literal value="test-id" type="xs:string"/>
      </operator>
      <operator op="=" cardinality="one-to-one">
         <data>
            <axis name="attribute" nodeTest="attribute(Q{}some-other-attribute)"/>
         </data>
         <literal value="some-value" type="xs:string"/>
      </operator>
   </operator>
</filterExpression>

Is my only option to parse the XML nodes and recompose the expression? Or is there a shorter way that I am missing?

(I still have to figure out if converting the XML back to Xpath expression is trivial or if it will involve any trickery.)

atlantis
  • 817
  • 1
  • 10
  • 16

2 Answers2

1

If you want to rewrite an XPath expression programatically then you would need to look into XPath parsers. See https://www.w3.org/2002/11/xquery-xpath-applets/xpathApplet.html for an example.

Martin Honnen
  • 160,499
  • 6
  • 90
  • 110
0

Here are two libraries that you can use to parse XPath expressions:

  1. Saxon's net.sf.saxon.s9api.XPathCompiler. You might also want to experiment with the explain() interface on compiled XPaths.
  2. The Jaxen XPath Engine for Java. Note, however, that Jaxen's support/stability has vacillated over time.

Given a choice, I'd develop against Saxonica's library.

Community
  • 1
  • 1
kjhughes
  • 106,133
  • 27
  • 181
  • 240
  • Thanks for the pointers. I checked Saxonica and got to the explain() part - but need some help moving forward. Updated my question as I need to post formatted code. – atlantis May 03 '16 at 23:57