Having looked at various popular modules for working with XML / XPath I have yet to see a straight-forward way to achieve this.
Essentially the interface would look something like:
my $xpath = get_path($node1, $node2);
…which would return the relative path from $node1 to $node2.
I include my own time in the calculation of ‘efficiency’ – I’ll take any existing solution for this problem. Failing that, I’d like to know some of the pitfalls one might come up against in any ‘obvious’ home-grown solutions.
Off the top of my head I could imagine simply first searching for $node2 in $node1’s descendants, then failing that iterate up $node1’s ancestors doing the same thing. Would that be as raucously resource-intensive as I fear?
For my particular use-case, I can assume the absolute paths of both $node1 and $node2 are known. Given that, I would like to think there’s some ‘XPath math’ that could be done between the two full paths without having to run about all over the tree, but I don’t know what that process would look like.
To summarise:
1) Do any existing CPAN modules make what I want to do easy?
2) If not, what’s an efficient way to go about it?
Find the absolute path for both nodes.
Remove common leading segments.
For each segment in the reference, prepend the target with a
..segment.Convert to XPath.
Code:
It currently supports element and attribute nodes. It could be expanded to support other node types, possibly trivially.