Last active
August 29, 2015 14:04
-
-
Save gustavofonseca/e9d0656fd2c0e7f65393 to your computer and use it in GitHub Desktop.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
def get_xpath(element): | |
"""Get the XPath string to element. | |
This code is a port of a C# snippet published at | |
http://stackoverflow.com/a/9221904 | |
""" | |
path = '/' + element.tag | |
parent = element.getparent() | |
if parent is not None: | |
siblings = parent.findall(element.tag) | |
if len(siblings) > 1: | |
position = 1 | |
for sibling in siblings: | |
if sibling is element: | |
break | |
else: | |
position += 1 | |
path += '[%s]' % position | |
path = get_xpath(parent) + path | |
return path |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import unittest | |
from StringIO import StringIO | |
from lxml import etree | |
class GetXpathTests(unittest.TestCase): | |
def test_root_level(self): | |
sample = StringIO(""" | |
<article> | |
<front> | |
Hey! | |
</front> | |
</article> | |
""") | |
sample = etree.parse(sample) | |
element = sample.getroot() | |
self.assertEqual(utils.get_xpath(element), '/article') | |
def test_first_level(self): | |
sample = StringIO(""" | |
<article> | |
<front> | |
Hey! | |
</front> | |
</article> | |
""") | |
sample = etree.parse(sample) | |
element = sample.xpath('front')[0] | |
resulting_xpath = utils.get_xpath(element) | |
self.assertEqual(resulting_xpath, '/article/front') | |
self.assertIn(element, sample.xpath(resulting_xpath)) | |
def test_first_level_many(self): | |
sample = StringIO(""" | |
<article> | |
<front> | |
Hey! | |
</front> | |
<front> | |
You! | |
</front> | |
</article> | |
""") | |
sample = etree.parse(sample) | |
element = sample.xpath('front')[1] | |
resulting_xpath = utils.get_xpath(element) | |
self.assertEqual(resulting_xpath, '/article/front[2]') | |
self.assertIn(element, sample.xpath(resulting_xpath)) | |
def test_second_level(self): | |
sample = StringIO(""" | |
<article> | |
<front> | |
Hey! | |
<title> | |
Foobar | |
</title> | |
</front> | |
</article> | |
""") | |
sample = etree.parse(sample) | |
element = sample.xpath('front/title')[0] | |
resulting_xpath = utils.get_xpath(element) | |
self.assertEqual(resulting_xpath, '/article/front/title') | |
self.assertIn(element, sample.xpath(resulting_xpath)) | |
def test_first_level_many(self): | |
sample = StringIO(""" | |
<article> | |
<front> | |
Hey! | |
</front> | |
<front> | |
You! | |
<title> | |
Foobar | |
</title> | |
<title title-type="actual"> | |
Baz | |
</title> | |
</front> | |
</article> | |
""") | |
sample = etree.parse(sample) | |
element = sample.xpath('front/title[@title-type="actual"]')[0] | |
resulting_xpath = utils.get_xpath(element) | |
self.assertEqual(resulting_xpath, '/article/front[2]/title[2]') | |
self.assertIn(element, sample.xpath(resulting_xpath)) |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment