Автоматизация seleniumа – поиск наилучшего xpath

Я стараюсь избегать использования xpaths, которые являются «положением xpath». Причина в том, что xpath может измениться и завершиться автоматическим тестом, если новый объект находится на странице и сдвигает ожидаемую позицию xpath.

Но на некоторых веб-страницах это единственный xpath, который я могу найти. Например, я хочу щелкнуть вкладку «FooBar».

Если я использую плагин Selenium IDE FireFox, я получаю:

//td[12]/a/font 

Если я использую плагин FirePath Firefox, я получаю:

 html/body/form/table[2]/tbody/tr/td[12]/font 

Если к веб-странице добавлена ​​новая вкладка «Hello, World» (перед вкладкой FooBar), то вкладка FooBar изменится и будет иметь положение xpath

 //td[13]/a/font 

Что бы вы предложили сделать?

TY!

Вместо использования абсолютного xpath вы можете использовать relateive xpath, который является коротким и надежным.

Сказать

 FooBar By.id("FooBar"); By.name("FooBar"); By.xpath("//td[text()='FooBar']") //exact match By.xpath("//td[@id='FooBar']") //with any attribute value By.xpath("//td[contains(text(),'oBar')]") //partial match with contains function By.xpath("//td[starts-with(text(),'FooB')]") //partial match with startswith function 

Этот пост в блоге может быть вам полезен.

Относительная xpath – хорошая идея. relative css еще лучше (быстрее). Если возможно, укажите / запросите id для элемента. Проверьте также chrome -> check element -> copy css / xpath

Использование //td не является хорошей идеей, потому что оно вернет все ваши td узлы. Любой предикат, такой как //td[25] будет очень хрупким выбором, потому что любой td добавленный в любую предыдущую таблицу, изменит его результат. Использование плагинов для генерации XPath отлично подходит для быстрого поиска того, что вы хотите, но всегда лучше использовать его как отправную точку, а затем анализировать структуру файла для записи локатора, который будет сложнее сломать при возникновении изменений.

Лучшие локаторы привязаны к инвариантным значениям или атрибутам. Плагины обычно не будут предлагать привязки идентификаторов или атрибутов. Они обычно используют абсолютные позиционные выражения. Если вы можете переписать свой путь локатора в терминах инвариантных структур в файле, вы можете затем выбрать элементы или текст, которые вы хотите относить к нему.

Например, предположим, что у вас есть

  ... ... lots of code.... 

header that has a special word

... other tags and text but not `h1` ... ... ...
some-invariant-text other text the field that you want

Таблица имеет идентификатор. Это лучший якорь. Теперь вы можете выбрать таблицу как

 //table[@id='some-id'] 

Но во многих случаях у вас нет идентификатора или даже какого-то другого инвариантного атрибута. Вы все же можете попытаться обнаружить шаблон. Например: предположим, что последний

до

таблицы содержит слово, которое вы можете сопоставить, вы все равно можете найти таблицу, используя:

 //table[preceding::h1[1][contains(.,'word')]] 

Когда у вас есть таблица, вы можете использовать относительные оси для поиска других узлов. Предположим, вы хотите td но нет никаких атрибутов ни на одном, ни на tr , и т. Д. Вы все равно можете искать некоторый инвариантный текст. В таблицах обычно есть заголовки или какой-то фиксированный текст, который вы можете сопоставить. В приведенном выше примере, если вы найдете td который является 2 поля до того, который вы хотите, вы можете использовать:

 //table[preceding::h1[1][contains(.,'word')]]/td[preceding-sibling::td[2][.='some-invariant-text']] 

Это простой пример. Если вы примените некоторые из этих предложений к файлу, над которым работаете, вы можете улучшить свое выражение XPath и сделать код выбора более надежным.