Обычно я сталкиваюсь с такими неприятностями, когда смотрю на спецификацию.
Как вы, вероятно, знаете, в текущей спецификации нет ни одного для :contains()
, и поэтому вы полагаетесь на недокументированные, неисследованные функции конкретного браузера / анализатора. Это должно работать, но это не так - очевидно, реализация не была завершена. И теперь псевдокласс ушел.
Не могли бы вы вместо этого пойти на XPath ? Либо внутренними методами Selenium, либо JavaScript . Этот XPath совпадает с вашим селектором CSS номер 2:
//div[contains(text(),'My Header Title')]/following-sibling::div//input[contains(@class,'my_button')]
EDIT
После того, как ваш комментарий показал мне, что мы говорим о Selenium RC и, следовательно, Sizzle, я копнул глубже.
Я взял ваш пример HTML, снял его со скрытых и (казалось бы) ненужных элементов и остался с этим:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8" />
<script src="sizzle.js" type="text/javascript"></script>
</head>
<body class="bp">
<div class="container">
<div id="nav_bar">
<div id="user_bar">
<div id="wrapper" style="border-radius: 10px 10px 10px 10px;">
<div class="content">
<div class="breadcrumb_trail">
<div class="organizer_widget root_organizer" title="WorkflowItem" style="">
<div class="object organizer">
<div class="interior">
<form method="POST" enctype="multipart/form-data">
<div class="organizer_header view_header"> My Header Title </div>
<div class="organizer_widget" title="Citation" style="">
<div id="citation" class="object organizer">
<div class="clear"></div>
<div class="interior">
<div id="Citation___id_widget" class="widget_row numeric">
<div id="Citation___title_widget" class="widget_row string">
<div id="Citation___abbreviated_title_widget" class="widget_row string">
<div id="Citation___authors_display_string_widget" class="widget_row string">
<div id="Citation___language_widget" class="widget_row choice">
<div id="Citation___link_widget" class="widget_row link">
<input id="ba_citation" class="my_button" type="button" value="Break Associations" name="break_assoc_5376dcc81102a5d76bf829513b096be8f67e560d" />
<div class="clear"></div>
</div></div></div></div></div></div>
</div>
</div>
</div>
</form>
</div>
</div>
</div>
</div>
</div>
</div>
</div>
</div>
</div>
</body>
</html>
Я скачал последний Sizzle и получил версию Sizzle, которая фактически используется Selenium в текущем выпуске .
Оказывается, эти два очень разные.
например. contains
реализация текущего Sizzle:
return ~( elem.textContent || elem.innerText || getText( elem ) ).indexOf( match[3] );
и реализация Selenium использует:
return (elem.textContent || elem.innerText || getText([ elem ]) || "").indexOf(match[3]) >= 0;
Я попробовал обе реализации в моем тестовом документе, результаты можно увидеть здесь (нажмите, чтобы увеличить):
Current Sizzle - идеально подходит всем
Sizle's Sizzle - соответствует 1 из 4
Результаты говорят сами за себя. Selenium использует старую версию Sizzle, которая как-то несовершенна в обработке псевдокласса :contains()
. Текущая версия Sizzle не страдает от этой ошибки и может хорошо найти все элементы.
Теперь вы можете сделать любой из этих:
- Файл ошибки Selenium.
- Используйте XPath в качестве обходного пути.
- Переключите файл
sizzle.js
в свой пакет Selenium.